Você está na página 1de 6

Makefile

O makefile um arquivo para configurao de compilao, utilizado pelo programa Make, cuja idia simplificar e agilizar a compilao de programas. Para utilizar o makefile basta criar o arquivo com o nome makefile no diretrio onde se encontram os arquivos fonte para compilao e executar o programa make no mesmo diretrio. A sintaxe mais simples de um makefile : Regra: dependncias comando1 comando2 ... comandoN A regra ou alvo um rtulo, seguido de dependncias. Antes de executar os comandos de uma regra, o programa make se certifica de que todas as dependncias foram satisfeitas. Uma dependncia pode ser outra regra ou ento algum arquivo necessrio para execuo dos comandos. Por exemplo, a regra de compilao de um executvel pode ter como dependncia as regras que compilam as bibliotecas necessrias e tambm os arquivos fonte necessrios. Aps as dependncias, temos a lista de comandos. Os comandos usados aqui so referentes ao terminal Linux. Note que os comandos so identados com TABs e no com espaos! Cada comando pode ser qualquer chamada de um programa de linha de comando, por exemplo, rm, cd, mkdir ou chamada ao compilador gcc. A regra pode ter qualquer nome. Por exemplo, o nome da regra que compila o arquivo programa.c no executvel programa pode ser programa. ideal usar o nome do arquivo quando existe um arquivo de sada dos comandos da regra, pois atravs do nome da regra que o makefile sabe se precisa recompilar o arquivo. Um exemplo: programa: programa.cpp programa.h gcc -o programa programa.c

Neste makefile temos apenas uma regra que gera o executavel programa. O programa make, antes de executar os comandos desta regra, verifica se os arquivos programa.c e programa.h existem. S ento so executados os comandos, no caso a compilao. No caso da dependncia ser outra regra, a regra da dependncia avaliada antes da regra dependente. Por exemplo: executa: programa ./programa programa: programa.c programa.h gcc -o programa programa.c

A primeira regra a ser avaliada sempre a primeira do arquivo, no nosso caso a regra executa. Porm, durante a avaliao da regra executa, a dependncia programa encontrada.

Como existe uma regra com este mesmo nome no arquivo, o make sabe que se trata de uma outra regra e no de um arquivo. Antes de executar os comandos da regra executa, o make avalia a regra programa, verifica as dependncias conforme explicado acima e executa os comandos da regra programa Agora a regra programa est satisfeita e o make pode executar os comandos da regra executa, que no nosso caso executa o programa compilado. Repare que neste caso, o programa s executado se a compilao ocorrer com sucesso. Caso haja um erro de compilao, a avaliao para e o comando da regra executa no so executados. Outro caso interessante quando se chama o make duas vezes consecutivas. Se na primeira chamada compilao ocorreu sem problemas, na segunda chamada o programa no compilado, ou seja, o make percebe que no necessrio compilar o programa e pula a regra programa, indo direto para a regra executa. Um exemplo um pouco mais complexo: all: msgola programa @echo Rodando o programa programa.exe msgola: @echo Bem vindo ao makefile. Vou tentar executar o programa. programa: programa.o gcc -o programa programa.o programa.o: programa.c programa.h gcc -g - Wall -c programa.c

O make inicia pela primeira regra no arquivo, no nosso caso a regra all. Porm a regra all tem duas dependncias msgola e programa. Ento o make avalia a primeira dependncia, a regra msgola. Como esta regra no tem nenhuma dependncia, executa os comandos da regra e vai para a prxima dependncia pendente de all, ou seja, programa. Porm a regra programa depende da regra programa.o e programa.o depende dos arquivos programa.c e programa.h. Se os arquivos estiverem no mesmo diretrio, as dependncias da regra programa.o foram satisfeitas e podemos executar o comando da regra programa.o. Depois de executar o comando da regra programa.o, voltamos para a regra programa e a executamos. S agora temos a dependncia programa da regra all satisfeita e podemos executar os comandos dela. O comando echo repete todos os seus parmetros (o que voc escreve depois dele) na tela, a arroba antes dele apenas indica que voc no quer que o comando seja repetido na tela. No temos que executar primeiro sempre a primeira regra que aparece. Podemos dizer para o make executar uma regra qualquer. Para isso passamos como parmetro na linha de comando o nome da regra que queremos executar. Por exemplo: executa: programa ./programa programa: programa.c programa.h

gcc -o programa programa.c clean: /bin/rm -f programa programa.o Se executarmos na linha de comando: make clean O make vai executar apenas a regra clean, que elimina os arquivos compilados. Foi usado o caminho completo do comando rm, ao invs de apenas rm, pois muitos usurios tem esse comando como alias para outro comando. Ento, sempre que se quiser remover arquivos usa-se /bin/rm.

