How to compile your MacOS desktop application for ARM64, Apple silicon M1 CPU chip

Apple silicom M1 chip, ARM64 RISC CPU

The new generation of Apple Macs and Macbooks come with a major change in the CPU. They have an Apple processor, the M1 Apple silicon chip, a RISC / ARM64 architecture.

Old intel based applications will continue to run under the Rosetta2 emulator. Applications compiled for ARM64 will run natively.

We are collecting here the steps needed to build a MacOS universal binary for your MacOS desktop application software. We are following ourselves these steps to build the v1.4.2 of our Software Product Analytics library, "SoftMeter".

We will keep updating this post while we receive any clarification requests.

1. What needs to be done

The library must be compiled as a "fat" (universal) binary. A universal binary looks no different than a regular app, but is a binary that contains two executables, one for the usual (until today) x86_64 for intel type of processors, and one for the Apple's M1 ARM64 processor. MacOS will choose which version to execute.

2. What you need to have

  • The newly released XCode 12.2 or newer version.
  • You need the MacOS SDK v11. This comes with XCode 12.2. You cannot use previous versions (e.g. v10.15) of the MacOS SDK because they do not contain the new architecture ARM64. They only contain the x86_64 architecture.
  • You do not need an Apple silicon Mac to build universal applications. You can build it on your pre-2020 Mac.
  • If your application uses 3rd party compiled binaries (e.g. OpenSLL), you must obtain universal binaries for those libraries. Our SoftMeter product analytics library does not rely on any 3rd party libraries, so it can be compiled immediately.

3. Adjust your compilation (build) settings

You only need to clear any custom setting you have put under the architecture settings. Xcode comes with the default,
"Standard architectures (Apple silicon, Intel)" which is coded as
ARCHS=arm64 x86_64.
Also make that the "build only active architecture" is NO.

4. Verify that the compiled binary contains both architectures

In MacOS terminal run the command

lifo -info path-to-your-binary-file

For example if you run this command against our SoftMeter dylib,

lipo -info libSoftMeter.dylib

you will get the result:

Architectures in the fat file: libSoftMeter.dylib are: x86_64 arm64

Note: you must use the command for the binary file inside your app bundle (not the .app bundle itself). I.e. the file under
myapp.app/contents/MacOS/myapp
This works in the same way also for the screensaver bundles (.saver).

5. Digitally sign your binary

Digitally signing your binary does not change. The "fat" binary is still a single file.

The following command will check if the file is correctly signed and also show you if it contains both architectures of x86_64 and ARM64.

codesign -dv --verbose=4 path-ti-your-binary

6. Notarize your binary with Apple

Notarizing with Apple your binary does not change. The "fat" binary is still a single file.

Appendix - Useful links

 

Add new comment