When trying to run the ld command with the -melf_i386 option, i get this error:
ld -melf_i386 helloWorld.o -o hello
ld: unknown option: -melf_i386
This option does work on Linux.
How do I fix this?
You can't. macOS does not support ELF binaries, and its linker does not support ELF output. As such, the -melf_i386 option does not exist. (Indeed, the entire -m option for selecting an emulation does not exist either; macOS handles subarchitectures in a rather different way from Linux.)
If you are trying to create ELF binaries for a Linux system, you will need to install a cross-compile toolchain. I'm not aware of any prebuilt toolchains for this purpose; most developers targeting Linux systems do not compile software on macOS. A more viable option may be a Linux virtual machine.
If you are trying to create an ELF binary to run on the macOS system, you're out of luck. That isn't possible.
If you are trying to follow a tutorial on assembly programming, be warned that the macOS system call interface is not compatible with the one on Linux. Use a Linux system (or virtual machine) to follow this tutorial.
Related
when i run a command in terminal (Using El Capitan)
ld -m elf_i386 -T linker.ld -o kernel kasm.o kc.o
It shows the following error :
ld: warning: option -m is obsolete and being ignored
ld: file not found: elf_i386
Can anybody help me with this?
when i run a command in terminal
You are trying to link some kind of kernel using ld directly. This is actually one of very few cases where using ld directly is appropriate.
However, the command line arguments you give to ld assume that you are using GNU-ld (you may have copied them from a Linux tutorial), but you are not using GNU-ld, you are using MacOS native linker, which doesn't understand these arguments.
Can anybody help me with this?
Please ask a separate question, along the lines of "I am trying to build XXX on MacOS, following tutorial YYY, and don't understand how to adjust this Linux command to Mac OS".
Note that it may not be possible to build XXX on MacOS at all. In particular, the ld manpage does not mention ELF as possible output, so if your "build XXX" goal includes building an ELF kernel, you'll likely need to build a cross-linker (a GNU-ld linker which runs on Mac OS (i.e. hosted on Mac OS), but produces code for ELF target.
I'm trying to compile and link an assembly file to an executable with NASM and the standard LD linker on my MacBook Air M1. I have no problems with getting the .o file, but if I want to link it with LD, it throws that error:
ld: file not found: elf_i386
Command:
ld -m elf_i386 -s -o hello hello.o
What do I have to change?
Those are options for GNU ld on x86 Linux. (Note the ELF part of the target object-file format, and the i386). MacOS uses the MachO object-file format, not ELF, and apparently their ld takes different options.
Also, MacOS hasn't supported 32-bit x86 for a few versions now, so an M1 mac with an AArch64 CPU definitely can't run 32-bit x86 executables natively.
So get an emulator for a 32-bit Linux environment if you want to follow a tutorial for that environment, or find a tutorial for AArch64 MacOS. Or possibly x86-64 MacOS which should still work transparently thanks to Rosetta, but make sure single-step debugging actually works. That's an essential part of a development environment for learning asm.
Assembly language is not portable at all, you need a tutorial for the OS, CPU-architecture, and mode (32-bit vs. 64-bit) that you're going to built in. Don't waste your time trying to port a tutorial at the same time you're learning the basics it's trying to teach. You'd have to already know both systems to know which parts of the code and build commands need to change.
I'm trying to follow this blog but on Windows and with the latest Rust. It seems to me that the correct way of doing things like this is changing very frequently with Rust, so I'm hoping for an up-to-date Windows adaptation.
What I've tried so far:
I installed gcc-arm-embedded.
I had unverified partial success manually cross-compiling libcore, but then I switched to use the recommended xargo, the functionality of which (I read) is on its way to being included in Cargo eventually. While I don't understand any of it very well, I'm hoping to get to the part where I can write/run the code and then maybe I can back into understanding the compilation better.
With japaric's awesome help, I was able to get the "aarch64" targeted build working to generate the .o file (as of this particular commit).
And this part seems to verify:
$ file target/aarch64-raspi3-none-elf/release/deps/rust_rasp-ed0c2377e0a7df81.o
target/aarch64-raspi3-none-elf/release/deps/rust_rasp-ed0c2377e0a7df81.o: ELF 64-bit LSB relocatable, ARM aarch64, version 1 (SYSV), not stripped
When I try to use the GNU Arm Embedded Toolchain linker, I get:
$ arm-none-eabi-gcc -O0 -mfpu=vfp -mfloat-abi=hard -march=armv6zk -mtune=arm1176jzf-s -nostartfiles target/aarch64-raspi3-none-elf/release/deps/rust_rasp-ed0c2377e0a7df81.o -o kernel.elf target/aarch64-raspi3-none-elf/release/deps/rust_rasp-ed0c2377e0a7df81.o: file not recognized: File format not recognized
collect2.exe: error: ld returned 1 exit status
And #rust IRC chatroom helpfuls told me that rpi3 is aarch64, not arm, so I need to find an aarch64 linker ...
I think it's working! Things I learned:
xargo is good
rpi3 is different enough from rpi2 to cause my problems in tool selection
xargo doesn't care what toolchain rustup defaults to because I'm not asking it to link for me and it does its own toolchain selection
I needed to target aarch64, not arm. For this I used the linaro aarch64 mingw32 download, unpacked, added its bin folder to my PATH. Then the aarch64 tools were easy to adapt from the blog.
For people who want to do this themselves, see https://github.com/JasonKleban/rust-rasp . Not so complicated!
I aim to blink the onboard activity led as confirmation that we do really have control, but looks like that will be kinda complicated on the rpi3 (see my readme, if still applicable)
when i run a command in terminal (Using El Capitan)
ld -m elf_i386 -T linker.ld -o kernel kasm.o kc.o
It shows the following error :
ld: warning: option -m is obsolete and being ignored
ld: file not found: elf_i386
Can anybody help me with this?
when i run a command in terminal
You are trying to link some kind of kernel using ld directly. This is actually one of very few cases where using ld directly is appropriate.
However, the command line arguments you give to ld assume that you are using GNU-ld (you may have copied them from a Linux tutorial), but you are not using GNU-ld, you are using MacOS native linker, which doesn't understand these arguments.
Can anybody help me with this?
Please ask a separate question, along the lines of "I am trying to build XXX on MacOS, following tutorial YYY, and don't understand how to adjust this Linux command to Mac OS".
Note that it may not be possible to build XXX on MacOS at all. In particular, the ld manpage does not mention ELF as possible output, so if your "build XXX" goal includes building an ELF kernel, you'll likely need to build a cross-linker (a GNU-ld linker which runs on Mac OS (i.e. hosted on Mac OS), but produces code for ELF target.
What is involved in compiling 32-bit Intel OS X binaries on a 64-bit command-line environment? Is it as simple as adding a -m32 flag? I'm not using Xcode, but could use it to install libraries that gcc could use, if needed. Thanks for your advice.
If you're compiling on a Macintosh computer using Apple's implementation of GCC, one of the extra options you can pass along is the "-arch" parameter.
The man page says this:
-arch arch
Compile for the specified target architecture arch.
The allowable values are i386, x86_64, ppc and ppc64.
Multiple options work, and direct the compiler to produce "universal"
binaries including object code for each architecture specified with -arch.
This option only works if assembler and libraries are available
for each architecture specified. (APPLE ONLY)