Usando variaveis
E se quisermos mudar as flags de compilao e usar a otimizao -O2 no lugar de adicionar informao de depurao com -g? vivel mudar manualmente quando se tem poucos arquivos, mas com muitos prefervel usar variveis. Uma varivel X armazena uma string e declarada no inicio do makefile e qualquer comando que queira usar o contedo de X deve fazer $(X) na parte do cdigo. Isto especialmente til quando se tenta compilar o cdigo em diferentes compiladores, ou mesmo em diferentes plataformas, onde um mero comando rm pode estar em um diretrio diferente ou mesmo substitudo por outro comando, em cada plataforma. Analise este makefile, que contm os arquivos main.c, arq1.c, arq2.c, arq1.h e arq2.h: # regra default, para compilar tudo all: prog # regra para linkar o programa prog: main.o arq1.o arq2.o gcc -o prog arq1.o arq2.o # regra para o arquivo "main.o". main.o: main.c arq1.h arq2.h gcc -c main.c # regra para o arquivo "arq1.o". arq1.o: arq1.c arq1.h gcc -c arq1.c # regra para o arquivo "arq2.o". arq2.o: arq2.c arq2.h gcc -c arq2.c # regra para limpar arquivos que podem ser recompilados clean: /bin/rm -f programa programa.o

O seguinte Makefile faz o mesmo que o anterior, mas com a incluso do uso de variveis no mesmo:

# usa o "gcc" para compilar os fontes CC = gcc # o linker tambm o "gcc". em outros compiladores pode acontecer de ser algo diferente LD = gcc # As flags do compilador vo aqui CFLAGS = -g -Wall # As flags do linker vo aqui. Atualmente no h nenhum, mas se # mudarmos a compilao para otimizao de cdigo, ns vamos com #certeza querer usar a flag "-s" para retirar informaes de depurao #e de smbolos do cdigo final LDFLAGS = # use este comando para apagar arquivos RM = /bin/rm -f # lista dos objetos gerados OBJS = main.o arq1.o arq2.o # nome do programa executvel PROG = prog # regra default, para compilar tudo all: $(PROG) # regra para linkar o programa $(PROG): $(OBJS) $(LD) $(LDFLAGS) $(OBJS) -o $(PROG) # regra para o arquivo "main.o". main.o: main.c arq1.h arq2.h $(CC) $(CFLAGS) -c main.c # regra para o arquivo "arq1.o". arq1.o: arq1.c arq1.h $(CC) $(CFLAGS) -c arq1.c # regra para o arquivo "arq2.o". arq2.o: arq2.c arq2.h $(CC) $(CFLAGS) -c arq2.c # regra para limpar arquivos que podem ser recompilados clean: $(RM) $(PROG) $(OBJS) Voc ainda pode alterar o valor da variavel quando invocando o Makefile. Por exemplo: make CFLAGS = -O2 Essa chamada de make modifica a flag utilizada.

Regras para tipos de arquivo


Vamos ver como mudar regras redundantes, ou seja, regras que recebem como entrada o mesmo tipo de arquivo, e criam tambm o mesmo tipo de arquivo. Veja o exemplo abaixo: # retiramos todas as definies de variveis, pois so exatamente como #no makefile anterior . . # regra de linking continua o mesmo de antes $(PROG): $(OBJS) $(LD) $(LDFLAGS) $(OBJS) -o $(PROG) # agora comeam as meta-regras para compilar qualquer arquivo "C" %.o: %.c $(CC) $(CFLAGS) -c $<

O caractere % indica que todos que contenham % na regra tem a mesma string naquela parte. Assim, nossa regra significa: "Um arquivo com sufixo .o depende de um arquivo com mesmo nome, mas sulfixo .c". Dessa forma, todo arquivo .c encontrado ir ser dependncia de uma regra com mesmo nome, porm .o. O comando abaixo, ento, gera um arquivo objeto do .c. A string "$<" faz referncia lista de dependncias, que foi verificada pela regra (em nosso caso, o nome completo do fonte). Ento, como temos trs arquivos .c sero executados na verdade os comandos: gcc -g -Wall -c gcc -g -Wall -c gcc -g -Wall -c arq1.c arq2.c main.c

Alvos frequentemente utilizados pela comunidade


Existem alguns nomes de alvo que so frequentemente utilizados por todos os programadores. Abaixo segue alguns deles:

all - utilizado como o primeiro nome de alvo do arquivo e, portanto, o nome de alvo padro. A utilizao deste alvo define o projeto inteiro. install -utilizado para instalar um projeto. clean - utilizado para remoo dos arquivo objeto e arquivos temporrios criados no processo de instalao. clobber - utilizado para remover os alvos que so construdos (normalmente executveis e bibliotecas). Voc remove estes alvos para reconstruir o projeto do zero.

distclean - usado para remover tudo, exceto os arquivos originais que foram distribudos pela internet. Este alvo vai alm do clobber, pois remove tambm os arquivos de configurao.

Você também pode gostar