program without libc (without std lib) leads to cryptic error
The code at http://doc.rust-lang.org/guide-unsafe.html#avoiding-the-standard-library requires libc. It isn't possible to remove this line or to replace it with the platform independent rlibc. The following error occurs (playpen: http://is.gd/GWl8YT):
error: linking with `cc` failed: exit code: 1
note: cc '-m64' '-L' '/usr/lib64/rustlib/x86_64-unknown-linux-gnu/lib' '-o' 'out' 'out.o' '-Wl,--whole-archive' '-lmorestack' '-Wl,--no-whole-archive' '-nodefaultlibs' '-Wl,--gc-sections' '-pie' '-Wl,--as-needed' '-Wl,-O1' '-L' '/home/rust/.rust' '-L' '/home/rust' '-Wl,--whole-archive' '-Wl,-Bstatic' '-Wl,--no-whole-archive' '-Wl,-Bdynamic' '-lcompiler-rt'
note: /usr/lib/gcc/x86_64-unknown-linux-gnu/4.9.1/../../../../lib/Scrt1.o: In function `_start':
(.text+0x12): undefined reference to `__libc_csu_fini'
/usr/lib/gcc/x86_64-unknown-linux-gnu/4.9.1/../../../../lib/Scrt1.o: In function `_start':
(.text+0x19): undefined reference to `__libc_csu_init'
/usr/lib/gcc/x86_64-unknown-linux-gnu/4.9.1/../../../../lib/Scrt1.o: In function `_start':
(.text+0x25): undefined reference to `__libc_start_main'
collect2: error: ld returned 1 exit status
error: aborting due to previous error
I want to use libcore, that doesn't require libc (http://doc.rust-lang.org/core/). The libcore code example in the guide (http://doc.rust-lang.org/guide-unsafe.html#using-libcore) has no libc dependency, but the playpen link in the top right of the code example reinserts it and removing it leads to the same error as above (http://is.gd/sxVAr0).
I also encountered this error in Rust 0.13 nightly, and it prevents me from continuing.
Daniel A.A. Pelsmaeker at 2014-11-04 23:18:16
The
rlibclibrary provides a low quality implementation of a few primitives required by LLVM for the freestanding use case. It is not going to replace the platform's standard C library in a hosted environment. This is a documentation issue, not a bug in the compiler or libraries.It's not likely that Rust will support running in a hosted environment without the platform's usual entry point. It does support freestanding usage, but in that environment the programmer is responsible for providing the entry code.
Daniel Micay at 2014-11-04 23:23:14
So, if I understand correctly,
extern crate libcremoves the errors but the resulting binary won't be freestanding. If I want a freestanding binary, how would I go about providing the missing functions__libc_csu_fini,__libc_csu_initand__libc_start_main(and others)?Daniel A.A. Pelsmaeker at 2014-11-05 00:19:12
Those functions are provided by the C runtime and it's not trivial to replicate all of the functionality yourself. You need to handle differences between Linux kernel versions and set up stuff like the vdso yourself. It would be a much better idea to use a C standard library implementation like musl... I can't see an advantage to reinventing this wheel.
Daniel Micay at 2014-11-05 00:37:25
Anyway, you really don't want to be calling the raw system calls yourself. For example, the
setuidsystem call really only changes theuidof the thread rather than the process and you need to set up a bunch of real-time signal magic to interrupt the other threads and set it globally. That's just a small example of the obstacles you're going to face if for some reason you decide to build everything from the ground up. It's certainly not necessary to get a binary without any external library dependencies.Daniel Micay at 2014-11-05 00:39:03
If you want to write an OS Kernel or something like that compile your crate as a staticlib and link it manually with some entry code (that provides a stack and sets the stack limit in fs:XY). Not sure if there's a better way to do this but at least it works :)
Philipp Oppermann at 2014-11-05 09:49:28
Thanks, I indeed intended to try my hand at writing an operating system kernel, which is why I was looking at freestanding Rust. I'll look into
staticlib.Daniel A.A. Pelsmaeker at 2014-11-05 09:52:25
This doesn't seem to be an actual bug, then.
Steve Klabnik at 2015-03-08 13:55:15
@steveklabnik maybe the real bug is how cryptic the error is?
Carl Patenaude-Poulin at 2015-12-28 19:12:38
@lilred this issue was opened a very long time ago, does the same thing happen today? I've been doing osdev and I haven't run into it.
Steve Klabnik at 2015-12-28 19:19:06
Carl Patenaude-Poulin at 2015-12-28 19:20:26
Just a quick brain dump since I'm on mobile right now:
I think I ran into this error back then when I tried to build a
no_stdexecutable. The solution was to build it as a staticlib instead and link it manually.I think the main problem is that an
executableisn't well defined without an operating system andlibc. But the docs were/are very sparse on this topic, so I think we should at least improve them.The error message is so cryptic because it is an error from the linker. I'm not sure if it can be improved easily.
Philipp Oppermann at 2015-12-28 19:44:11
The error message is so cryptic because it is an error from the linker. I'm not sure if it can be improved easily.
Yes, this is my fear as well. Hrm.
Steve Klabnik at 2015-12-28 20:12:27
Re-opening just in case, and re-tagging diagnostics.
Steve Klabnik at 2015-12-28 20:12:45
This still happens today:
error: linking with `cc` failed: exit code: 1 | = note: "cc" "-Wl,--as-needed" "-Wl,-z,noexecstack" "-m64" "-L" "/home/josh/.rustup/toolchains/nightly-x86_64-unknown-linux-gnu/lib/rustlib/x86_64-unknown-linux-gnu/lib" "/tmp/embedtest/target/release/deps/embedtest-b44225ae3dc56b70.0.o" "-o" "/tmp/embedtest/target/release/deps/embedtest-b44225ae3dc56b70" "-Wl,--gc-sections" "-pie" "-Wl,-z,relro,-z,now" "-Wl,-O1" "-nodefaultlibs" "-L" "/tmp/embedtest/target/release/deps" "-L" "/home/josh/.rustup/toolchains/nightly-x86_64-unknown-linux-gnu/lib/rustlib/x86_64-unknown-linux-gnu/lib" "-Wl,-Bstatic" "/home/josh/.rustup/toolchains/nightly-x86_64-unknown-linux-gnu/lib/rustlib/x86_64-unknown-linux-gnu/lib/libcore-d213300c6af4be27.rlib" "-Wl,-Bdynamic" = note: /usr/lib/gcc/x86_64-linux-gnu/6/../../../x86_64-linux-gnu/Scrt1.o: In function `_start': (.text+0x12): undefined reference to `__libc_csu_fini' /usr/lib/gcc/x86_64-linux-gnu/6/../../../x86_64-linux-gnu/Scrt1.o: In function `_start': (.text+0x19): undefined reference to `__libc_csu_init' /usr/lib/gcc/x86_64-linux-gnu/6/../../../x86_64-linux-gnu/Scrt1.o: In function `_start': (.text+0x26): undefined reference to `__libc_start_main' collect2: error: ld returned 1 exit statusJosh Triplett at 2017-07-21 18:33:15
This is still a problem. @phil-opp suggested this was due to Rust not clearly defining what an executable is in a freestanding environment. This also seems to happen when invoking
rustcwith-gand--omit=obj,linkinRUSTFLAGS. It seems like the compiler gets confused and infers that debugging flags require a hosted environment, so switches to the host architecture for its compilation target?New working playpen: https://play.rust-lang.org/?gist=3291629081e07458e1dae21bf12660f7&version=nightly&mode=debug
Joshua Barretto at 2018-05-01 08:54:49
It seems like the C runtime is always linked when compiling for the host OS, even without a
libcdependency (at least on Linux). Passing-nostartfilesto the linker fixes this problem on Linux.Philipp Oppermann at 2018-05-01 16:53:06
I did manage to get a Rust program to link with
-nostdlib, which removed these errors, but got the following spurious warning:warning: unused attribute --> src/main.rs:4:1 | 4 | #[link_args="-nostdlib"] | ^^^^^^^^^^^^^^^^^^^^^^^^ |Josh Triplett at 2019-01-14 21:43:22
I did manage to get a Rust program to link with
-nostdlib, which removed these errors, but got the following spurious warning:warning: unused attribute --> src/main.rs:4:1 | 4 | #[link_args="-nostdlib"] | ^^^^^^^^^^^^^^^^^^^^^^^^ |Just figured out, you can avoid this warning by putting
[target.x86_64-unknown-linux-gnu] rustflags = [ "-C", "link-arg=-nostdlib" ] [build] target = "x86_64-unknown-linux-gnu"into
.cargo/configThomas Shufps at 2021-03-23 10:39:05