Skip to content

Compiling on Macs with Apple Silicon

Casper Jeukendrup edited this page Jun 7, 2023 · 24 revisions

It is not yet possible to create a native Apple Silicon (ARM) build, mainly because Qt 5.15 (which we are using) does not support ARM yet. Therefore, you will need to build in Intel mode (x86_64) and run under Rosetta 2.

Contents

Method 1: Using a Dual HomeBrew Installation

This is the official, easiest, most convenient and non-destructive method.

Build tools

Build tools like CMake, Ninja and Git can be installed in ARM mode.

  1. Install HomeBrew in ARM mode:

    /bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"

    Follow the instructions that appear after running this command.

  2. Install CMake, Ninja and Git:

    brew install cmake ninja git

Packages

Install Qt as described here: Install Qt and Qt Creator.

MuseScore depends on a package called libsndfile. Because you are building MuseScore in x86_64 mode, you must also install this package in that mode. Otherwise, it will cause linker errors. Below are instructions for how to do this.

Generally, you can use arch -x86_64 command to run command in x86_64 mode. This should ask you to install Rosetta 2 if you haven't done that yet. We will use this to install HomeBrew in x64_64 mode, which allows us to install libsndfile in x86_64 mode.

Homebrew behaves differently in x86_64 mode. In ARM mode, it puts its packages in /opt/homebrew/bin. In x86_64 mode, it puts packages in /usr/local/bin. If you installed Homebrew correctly, /opt/homebrew/bin should appear in the $PATH variable before /usr/local/bin. This means that your shell will first look in /opt/homebrew/bin when searching for the brew command or any packages installed so that the ARM version will be used by default. If you want to use the x86_64 version instead, you must prepend /usr/local/bin to the $PATH variable. You can do that by prepending PATH=/usr/local/bin:$PATH to a command (or by running export PATH=/usr/local/bin:$PATH, but that will affect all future commands in the current session). Note that we use colons here (:), not semicolons.

  1. Install HomeBrew in x86_64 mode:
    arch -x86_64 /bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
  2. Install pkg-config and libsndfile in x86_64 mode:
    PATH=/usr/local/bin:$PATH arch -x86_64 brew install pkg-config libsndfile

Tip: You can set an alias for HomeBrew in x86_64 mode. For example, in your shell profile (~/.zprofile, ~/zshrc, or ~/.profile), you can add:

alias brew_intel="PATH=/usr/local/bin:\$PATH arch -x86_64 brew"

This allows you to use it like:

brew_intel install pkg-config libsndfile

Compiling MuseScore

Now that we have these things installed, we can start building MuseScore.

# Inside the MuseScore source code directory:
PATH_TO_QT=~/Qt/5.15.2/clang_64/bin # This is the default location, but it might be different for you
PATH=$PATH_TO_QT:/usr/local/bin:$PATH ./build.cmake

Note that the body of the second command is just ./build.cmake. See Compile on the command line for information about this script.

The PATH=$PATH_TO_QT:/usr/local/bin:$PATH prefix of the command ensures that the $PATH variable is set correctly. When CMake searches for a package, it will look in the directories mentioned in $PATH one by one. So when it looks for Qt, it will first look in the first directory, where it will immediately find Qt, because the first directory was the Qt directory. When it then looks for pkg-config and libsndfile, it won't find them in the first directory (that was the Qt directory), but it will find them in the second directory, which is /usr/local/bin, where we just installed them using HomeBrew. When it looks for, for example, Ninja, it won't find it in the first two directories, but then it will look in /opt/homebrew/bin, and there it will be found, because that one was installed in arm64 mode.

You probably don't want to specify those PATHs every time you run the script. As described on the page about build.cmake, you can also specify these things in a build_overrides.cmake file:

set(ENV{QTDIR} "$ENV{HOME}/Qt/5.15.2/clang_64") # or wherever Qt is located; note that we are not adding "/bin" to the path
set(ENV{PATH} "/usr/local/bin:$ENV{PATH}")

Method 2: Creating a Dedicated Iterm2

If you use the Iterm2 terminal application, and you don't need to use HomeBrew for anything else, you can alternatively use the following method.

The first thing you'll want to do is dump (you can use brew list to list all of the installed packages) and uninstall your ARM brew if you have it. Of course, you should ensure you aren't using any of these packages for another dev environment. If so, you may want to check out Method 1: Using a Dual HomeBrew Installation.

Then, use these instructions for installing Iterm2:

  1. Download Iterm2 I386 shell (or any other supporting running in I386 arch mode)
  2. Unzip and move Iterm2 to your Applications folder
  3. Duplicate Iterm2, and name the duplicated item "Iterm2 Rosetta"
  4. Right-click on it, and choose "Get info"
  5. Inside the info panel, check "Open using Rosetta"

Now when you open this terminal and enter arch, it should display i386 (entering arch on your standard M1 terminal would show arm64).

This will provide a safe I386 sandbox on your M1 machine, which may also be used for other I386 projects.

