Sign in Join
Wiki copytemporary

Cross compiling for Win32 under Linux/it: what changed

Revision 3 to 4. Removed lines have a minus sign; added lines have a plus sign.

OldNewLine
11## Suggerimenti per la Cross-Compilazione - creazione di binari per Win32 in ambiente Linux
22
33Dalla versione 0.9.10 esiste un rpm 'fpc-crosswin32', che installa i *binutils* necessari (p.e. cross assembler, cross linker), i file .ppu di fpc cross-compilati per win32 e modifica il file /etc/fpc.cfg.
44
55Tuttavia non include i file cross-compilati .ppu dell'LCL. É necessario che questi siano compilati dall'utente dopo l'installazione dell'fpc-crosswin32.
66
77## Lazarus ed il Compilatore Free Pascal
88
99### La Cross-compilazione - cosa bisogna sapere
1010
1111Questo è una breve introduzione per i novizi.
1212
1313La sezione seguente descrive come impostare il sistema per la cross-compilazione, in modo tale che lavori sotto linux e crei eseguibili per win32 (o freebsd o dawin, o ...). Perché usare la cross-compilazione: il FreePascal è un compilatore con l'obiettivo di convertire un programma sorgente in uno binario (in linguaggio macchina). Questi file binari contengono numerose informazioni, ad esempio la descrizione di come il sistema operativo deve avviare l'eseguibile. Nella maggior parte dei casi i file binari sono specifici per una determinata piattaforma e possono essere utilizzati solo sulla piattaforma per la quale sono stati scritti.
1414
1515Di per sé il FreePascal non richiede un setup complesso. Esso è in grado di creare binari per molte piattaforme. Ed in pratica può già farlo. Tuttavia il compilatore è solo una parte. Bisogna anche tener conto dell'assembler ed del linker. E purtroppo questi strumenti non sono in grado di creare direttamente codice multipiattaforma. Ecco è necessario far riferimento a linker 'ld' e assembler 'as' specifici per ciascuna piattaforma di destinazione. Fortunatamente, per risolvere tali problemi, è possibile ricorrere alle *binutils*. Dopo aver creato gli strumenti "cross", tutte le unit pascal di fpc saranno cross-compilate. Ad esempio, ci sarà un file system.ppu per ciascuna piattaforma di destinazione. Quindi sarà necessario settare il file di config dell'fpc, così che la compilazione multipiattaforma avvenga tanto facilmente da dimenticarsi tutti i noiosi dettagli. La stessa cosà dovrà essere fatta per l'LCL - la *lazarus component library*. Infine sarà possibile compilare programmi per win32 su Linux. Successivamente i programmi realizzati si potranno testare con wine, con una macchina virtuale o copiandoli direttamente su una macchina reale windows.
1616
1717### Percé da *nix a windows e non viceversa.
1818
1919La ragione principale di ciò è che generare binari unix su una piattaforma estranea (un'altra unix o anche un'altra distribuzione Linux) è più complicato. Il linking statico è complicato di suo, maggiormente quello *shared*.
2020
2121You would need the used libraries from the target platform's (gtk, glib,libc etc), and a lot of additional configuring for ld. (library paths, dynlinker path etc)
2222
2323This has been partially done (for the static case), but it is hard since it needs manual postediting of linker files and linker commandline, and a deep understanding about what makes Unix binaries tick.
2424
2525### Download del codice sorgente del FPC
2626
2727Per realizzare programmi multipiattaforma purtroppo i binari non sono sufficienti, è dunque necessario scaricare i sorgenti completi del fpc. Si veda www.freepascal.org. Per ottenere i sorgenti è possibile usare SVN o una [daily snapshot](http://www.hu.freepascal.org/lazarus/).
2828
2929Per gli esempi che seguono si suppone che i sorgenti siano stati scaricati nella cartella *~/sources/fpc*.
3030
3131### Scaricare le gnu binutils.
3232
3333É possibile scaricare l'ultima versione delle binutils da [<http://ftp.gnu.org/gnu/binutils/>](http://ftp.gnu.org/gnu/binutils/)\
3434Supponiamo di scaricare le binutils-2.xx.tar.gz nella cartella *~/download/*.
3535
3636### Cross build binutils
3737
3838Nel repository di fpcbuild c'é uno script per creare le binutils per tutte le piattaforme: install/cross/buildcrossbinutils Prima di procedere visitate [<http://svn.freepascal.org/svn/fpcbuild/branches/>](http://svn.freepascal.org/svn/fpcbuild/branches/) e individuate la versione di vostro interesse.
3939
4040Per scaricare la cartella install da fpcbuild:
4141
42-` []$ cd ~`\
43-` []$ svn co `[`http://svn.freepascal.org/svn/fpcbuild/branches/fixes_2_2/install`](http://svn.freepascal.org/svn/fpcbuild/branches/fixes_2_2/install)` install`\
42+```text
43+ []$ cd ~
44+ []$ svn co http://svn.freepascal.org/svn/fpcbuild/branches/fixes_2_2/install install
45+```
4446
4547(nota: verrà creata una nuova cartella *install* nella vostra home - la cartella NON deve esistere!)
4648
4749Creare una copia dello script:
4850
49-` []$ cd ~/install/cross/`\
50-` []$ cp buildcrossbinutils buildcrossbinutils.sh`
51+```text
52+ []$ cd ~/install/cross/
53+ []$ cp buildcrossbinutils buildcrossbinutils.sh
54+```
5155
5256Modificare le variabili all'inizio dello script.
5357
5458La variabile BASE punta ad una directori di lavoro ed installazione. Essa dovrebbe essere vuota. Per esempio:
5559
56-` BASE=~/cross_fpc`
60+```text
61+ BASE=~/cross_fpc
62+```
5763
5864Ora il file binutils scaricato. se per esempio è stato scaricato in ~/download/binutils-2.18.tar.gz allora impostare le variabili come segue
5965
60-` BINUTILSPATH=~/download/`\
61-` BINUTILSBASE=binutils`\
62-` BINUTILSVERSION=2.18`\
63-` BINUTILS_GZIP=yes`
66+```text
67+ BINUTILSPATH=~/download/
68+ BINUTILSBASE=binutils
69+ BINUTILSVERSION=2.18
70+ BINUTILS_GZIP=yes
71+```
6472
6573Lo script aggancerà questo automaticamente a ~/download/binutils-2.18.tar.gz. Le variabili restanti da modificare definizcono la piattaforma di destinazione desiderata. Per default verranno considerate tutti i sistemi operativi supportati, ma cò richiede molto tempo (anche alcune ore su macchine lente). Per compilazioni per Windows, è necessario solo
6674
67-` TARGETS_WIN="mingw32"`\
68-` `
75+```text
76+ TARGETS_WIN="mingw32"
77+```
6978
7079e possono essere commentate le altre righe:
7180
72-` #BSD="freebsd netbsd openbsd"`\
73-` #TARGETS_WIN="cygwin mingw32 msdosdjgpp"`\
74-` #TARGETS_I386="${BSD} linux solaris darwin"`\
75-` #TARGETS_POWERPC="${BSD} linux darwin"`\
76-` #TARGETS_SPARC="${BSD} linux solaris"`\
77-` #TARGETS_M68k=`
81+```text
82+ #BSD="freebsd netbsd openbsd"
83+ #TARGETS_WIN="cygwin mingw32 msdosdjgpp"
84+ #TARGETS_I386="${BSD} linux solaris darwin"
85+ #TARGETS_POWERPC="${BSD} linux darwin"
86+ #TARGETS_SPARC="${BSD} linux solaris"
87+ #TARGETS_M68k=
88+```
7889
7990Quindi lanciare lo script:
8091
81-` []$ sh buildcrossbinutils.sh`\
82-` `
92+```text
93+ []$ sh buildcrossbinutils.sh
94+```
8395
8496Lo script crea una sottocartella 'logs' contenente una serie di file di log. nel caso in cui ci dovessero essere errori partire osservando il contenuto di questi log.
8597
8698Si noti che per molte piattaforme (Linux,FreeBSD, win32) queste sono disponibili già in forma compilata. Si veda: <ftp://freepascal.stack.nl/pub/fpc/contrib/cross/>
8799
88100### Cross build FPC
89101
90102Nel repositorio scaricato è presente uno script per costruire l'fpc snapshot per tutte le piattaforme: install/cross/buildcrosssnapshot Creare una copia dello script:
91103
92-` []$ cd ~/install/cross/`\
93-` []$ cp buildcrosssnapshot buildcrosssnapshot.sh`
104+```text
105+ []$ cd ~/install/cross/
106+ []$ cp buildcrosssnapshot buildcrosssnapshot.sh
107+```
94108
95109Modificare le variabili all'inizio del nuovo script.
96110
97111Normalmente è sufficiente modificare almeno le seguenti: CROSSTOOLSROOT, FPCCVS, DESTDIR, TARGETS_OS e TARGETS_CPU. Ad esempio:
98112
99-` CROSSTOOLSROOT=~/cross_fpc/cross`\
100-` FPCCVS=~/sources/fpc`\
101-` TARGETS_OS="win32"`\
102-` TARGETS_CPU="i386"`\
103-` DESTDIR=~/cross_fpc/`\
104-` `
113+```text
114+ CROSSTOOLSROOT=~/cross_fpc/cross
115+ FPCCVS=~/sources/fpc
116+ TARGETS_OS="win32"
117+ TARGETS_CPU="i386"
118+ DESTDIR=~/cross_fpc/
119+```
105120
106121Lanciare lo script:
107122
108-` []$ sh buildcrosssnapshot.sh`
123+```text
124+ []$ sh buildcrosssnapshot.sh
125+```
109126
110127Fatto ciò le unit compilate si troveranno in ~/cross_fpc/
111128
112129### Configure your fpc.cfg
113130
114131Aprire come root il file /etc/fpc.cfg o creare una copia di /etc/fpc.cfg in ~/fpc.cfg ed editare questo file. Cercare nel config le stringhe seguenti:
115132
116133Nota: Su versioni obsolete di \$version e \$target sono ustae al posto di \$fpcversion e \$fpctarget
117134
118-`-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget`\
119-`-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget/*`\
120-`-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget/rtl`
135+```text
136+-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget
137+-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget/*
138+-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget/rtl
139+```
121140
122141Rimpiazzarle con il seguente codice (l'esempio è riferito ad una piattaforma linux per compilazioni win32):
123142
124-`#IFDEF win32`\
125-`-Fu~/cross_fpc/lib/fpc/$fpcversion/cross/units/i386-win32/`\
126-`-Fu~/cross_fpc/lib/fpc/$fpcversion/cross/units/i386-win32/*`\
127-`-Fu~/cross_fpc/lib/fpc/$fpcversion/cross/units/i386-win32/rtl`\
128-`-XPi686-mingw32-`\
129-`-FD~/cross_fpc/cross/bin`\
130-`#ELSE linux`\
131-`-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget`\
132-`-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget/*`\
133-`-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget/rtl`\
134-`#-Fu~/fpc/packages/*;~/fpc/rtl/linux`\
135-`#ENDIF`
143+```text
144+#IFDEF win32
145+-Fu~/cross_fpc/lib/fpc/$fpcversion/cross/units/i386-win32/
146+-Fu~/cross_fpc/lib/fpc/$fpcversion/cross/units/i386-win32/*
147+-Fu~/cross_fpc/lib/fpc/$fpcversion/cross/units/i386-win32/rtl
148+-XPi686-mingw32-
149+-FD~/cross_fpc/cross/bin
150+#ELSE linux
151+-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget
152+-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget/*
153+-Fu/usr/lib/fpc/$fpcversion/units/$fpctarget/rtl
154+#-Fu~/fpc/packages/*;~/fpc/rtl/linux
155+#ENDIF
156+```
136157
137158Infine: Testare e risolvere gli eventuali problemi
138159
139160### Compilazione multipiattaforma dell'LCL e dei componenti lazarus
140161
141162Sulla linea di comando:
142163
143-`cd lazarus; make clean all OS_TARGET=win32`\
144-`cd lazarus/lcl; make clean all `
164+```text
165+cd lazarus; make clean all OS_TARGET=win32
166+cd lazarus/lcl; make clean all
167+```
145168
146169Questo compilerà tutti i file per win32 (incluso l'IDE, che non è necessario, ma questo semplifica il tutto)
147170
148171O nell'IDE: impostare LCL, Synedit, Codetools, Package Registration e IDE Interface a Clean+Build, impostare LCL interface a win32/win64 ed impostare 'Target OS' a win32. Quindi 'build lazarus'.
149172
150173These four parts have splitted output directories, so your linux .ppu/.o files are *not* overwritten and you don't need to recompile them.
151174
152175### Cross compiling a project
153176
154177Set in Project-\>Compiler Options-\>Code the Target OS to 'win32' and in Paths the 'LCL Widget Type' to win32. That's all. The next time you build, you will create a win32 executable. The IDE will rescan for win32 units, so that 'Find declaration' and code completion features will now work with the win32 rtl instead of the linux rtl. When you open another project or reopen this project the IDE will automatically switch.
155178
156179### Hints for Cross compiling and Lazarus
157180
158181If you create an application/package for multiple targets, you will often do the following: Fix a bug, compile and test it under linux, then compile and test it under win32, .. . Because normally you overwrite your .ppu files, you have to recompile everything, everytime you switch. This is not necessary. The Lazarus IDE supports macros.
159182
160183Example 1: Cross compiling a project for linux and win32.
161184
162185Set Project -\> Compiler Options -\> Paths -\> Unit Output directory to \$(TargetOS). This macro will be replaced by the value in Code -\> TargetOS in lowercase (i.e. "linux" for Linux and "win32" for Win32). The output directory is relative to your project directory (the directory where your .lpi is). Create a linux and win32 directory in your project directory. When you click on the "Show Options" button at the bottom of the compiler options, you will see a -FElinux/ or -FEwin32/. This option tells the compiler where to write the output (e.g. .ppu/.o files).
163186
164187Example 2: Cross compiling a project for various platforms and widget sets.
165188
166189Set the Unit output directory to \$(TargetCPU)/\$(TargetOS)/\$(LCLWidgetType) and create the sub directories for all targets. This path construction is also used by the LCL.
167190
168191The same can be done for packages.
169192
170193### Cross compiling and Lazarus Packages
171194
172195Lazarus packages are not limited to libraries. They can be used to compile nearly everything. And the IDE automatically recompiles them if needed. Packages can inherit compiler options. For example: A project that uses a package inherits the output directory of the package. In other words: the output directory of the package is added to unit search path of the project. See in the IDE: Project -\> Compiler options -\> Inherited. Inheritance normally works only one way. But there are exceptions: The target platform (OS and CPU) of the project overrides the target for all used packages. That means, if you set the Target OS of the project to "win32" and compile the project, the IDE will check if the used packages need to be recompiled for this Target OS.
173196
174197For example:
175198
176199Package A has as output directory: lib/\$(TargetOS) Project uses A.
177200
1782011. The project is built for linux. The IDE compiles A for linux in \<PackageDirOfA\>/lib/linux/, then it compiles the project for linux.
1792022. The project is built for win32. The IDE compiles A for win32 in \<PackageDirOfA\>/lib/win32/, then it compiles the project for win32.
1802033. The project is built again for linux. The IDE checks A for linux and does not recompile it. Then it compiles the project for linux.
181204
182205So, using the macros saves a lot of time.
183206
184207## For Unix (general)
185208
186209Option -XLA is used to rename library dependencies specified in pascal units. Format is -XLAold=new, to modify ld link option -l\<old\> to -l\<new\>.
187210
188211Option -XR\<sysroot\> (recent trunk) that can be used to specify the target system root. It's used for:
189212
190213- adding a prefix to the default added library paths; in the past you used to specify -Xd and these paths manually. E.g. for i386-linux instead of passing /lib, /usr/lib, and /usr/X11R6/lib to ld, it will pass \<sysroot\>/lib, \<sysroot\>/usr/lib, and \<sysroot\>/usr/X11R6/lib to ld.
191214- detecting the C library (linux specific): glibc or uclibc. E.g. for uclibc detection '\<sysroot\>/lib/ld-uClibc.so.0' is tried.
192215
193216## Per Linux sotto Win32
194217
195218É possibile reperire su tale argomento (meno importante del precedente) alcune informazioni nelle [[buildfaq]]
196219
197220## FreeBSD to sparc
198221
199222I managed to crosscompile from x86 to Sparc Solaris 9. However the result doesn't work very well, but here is my cmdline:
200223
201224in compiler/ execute:
202225
203-` gmake cycle CPU_TARGET=sparc OS_TARGET=solaris CROSSBINUTILPREFIX=solaris-sparc- CROSSOPT='-Xd -Fl~/src/sollib'`
226+```text
227+ gmake cycle CPU_TARGET=sparc OS_TARGET=solaris CROSSBINUTILPREFIX=solaris-sparc- CROSSOPT='-Xd -Fl~/src/sollib'
228+```
204229
205230~/src/sollib is a directory that contains:
206231
207232- a set of .o's from /usr/local/gcc-3.3-32bit/lib/gcc-lib/sparc-sun-solaris/3.3
208233- libgcc.a from /usr/local/gcc-3.3-32bit/lib/gcc-lib/sparc-sun-solaris/3.3
209234- a set of lib*.so from /usr/lib: libaio.so libmd5.so libc.so libelf.so librt.so libdl.so libm.so
210235
211236Problem is illustrated by the following binary.
212237
213-` Free Pascal Compiler version 2.1.1 [2006/03/17] for sparc`\
214-` Copyright (c) 1993-2005 by Florian Klaempfl`\
215-` Target OS: Solaris for SPARC`\
216-` Compiling system.pp`\
217-` system.pp(15,1) Fatal: Syntax error, "BEGIN" expected but "identifier UNIT" found`
238+``` pascal
239+ Free Pascal Compiler version 2.1.1 [2006/03/17] for sparc
240+ Copyright (c) 1993-2005 by Florian Klaempfl
241+ Target OS: Solaris for SPARC
242+ Compiling system.pp
243+ system.pp(15,1) Fatal: Syntax error, "BEGIN" expected but "identifier UNIT" found
244+```
218245
219246I suspect wrong .o's are taken.
220247
221248## Per Mac OS X
222249
223250Si veda [forum post](http://www.lazarus.freepascal.org/index.php?name=PNphpBB2&file=viewtopic&p=7222#7222).
224251
225252## Contributi Originali
226253
227254Questa pagina è una traduzione dall'inglese di [Cross compiling for Win32 under Linux](http://wiki.lazarus.freepascal.org/Cross_compiling_for_Windows_under_Linux).
228255
229256---
230257*From the Free Pascal wiki, page "Cross compiling for Win32 under Linux/it", as it stood on 2021-07-20 after a change by Dbannon, out of the wiki's dump of 2024-05-26. Copyright stays with the author who wrote it, according to the old wiki's [[Licensing]] page. If you have concerns about this material, [message the admin](/wiki-contact).*

Back to history