Running a Swift Command Line Application's Executable Target on Linux

I have made a command line application in Swift. When I run the executable product it produces on my Mac, everything is fine and it works as expected. But when I copy the executable over to my Linux machine, it doesn't work and produces the following error:

-sh: ./script: cannot execute binary file: Exec format error

I assume that this is because Linux and MacOS use different executable file formats. With this in mind, I was wondering if it is possible to build the executable product in a format that will be able to run on my Linux machine, but I haven't been able to find any straightforward way to do this in Xcode thus far. Another option might be to convert the executable file to a supported format but I'm not sure if that is something that one can do either.

Here are the details on my Linux machine:

  Operating System: FSLC Wayland 3.1 (dunfell)
            Kernel: Linux 5.4.85+gedb81d8afdfe
      Architecture: arm64

How can I fix this to get the executable running on my Linux machine?

The simple answer is you can't move binaries between O/S architectures (Linux uses ELF formatted binaries, Darwin/MacOSX uses Mach-O formats, libraries are different, O/S primitive calls are different, etc.). Xcode only builds for Darwin based O/Ss (macOS, iOS, iPadOS, tvOS, watchOS).

Take the source code, compile and link on the Linux system.

Is your Mac an M1 Mac? The only Mac that supports arm64 is the M1 Mac, everything else is an x86_64 machine. That right there is a fundamental difference if you are not using an M1 Mac. They use radically different instruction sets.

I have access to both an M1 Mac and an Intel based Mac. Unfortunately the running the executable product compiled on either of the Macs on my Linux machine fails.

Do you know if the linux machine I have supports Swift by any chance?

To be expected, as I talked about above.

Not sure what "FSLC" means with regard to identifying a LInux variant. If you lookup something like "Swift Linux arm64" you'll find a variety of sources for arm64 versions of Swift. You'll have to look at the operating systems they delineate (CentOS, Ubuntu, Amazon Linux 2, Android (considered a Linux), Raspberry Pi, etc.) to see if there is a close enough match to your setup.

I just want to add that you don't need to compile on that particular Linux machine of yours. You could also compile within a Linux Docker container on your Macs that fit the right architecture -- arm64 in your case. This would be an option if you can't find a Swift version for your particular Linux distribution.

Once the static Linux version (for arm64) is build, you can just copy it to your FSLC Wayland system (which I also don't know what it means). If you build the executable with dynamic linking, then you must also have the Swift libraries installed on your target system.

1 Like