September 27, 2026

The mac mini -- Installing gcc

I play with many different micro controllers and small single board computers. Almost all of them are ARM based.

My development methodology for these is to use gcc as a cross compiler, which I have always hosted on an x86 system.

On my system right now, gcc, cc, and clang are all the same

Apple clang version 21.0.0 (clang-2100.3.34.2)
Target: arm64-apple-darwin27.0.0
Thread model: posix
InstalledDir: /Library/Developer/CommandLineTools/usr/bin
Despite the claim in the above, they all reside in /usr/bin.

Install gcc

I already have "brew" installed, so I do this:
brew install gcc
I do this in an ssh session, which makes for easy cut/paste. It needs these 7 dependencies to install gcc 16.2.0. It says something about a "bottle manifest".
gmp
isl
mpfr
libmpc
lz4
xz
zstd
I say "yes" and away it goes. It is done in no time!

However I don't see anything about binutils being installed. I'll bet this relies on the normal Apple assembler and linker. The recommendation for those is:

brew install aarch64-elf-binutils
So we do that. It takes no time at all.

But this isn't the whole story. The gcc-16 compiler yields Mach-O object files, not elf, and won't play well with the binutils we just installed. We need this:

brew install aarch64-elf-gcc
OK. That should do it.

Try it

gcc-16 --version
gcc-16 (Homebrew GCC 16.2.0) 16.2.0
Copyright (C) 2026 Free Software Foundation, Inc.
That's right -- it leaves "gcc" still pointing to Apple "clang" and we need to use "gcc-16" which does keep things clear.

Next I try compiling a trivial program that I compiled previously using cc (i.e. clang). It works! It compiles without errors and the executable runs and prints a message as expected.

gcc-16 -o first first.c
Notice that this is an aarch64 (64 bit ARM) compiler. On linux I have used two different ARM compilers:
aarch64-linux-gnu-gcc
arm-none-eabi-gcc
For 32 bit arm, I used the second of the above, typically with these switches:
arm-none-eabi-gcc -nostdinc -fno-builtin -marm -mcpu=cortex-a7 -mfpu=vfpv4
On 64 bit arm, I use the following:
aarch64-linux-gnu-gcc -nostdinc -fno-builtin -march=armv8-a+crc -mtune=cortex-a53
Let's try this:
gcc-16 -march=armv8-a+crc -c first.c
gcc-16 -march=armv8-a+crc -mtune=cortex-a53 -c first.c
It swallows both of those options without complaint and gives me first.o in each case.

What about 32 bit ARM?

So this may be a perfectly adequate gcc for 64 bit ARM projects, but what about 32 bit ARM?
You can choose between these:

brew install arm-none-eabi-gcc
brew install --cask gcc-arm-embedded
I am pleased that these are offered! I won't dive into the "cask" install until I understand exactly what it is all about, but the first looks too good to pass up.
Brew tells me it is downloading arm-none-eabi-binutils, which is very important as it will give me the assembler as well as the linker "ld".

Conclusion

Now we have 4 different ARM C compilers installed!
The original clang
gcc-16 for non-cross compiles
arm-none-eabi-gcc for 32 bit cross compiles
aarch64-elf-gcc for 64 bit cross compiles

Now I should try cloning Kyu and building it. First for an H3 target (32 bit). Then for an H5 target (64 bit).

That will end up requiring a tftp server -- which is a topic for another page.


Have any comments? Questions? Drop me a line!