Zabudnute schopnosti: automake a cross-compile

29.08.2009 00:51 | blackhole_ventYl

Clovek z casu na cas potrebuje skompilovat nejaky soft na inu platformu, nez na ktorej fici. Tomuto sa hovori cross-compile (chlapci od autotools tomu hovoria Canadske cross-compilovanie, zrejme to ma nieco spolocne so Svedskou trojkou). Niektore distra a niektore baliky, pripadne niektore revizovacie systemy (napr. bitbake) maju na cross-compile velmi sikovne poupravovane prostredie, ze cross-compile na inu masinu je zalezitostou jedneho prikazu v terminali.

Sem tam sa ale stane, ze sa cloveku bud nechce cele vyvojove prostredie instalovat, alebo potrebuje na inu masinu vytvorit balik a nechce sa mu na cielovu platformu tahat prekladac.

Aby sa vobec nieco dalo cross-compilnut, v prvom rade treba mat cross-compile-toolchain. Ten v minimalnej vybave pozostava z GCC beziaceho na prave prevadzkovanej platforme (napr. i686-linux) generujuceho binarky pre cielovu platformu (napr. arm-angstrom-linux-gnueabi). Ak chcem skompilovat nieco vacsie, ako hello world, oplati sa mat pre cielovu platformu k dispozicii aspon zakladne kniznice a ich headery. Ak treba kompilovat komplikovanejsie baliky (napr. Xkovu aplikaciu), tak samozrejme treba mat patricne kniznice v toolchaine, rovnako aj ich includes.

Ako donutit toolchain makat? V prvom rade niekde musi byt nainstalovany (kludne aj v home, na toto netreba rootovske prava). Ja mam napriklad toolchain z distribucie Angstrom (jedna vetva OpenEmbedded), takze moj toolchain sa nachadza na krkolomnej adrese /home/ventyl/OE/angstrom-stable/cross/armv5te/bin/. Na tejto ceste konkretne sa nachadzaju binarky GCC preprocesora, prekladaca, assemblera a linkera. Tie su potrebne k tomu, aby sa vobec nieco dalo prelozit.

V adresari /home/ventyl/OE/angstrom-stable/staging/armv5te-angstrom-linux-gnueabi/usr/lib/pkgconfig/ sa nachadzaju skripty pre pkgconfig, co je druha dolezita sucast, ktora sa konfiguruje. Prekladac C-cka a linker sa zrejme nijako zvlast nekonfiguju, evidentne sa dokazu spamatat z cesty k toolchainu.

Postup rozchodenia cross-compilu s automake projektom je asi taky, ze najprv sa musi nastavit prostredie (zakazdym):
export PATH=$PATH:/home/ventyl/OE/angstrom-stable/cross/armv5te/bin/
export PKG_CONFIG_PATH=/home/ventyl/OE/angstrom-stable/cross/armv5te/bin/
tym je zarucena aspon aka-taka sanca, ze configure po spusteni zbehne. Nasledne treba spravit v strome zdrojakov poriadok, ak sa v nom predtym nieco uz kompilovalo. Takze ak uz v danom adresari so zdrojakmi prebehla konfiguracia, tak uplne prvym prikazom je

make distclean

ktory posle do historie vsetky subory, ktore by pri cross-compilovani mohli byt zdravotne zavadne. Nasledne treba spustit configure. Ale nie len tak akokolvek, ale treba mu povedat, ze to chceme prave pre tu platformu. Na to ma configure zopar prepinacov. V prvom rade sa mu urcuje platforma na ktorej buildujeme (cez prepinac --build), cielova platforma (--host) a cielovy stroj (--target). Cielova platforma a cielovy stroj sa lisia iba ak sa kompiluje cross-kompilujuci prekladac, pretoze ten sice vytvara binarky pre inu platformu, ale bezi na rovnakej platforme, na akej je zostavovany, preto budu prepinace host a build rovnake a prepinac target bude iny. V ostatnych pripadoch by mali byt prepinace host a target rovnake.

Ked chceme cross-kompilovat pre ARM5 s vyssie menovanym toolkitom, prikaz by vyzeral asi takto:

./configure --build=i686-linux --host=arm-angstrom-linux-gnueabi --target=arm-angstrom-linux-gnueabi

i686-linux sa moze lisit a napr. na 64bitovej masine to moze byt x86_64-linux, pripadne aj ine.
Parameter host a target maju svoje hodnoty zavisle od toho, ako cross-compile toolchain sa pouzije. Obecny toolchain pre arm sa vola arm-linux, teda parametre host a target by pri jeho pouziti mali hodnoty arm-linux.

Ak configure zbehne bez chyby, nasledne by sa pouzitim make-u malo dat kompilovat. Vysledna binarka by mala byt pre platformu, ktoru sme urcili v parametri target.

Pri preklade sa moze stat, ze vyskoci haluzna chyba stazujuca sa na /usr/include v include paths s tym, ze dany stav je potrebne nahlasit ako bug. Nejedna sa ale o bug GCC-cka, ale o bug makefile-u, pretoze v projekte je natvrdo nastavena include cesta niekam do /usr/include, co ale samozrejme nie je pri cross-compile mozne, lebo by sa potencialne pouzili includes z ineho systemu, nez pre ktory sa preklada.

Bonbonik na zaver: Cross-compile a KDevelop
Cross compile sa da jednoducho naklikat aj v KDevelope, ak sa pouzije sablona automake project. Takze si zalozime novy projekt, ako typ vybereme C, alebo C++ a potom Automake project. Vyplnime vsetky nalezitosti, vyrobime novy target typu Program, vyplnime nazov. Pridame subor a napiseme donho nejake smetie, napr.:

#include <stdio.h>
int main(int argc, char ** argv) {
printf("cross compile test!\n");
return 0;
}

Potom si treba z menu Project otvorit Project options. Vlavo v zalozke Configure options treba hore do boxu configuration vpisat nieco v style cross, napr.: "armv5te-cross".

Do pola configure arguments treba pridat prepinace podobne, ako sa pridali configure-u na prikazovy riadok, cize: "--build=i686-linux --host=arm-angstrom-linux-gnueabi --target=arm-angstrom-linux-gnueabi". A navyse treba v poli environment variables nastavit premennu PATH a PKG_CONFIG_PATH rovnako, ako prikazmi export vyssie v texte. Potom treba kliknut na tlacidlo Add, co by malo pridat novy profil a spytat sa, ci sa ma pre tento profil spustit configure. Odpovieme ze nie.

Nasledne treba v zalozke Make options rovnako vyplnit premennu PATH. Potom mozno projekt ulozit, spustit distclean (ak sme uz nieco kompilovali pre aktualnu platformu), potom automake, configure a nasledne make. KDevelop ma prijemnu vlastnost tu, ze pre kazdu konfiguraciu automake-u uklada vysledne binarky do oddeleneho adresara, takze je mozne paralelne pracovat s viacerymi konfiguraciami bez nutnosti zakazdym zostavovat cely projekt odznova. Vysledna binarka sa da najst v podadresari rovnomennom s nazvom konfiguracie configure-u (dvojite norenie...).