Makefile

Linux.fista
Versio hetkellä 4. lokakuuta 2007 kello 20.52 – tehnyt Heikki (keskustelu | muokkaukset) (→‎Esimerkki: muuttuja)
Siirry navigaatioon Siirry hakuun

Makefile on tiedosto, jonka perusteella make kääntää ohjelman lähdekoodin. Makefilet ovat käteviä etenkin ohjelmoijille, jotka voivat niiden avulla automatisoida ohjelman käännösprosessin.

Tiedoston rakenne

Makefilen rakenne on tarkasti määrätty seuraavanlaiseksi:

kohdetiedosto: lähdetiedosto1 lähdetiedosto2 lähdetiedosto3
  <tabulaattori>kääntämiskomennot

Esimerkiksi hello.c-nimiselle C-kieliselle ohjelmalle voitaisiin luoda seuraavanlainen Makefile:

hello: hello.c
    gcc hello.c -o hello

Jonka jälkeen samassa hakemistossa ajettu komento make kääntäisi ohjelman.

Useampia kohteita

Samassa Makefilessä voi olla useampia käännöskohteita, joita voidaan kutsua joko pelkästään tai niitä voidaan hyödyntää toisesta kohteesta käsin. Esimerkiksi jos edellä käyttämäämme hello-ohjelmaan lisätään toinen tiedosto world.c, voitaisiin Makefilestä tehdä seuraavanlainen:

# Linkitys
hello: hello.o world.o
     gcc hello.o world.o -o hello
# Pelkkä käännös, ei linkitystä
hello.o: hello.c
     gcc -c hello.c -o hello.o 
world.o: world.c
     gcc -c world.c -o world.o

Jolloin koko ohjelman kääntäminen sujuisi komennolla make. Jos makelle ei kerrota erikseen, mikä kohde halutaan käsitellä, make käsittelee ensimmäisen lohkon. Toisaalta pelkän world.c-tiedoston kääntäminen onnistuisi komennolla

make world.o

Tätä ominaisuutta hyödynnetään usein Makefileissä olevilla clean- ja install-kohteilla. Esimerkiksi Makefilen lopussa voisi olla seuraavanlainen clean-kohde:

clean:
      rm *.o hello

Joka poistaisi käännetyt objektitiedostot (hello.o ja world.o) ja käännetyn ohjelman (hello). Tätä kutsuttaisiin komentoriviltä komennolla

make clean

Muuttujat

Make tukee erilaisten muuttujien käyttöä Makefileissä, jolloin saadaan tiedostosta helpommin ylläpidettävä ja siirrettävä kun komentoja ja niiden parametreja ei tarvitse "kovakoodata".

Muuttujat määritellään yksinkertaisesti syntaksilla

muuttuja = arvo

Esimerkiksi C-kääntäjä on yleensä CC-nimisessä muuttujassa:

CC = gcc

Muuttujiin voi viitata koodissa syntaksilla $(muuttuja), esimerkiksi hello.c-tiedoston kääntävä osa edellisestä Makefilestä muuttuisi seuraavanlaiseksi

CC = gcc
hello.o: hello.c
     $(CC) -c hello.c -o hello.o

Nyt kääntäjän vaihtaminen toiseksi onnistuu pelkkää muuttujaa muuttamalla, mistä on hyötyä Makefilen kasvaessa suuremmaksi. Vastaavalla tavalla muuttujina käytetään usein esimerkiksi käännösoptioita, jolloin kaikkiin tiedostoihin saadaan haluttaessa joko debug-käännösoptiot (-g, -O0) tai julkaisua varten tehokkaat optimoinnit (-O3).

Esimerkki

Esimerkki Makefilestä, jota käytetään kääntämään kahdesta C++-kielisestä lähdekooditiedostosta (src/main.cpp ja src/funktiot.cpp).

#Objektitiedostot
PROJEKTI = src/main.o src/funktiot.o

#Käännösasetukset
LDFLAGS = -lm
CXXFLAGS = -g

#Oletuksena suoritetaan osio "softa"
all: softa

#Tiedot, mistä lähdekooditiedostoista objektitiedostot käännetään
src/main.o: src/main.cpp
src/funktiot.o: src/funktiot.cpp

#Kääntö
softa:
    g++ $(PROJEKTI) $(CXXFLAGS) $(LDFLAGS) -o ohjelma

#Clean, joka poistaa tarpeettomat objektitiedostot
clean:
    rm -f $(PROJEKTI)

Nyt projektin hakemistossa voidaan ajaa komento make, jolloin make kääntää projektin:

$make
g++ -g   -c -o src/main.o src/main.cpp
g++ -g   -c -o src/funktiot.o src/funktiot.cpp
g++ src/main.o src/funktiot.o -g  -o ohjelma

Huomaa, että jos nyt muokkaamme tiedostoa src/funktiot.cpp ja ajamme maken uudelleen, tiedostoa src/main.cpp ei käännetä uudestaan:

$touch src/main.cpp
$make
g++ -g   -c -o src/main.o src/main.cpp
g++ src/main.o src/funktiot.o -g  -o ohjelma

Katso myös

Aiheesta muualla