This is a short introduction for newbies. The following sections describe how to setup a system to cross compile, that means creating binaries (executables) for a different platform as the one used for compilation - e.g. working under Linux and creating Win32 executables (or those for FreeBSD or Darwin, etc.). In this case, the platform used for compilation is usually referred to as "host" (Linux in the example above) and the platform where you want to run your created binaries is your "target". FreePascal is a compiler and basically converts source into binaries (machine language). These binaries also contain information on how the operating system starts the executables. Moreover, the binaries refer to the APIs provided by the particular operating system, that's why different implementation of our Run-Time Library is necessary for different operating systems. Therefore these binaries are platform specific. FreePascal itself does not need much setup. It can create binaries for many platforms. Just tell it to do so.
Host and target on the same CPU
FPC is designed so that the distributed compiler can create machine code for a certain CPU (because different CPUs need different machine code) and it knows specific requirements for all supported platforms (operating systems) available on that particular CPU. This means that you can perform cross-compilation with the same compiler used for native compilation as long as you stick to the same CPU.
Host and target on different CPUs
If you need to create binaries for a different CPU, you need a special cross-compiler, i.e. compiler running on the host platform, but able to create machine code for a different CPU (in the case of FPC, such a cross-compiler would be again able to target all supported platforms available on the _target_ CPU). This cross-compiler is then usually stored in the same directory as the native compiler. Such a cross-compiler may be either compiled by yourself, or you can use a ready made distributed cross-compiler provided for some platforms directly by the FPC team (usually platforms mostly used in portable devices like arm-linux or arm-wince, because these are usually not used as host platforms). Fpc binary can then select the right compiler (either the native compiler or the cross-compiler) for the target CPU selected using the -P parameter.
The compiler is only one part. We also need the assembler and the linker. FPC provides internal assembler and/or linker for just some platforms, other platforms needs to use external tools for that. And these tools are usually not able to create binaries for different platforms. That's why we have to different special linker 'ld' and assembler 'as' for every target platform. These are the binutils.
Units for target
After creating (or having/installing) the cross tools, one needs FPC RTL and other units compiled for the chosen target platform. For example, every target platform needs a different file system.ppu (System unit), etc. These units may be either compiled using your compiler set up for compilation to the target platform, or you may potentially use officially distributed units compiled (and distributed) with exactly the same FPC version (if available in format useable under the particular host platform).
Then your fpc config file will be setup, so that cross compilation becomes so easy, that you can forget all the boring details. The same will be done for the LCL - the lazarus component library (if using Lazarus). And after this you can cross compile pascal programs for the (different) target platform. The resulting binaries may then be copied to a machine running the target platform, or run under an emulator (e.g. Wine for Win32 binaries under Linux, etc.).
There are a few common steps involved in crosscompiling that you must do in every case:
- Have already a FreePascal compiler for the platform you wish to compile from.
- You need to have the FreePascal source code (except for the special case of having everything prepared by someone else).
- You need to either build from source or obtain binaries of the cross-binutils that run on the platform you are on and are designed to build programs for your desired target platform.
- Sometimes you will need some files from the target you are compiling to.