All the following commands for this method will be entered in the Rosetta Iterm2 you created.

Installing Dependencies in I386 Brew Mode

  1. Install Homebrew in I386 mode in Rosetta Iterm2 (if you haven't already):
    /bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
    
  2. Install required dependencies:
    brew install cmake ninja git pkg-config libsndfile
    

This way, the linker will be happy having pkg-config and libsndfile in I386 mode, and having other brew commands running in I386 mode will not be a problem compared to the mess of managing multiple brew modes (you will only need ARM brew if you have other development libraries requesting link in ARM).

At this point, you may choose to install the packages you dumped from your ARM brew.

Install Qt as described here: Install Qt and Qt Creator.

Compiling MuseScore

Now that we have these things installed, we can start building MuseScore.

Important: the following commands need to be run in the Rosetta Iterm2 as well.

# Inside the MuseScore source code directory:
PATH_TO_QT=~/Qt/5.15.2/clang_64/bin # This is the default location, but it might be different for you
PATH=$PATH_TO_QT:/usr/local/bin:$PATH ./build.cmake

Note that the body of the second command is just ./build.cmake. See Compile on the command line for information about this script.

The PATH=$PATH_TO_QT:/usr/local/bin:$PATH prefix of the command ensures that the $PATH variable is set correctly. When CMake searches for a package, it will look in the directories mentioned in $PATH one by one. So when it looks for Qt, it will first look in the first directory, where it will immediately find Qt, because the first directory was the Qt directory. When it then looks for pkg-config and libsndfile, it won't find them in the first directory (that was the Qt directory), but it will find them in the second directory, which is /usr/local/bin, where we just installed them using HomeBrew.

You probably don't want to specify those PATHs every time you run the script. As described on the page about build.cmake, you can also specify these things in a build_overrides.cmake file:

set(ENV{QTDIR} "$ENV{HOME}/Qt/5.15.2/clang_64") # or wherever Qt is located; note that we are not adding "/bin" to the path
set(ENV{PATH} "/usr/local/bin:$ENV{PATH}")

Qt Creator

After installing the required packages using one of the methods above, you should also be able to compile MuseScore in Qt Creator using these instructions: Compile in Qt Creator.

In the CMake options section, you may need to set the value of CMAKE_PREFIX_PATH to /usr/local/bin;%{Qt:QT_INSTALL_PREFIX} (the default is %{Qt:QT_INSTALL_PREFIX}). This is so that the x86_64 mode packages are found correctly.

Unofficial information added by a community member:

Normally if you build MuseScore from the terminal, you should be able to open the project in Qt Creator following the above instructions. You may need to add a couple of environment variables in QT Creator:

  1. Navigate to the Project view
  2. Under "Project Settings", click "Environment"
  3. Use the "Add" Button to add the following environment variables. If Qt is installed somewhere differently for you, make sure to change these entries to the proper location. Note that we are not adding /lib to the path.

DYLD_FRAMEWORK_PATH => {HOME}/Qt/5.15.2/clang_64/lib

DYLD_LIBRARY_PATH => {HOME}/Qt/5.15.2/clang_64/lib

Ensure that the two environment variables we just set show up in "Environment" under "Run Settings". If not, ensure it is set to "Build Environment". This is important for dynamic library loading at runtime.

At this point, you should be done! Go ahead and run in debug mode and see if there are any errors.

Known issues

macOS asks "MuseScore would like to access files in your Desktop folder" too often

Every time that you have compiled MuseScore, macOS should ask this one time (one time per folder: Desktop, Documents, Downloads). But on Apple Silicon Macs, the security is a bit more strict; this causes macOS to ask permission again and again, for every single operation MuseScore does with the file system. So, also when loading the list of recent files, macOS will ask it for each recent file again. This is annoying and not workable. The solution is to codesign the compiled MuseScore app. That means running the following command:

codesign --force --deep --sign - /path/to/install/directory/mscore.app

where /path/to/install/directory is the path specified in CMAKE_INSTALL_PREFIX.

In Qt Creator, this can be done too:

  1. Go to Projects mode
  2. Go to "Run"
  3. Under Deployment, click "Add Deploy Step" and then "Custom Process Step"
  4. Enter the following information:
    • Command: codesign
    • Arguments: --force --deep --sign - /path/to/install/directory/mscore.app where /path/to/install/directory is the path specified in CMAKE_INSTALL_PREFIX.
    • (Working directory does not matter.)

If the install directory is /Users/casper/Desktop/MuseScore/MuseScore4_Qt6.install, then the result should look like this:

Setting up the codesign step in Qt Creator

Testing

Translation

Compilation

  1. Set up developer environment
  2. Install Qt and Qt Creator
  3. Get MuseScore's source code
  4. Install dependencies
  5. Compile on the command line
  6. Compile in Qt Creator

Beyond compiling

  1. Find your way around the code
  2. Submit a Pull Request
  3. Fix the CI checks

Misc. development

Architecture general

Audio

Engraving

Extensions

Google Summer of Code

References

Clone this wiki locally