Build LLVM for Apple M1 (MacOS Big Sur)

I hope this is on topic for this list, since I expect that someone here must already have done this successfully, while I am still foundering around.

What I want to achieve is to build LLVM (and, in particular, clang/clang++ with OpenMP support) to run on and target the Apple M1 ARM processor running MacOS Big Sur. (I have a new Mac Mini :-)).
Ideally, it would be nice to be able to build a dual target fat-binary in which the X86_64 component compiled for X86_64 by default, and the Aarch64 component compiled or Aarch64 by default (this is what the Apple compiler in Xcode does…), however just being able to build an Aarch64 compiler that worked would be ahead of what I have managed to achieve.

My best attempt is configured using this script from a build directory inside the top-level llvm checkout.
The compilers found are those from Xcode.

Xcode, Ninja

BUILD_SYSTEM=Ninja
BUILD_TAG=ninja

cmake …/llvm
-G$BUILD_SYSTEM -B ${BUILD_TAG}_build
-DCMAKE_OSX_ARCHITECTURES=‘arm64’
-DCMAKE_C_COMPILER=which clang
-DCMAKE_CXX_COMPILER=which clang++
-DCMAKE_BUILD_TYPE=Release
-DCMAKE_BUILD_WITH_INSTALL_RPATH=1
-DCMAKE_INSTALL_PREFIX=$HOME/software/clang-12.0.0/arm64
-DLLVM_LOCAL_RPATH=$HOME/software/clang-12.0.0/arm64/lib
-DLLVM_ENABLE_WERROR=FALSE
-DLLVM_TARGETS_TO_BUILD=‘AArch64’
-DLLVM_DEFAULT_TARGET_TRIPLE=‘aarch64-apple-darwin20.1.0’
-DDEFAULT_SYSROOT=“$(xcrun --show-sdk-path)”
-DLLVM_ENABLE_PROJECTS=‘clang;openmp;polly;clang-tools-extra;libcxx;libcxxabi’

Configured like that I can build a compiler, OpenMP runtime and so on.

However…

  1. when linking it does not add -L$HOME/software/clang-12.0.0/arm64/lib to the linker command, so it fails to link OpenMP codes which require libomp.dylib, since it doesn’t find it. (See below: you can see that it did add the local, LLVM, include directory, so was able to find <omp.h>).
  2. If I fake that by explicitly adding the -L command, then it links OK, but fails to find libomp.dylib at runtime, even though it does look in some “brew” related places (despite not having anything like that in any envirables).

$ ./a.out
dyld: Library not loaded: @rpath/libomp.dylib
Referenced from: /Users/jcownie/tmp/./a.out
Reason: no suitable image found. Did find:
/usr/local/lib/libomp.dylib: mach-o, but wrong architecture
/usr/local/Cellar/libomp/11.0.0/lib/libomp.dylib: mach-o, but wrong architecture
Abort trap: 6

Any help gratefully received!

(I have a StackOverflow question at https://stackoverflow.com/questions/65293299/how-to-build-llvm-clang-clang-for-apple-m1 which contains similar information to that I have inlined here; if you would rather answer there, that’s fine, but don’t feel bound to. If i get an answer here i’ll update that myself so others can see it.)

Thanks

– Jim
James Cownie <jcownie@gmail.com>
Mob: +44 780 637 7146

Compilation, and linkage failure.

$ ~/software/clang-12.0.0/arm64/bin/clang -v -fopenmp hello_omp.c
clang version 12.0.0 (https://github.com/llvm/llvm-project.git 975b64b29375cdfb3672fedee4216c6512672fbf)
Target: aarch64-apple-darwin20.2.0
Thread model: posix
InstalledDir: /Users/jcownie/software/clang-12.0.0/arm64/bin
“/Users/jcownie/software/clang-12.0.0/arm64/bin/clang-12” -cc1 -triple arm64-apple-macosx11.0.0 -Wundef-prefix=TARGET_OS_ -Werror=undef-prefix -Wdeprecated-objc-isa-usage -Werror=deprecated-objc-isa-usage -emit-obj -mrelax-all --mrelax-relocations -disable-free -disable-llvm-verifier -discard-value-names -main-file-name hello_omp.c -mrelocation-model pic -pic-level 2 -mframe-pointer=non-leaf -fno-rounding-math -munwind-tables -fcompatibility-qualified-id-block-type-checking -fvisibility-inlines-hidden-static-local-var -target-cpu apple-a12 -target-feature +v8.3a -target-feature +fp-armv8 -target-feature +neon -target-feature +crc -target-feature +crypto -target-feature +fullfp16 -target-feature +ras -target-feature +lse -target-feature +rdm -target-feature +rcpc -target-feature +zcm -target-feature +zcz -target-feature +sha2 -target-feature +aes -target-abi darwinpcs -fallow-half-arguments-and-returns -debugger-tuning=lldb -target-linker-version 609.8 -v -resource-dir /Users/jcownie/software/clang-12.0.0/arm64/lib/clang/12.0.0 -isysroot /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk -internal-isystem /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/local/include -internal-isystem /Users/jcownie/software/clang-12.0.0/arm64/lib/clang/12.0.0/include -internal-externc-isystem /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/include -fdebug-compilation-dir /Users/jcownie/tmp -ferror-limit 19 -fmessage-length=167 -fopenmp -fopenmp-cuda-parallel-target-regions -stack-protector 1 -fblocks -fencode-extended-block-signature -fregister-global-dtors-with-atexit -fgnuc-version=4.2.1 -fmax-type-align=16 -o /var/folders/lt/nf3dtk8j16qfsl97d_vgv4dw000lts/T/hello_omp-ea548e.o -x c hello_omp.c
clang -cc1 version 12.0.0 based upon LLVM 12.0.0git default target aarch64-apple-darwin20.2.0
ignoring nonexistent directory “/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/local/include”
ignoring nonexistent directory “/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/Library/Frameworks”
#include “…” search starts here:
#include <…> search starts here:
/Users/jcownie/software/clang-12.0.0/arm64/lib/clang/12.0.0/include
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/include
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/System/Library/Frameworks (framework directory)
End of search list.
“/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/ld” -demangle -lto_library /Users/jcownie/software/clang-12.0.0/arm64/lib/libLTO.dylib -no_deduplicate -dynamic -arch arm64 -platform_version macos 11.0.0 0.0.0 -syslibroot /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk -o a.out /var/folders/lt/nf3dtk8j16qfsl97d_vgv4dw000lts/T/hello_omp-ea548e.o -lomp -lSystem
ld: library not found for -lomp
clang-12: error: linker command failed with exit code 1 (use -v to see invocation)
$

I have the same problem. Can someone help?

How to build LLVM fat binaries for M1, in which the X86_64 component generates X86_64 code by default, and the Aarch64 component generates Aarch64 code by default (this is what the Apple compiler in Xcode does)?

The fat binaries we built on my x86_64 OSX host, with clang -arch arm64 -arch x86_64 , always produce code for x86_64 target by default, irrespective of which arch is executing on M1.

To be more clear:
Xcode clang works as:
$ arch -arm64 clang -c a.c ; produces arm64 a.o
$ arch -x86_64 clang -c a.c ; produces x86_64 a.o

The fat binary I built on x86_64 OSX always produces x86_64 a.o by default, irrespective of the arch being executed.