Description
See old issue: #103687
Root cause: Dead code elimination due to mscoree.cpp refactoring in .NET 10
The chain is:
- singlefilehost_unixexports.src is unchanged — it lists MetaDataGetDispenser in both .NET 8 and .NET 10.
- mscoree.cpp was massively refactored for .NET 10:
VersionFunctions in mscoree.cppLines.NET 8/9MetaDataGetDispenser, GetMetaDataInternalInterface, GetMetaDataInternalInterfaceFromPublic, GetMetaDataPublicInterfaceFromInternal, ReOpenMetaDataWithMemory, ReOpenMetaDataWithMemoryEx, GetInternalSystemDirectory, SetInternalSystemDirectory, ...~300+.NET 10DllMain (excluded by CORECLR_EMBEDDED) + MetaDataGetDispenser60
All the internal metadata functions were moved out into the metadata subsystem directly.
- coreclr_static is compiled with CORECLR_EMBEDDED defined (as seen in the CMakeLists.txt):
With this flag, DllMain is #if'd out, leaving MetaDataGetDispenser as the only symbol from mscoree.cpp.
- Static library dead code elimination:
singlefilehost links against coreclr_static without --whole-archive. The GNU linker only pulls object files from static libraries when they resolve an undefined symbol. Since nothing in singlefilehost calls MetaDataGetDispenser, the linker never pulls mscoree.o into the binary. In .NET 8/9, mscoree.o was pulled in because it contained GetInternalSystemDirectory (and other functions) referenced from within the runtime — MetaDataGetDispenser just came along for free.
Fix for the dotnet/runtime project: force mscoree.o into the final binary, e.g. by adding -Wl,--undefined=MetaDataGetDispenser to the singlefilehost link flags, or moving MetaDataGetDispenser into a .cpp file that is already guaranteed to be linked (e.g., exports.cpp), or using attribute((used)) on the function.
PR: #116405 — "Delete extra layers" by @jkotas, merged June 9, 2025
Merge commit: c8403e6
Reproduction Steps
build single file self contained assembly and test
objdump -TC ./test | grep MetaDataGetDispenser
Expected behavior
show an exported symbol for MetaDataGetDispenser
Actual behavior
no exported symbol for MetaDataGetDispenser
Regression?
This seems to be a regression.
Known Workarounds
No response
Configuration
No response
Other information
No response
Description
See old issue: #103687
Root cause: Dead code elimination due to mscoree.cpp refactoring in .NET 10
The chain is:
VersionFunctions in mscoree.cppLines.NET 8/9MetaDataGetDispenser, GetMetaDataInternalInterface, GetMetaDataInternalInterfaceFromPublic, GetMetaDataPublicInterfaceFromInternal, ReOpenMetaDataWithMemory, ReOpenMetaDataWithMemoryEx, GetInternalSystemDirectory, SetInternalSystemDirectory, ...~300+.NET 10DllMain (excluded by CORECLR_EMBEDDED) + MetaDataGetDispenser60
All the internal metadata functions were moved out into the metadata subsystem directly.
With this flag, DllMain is #if'd out, leaving MetaDataGetDispenser as the only symbol from mscoree.cpp.
singlefilehost links against coreclr_static without --whole-archive. The GNU linker only pulls object files from static libraries when they resolve an undefined symbol. Since nothing in singlefilehost calls MetaDataGetDispenser, the linker never pulls mscoree.o into the binary. In .NET 8/9, mscoree.o was pulled in because it contained GetInternalSystemDirectory (and other functions) referenced from within the runtime — MetaDataGetDispenser just came along for free.
Fix for the dotnet/runtime project: force mscoree.o into the final binary, e.g. by adding -Wl,--undefined=MetaDataGetDispenser to the singlefilehost link flags, or moving MetaDataGetDispenser into a .cpp file that is already guaranteed to be linked (e.g., exports.cpp), or using attribute((used)) on the function.
PR: #116405 — "Delete extra layers" by @jkotas, merged June 9, 2025
Merge commit: c8403e6
Reproduction Steps
build single file self contained assembly and test
objdump -TC ./test | grep MetaDataGetDispenserExpected behavior
show an exported symbol for MetaDataGetDispenser
Actual behavior
no exported symbol for MetaDataGetDispenser
Regression?
This seems to be a regression.
Known Workarounds
No response
Configuration
No response
Other information
No response