Object files providing support for basic runtime facilities and added to the produced binaries at the start and at the end of linking.
Table of CRT objects for popular toolchains.
crtx ones are generally distributed with libc and the
begin/end ones with gcc.
See https://dev.gentoo.org/~vapier/crt.txt for some more details.
|Pre-link CRT objects||glibc||musl||bionic||mingw||wasi|
|dynamic-nopic-exe||crt1, crti, crtbegin||crt1, crti, crtbegin||crtbegin_dynamic||crt2, crtbegin||crt1|
|dynamic-pic-exe||Scrt1, crti, crtbeginS||Scrt1, crti, crtbeginS||crtbegin_dynamic||crt2, crtbegin||crt1|
|static-nopic-exe||crt1, crti, crtbeginT||crt1, crti, crtbegin||crtbegin_static||crt2, crtbegin||crt1|
|static-pic-exe||rcrt1, crti, crtbeginS||rcrt1, crti, crtbeginS||crtbegin_dynamic||crt2, crtbegin||crt1|
|dynamic-dylib||crti, crtbeginS||crti, crtbeginS||crtbegin_so||dllcrt2, crtbegin||-|
|static-dylib (gcc)||crti, crtbeginT||crti, crtbeginS||crtbegin_so||dllcrt2, crtbegin||-|
|static-dylib (clang)||crti, crtbeginT||N/A||crtbegin_static||dllcrt2, crtbegin||-|
|Post-link CRT objects||glibc||musl||bionic||mingw||wasi|
|dynamic-nopic-exe||crtend, crtn||crtend, crtn||crtend_android||crtend||-|
|dynamic-pic-exe||crtendS, crtn||crtendS, crtn||crtend_android||crtend||-|
|static-nopic-exe||crtend, crtn||crtend, crtn||crtend_android||crtend||-|
|static-pic-exe||crtendS, crtn||crtendS, crtn||crtend_android||crtend||-|
|dynamic-dylib||crtendS, crtn||crtendS, crtn||crtend_so||crtend||-|
|static-dylib (gcc)||crtend, crtn||crtendS, crtn||crtend_so||crtend||-|
|static-dylib (clang)||crtendS, crtn||N/A||crtend_so||crtend||-|
Use cases for rustc linking the CRT objects explicitly: - rustc needs to add its own Rust-specific objects (mingw is the example) - gcc wrapper cannot be used for some reason and linker like ld or lld is used directly. - gcc wrapper pulls wrong CRT objects (e.g. from glibc when we are targeting musl).
In general it is preferable to rely on the target’s native toolchain to pull the objects. However, for some targets (musl, mingw) rustc historically provides a more self-contained installation not requiring users to install the native target’s toolchain. In that case rustc distributes the objects as a part of the target’s Rust toolchain and falls back to linking with them manually. Unlike native toolchains, rustc only currently adds the libc’s objects during linking, but not gcc’s. As a result rustc cannot link with C++ static libraries (#36710) when linking in self-contained mode.
Which logic to use to determine whether to fall back to the “self-contained” mode or not.