读书之--跟我一起写Makefile

偶尔善良 提交于 2019-11-29 16:31:48

前言

以前在Windows下学习的时候,我一直使用Eclipse写C语言程序,比较标准C,GTK+.后来忽有一天学习Linux的时候,看到软件安装那里说了make这个工具,一时之间大是喜欢.因为我本人特别喜欢命令行的方式,于是我把系统换成了Ubuntu,安装了gcc,g++,gdb,make等一系列工具,下载了网上流传十分之广的<跟我一起写Makefile>.

然后我现在写程序,学校的作业我就是在Windows下用eclipse写代码,用UE写makefile,在CMD中make编译

如果是我自己学习的话,那绝对是Linux下写,那编译速度,那流畅,那感觉,,


我以前的makefile:

下面是一个很小的程序,就是在控制台输入两个整数,然后输出它们的和

test.c//入口

#include<stdio.h>
#include"sum.h"
int main( void ){
    int a = 0;
    int b = 0;
    puts("输入两个整数:");
    scanf("%d %d",&a,&b);
    printf("%d + %d = %d\n",a,b,sum(a,b));
    return 0;
}


sum.h//函数声明

#ifndef _SUM_H_
#define _SUM_H_

int sum( int a , int b );

#endif//_SUM_H_


sum.c//函数实现

#include"sum.h"

int sum( int a , int b ){
    return a + b;
}


makefile

OBJS=test.o sum.o

test:${OBJS}
    gcc -o test ${OBJS}
test.o:test.c sum.h
    gcc -c -Wall test.c
sum.o:sum.c sum.h
    gcc -c -Wall sum.c

.PHONY:clean
clean:
    -rm test ${OBJS}


于是我的运行结果是:


隐晦规则:

不过再我看了<跟我一起写makefile> Makefile介绍中的隐晦规则后,我的makefile文件成了:

OBJS=test.o sum.o 
test:${OBJS}
test.o:test.c sum.h
sum.o:sum.c sum.h 
.PHONY:clean
clean:     
    -rm test ${OBJS}

于是,我的编译效果是:


make 变量:

在执行make时,不是我希望的gcc -c -Wall,而是cc -c,这显示不是我想要的.于是我再查资料.终于在百度百科上查到了资料,于是makefile成了:

CC = gcc
CCFLAGS = -c -Wall
OBJS=test.o sum.o 
test:${OBJS}
test.o:test.c sum.h 
sum.o:sum.c sum.h 
.PHONY:clean
clean:     
    -rm test ${OBJS}

运行效果:



其中cc命令是UNIX上的C编译器,在Linux中cc和gcc就是一个东西:

laolang@laolang-Lenovo-G470:~/code/makefile/genwo/one/five$ which cc
/usr/bin/cc
laolang@laolang-Lenovo-G470:~/code/makefile/genwo/one/five$ cd /usr/bin
laolang@laolang-Lenovo-G470:/usr/bin$ ls -l cc
lrwxrwxrwx 1 root root 20 10月 14 03:48 cc -> /etc/alternatives/cc
laolang@laolang-Lenovo-G470:/usr/bin$ cd /etc/alternatives/
laolang@laolang-Lenovo-G470:/etc/alternatives$ ls -l cc
lrwxrwxrwx 1 root root 12 10月 14 03:48 cc -> /usr/bin/gcc
laolang@laolang-Lenovo-G470:/etc/alternatives$


伪目标:

在网上看到过可以使用 make 实现全部重新编译,看了伪目标,我的makefile就成了这样:

CC=gcc
CCFLAGS=-c -Wall
OBJS=test.o sum.o

test:${OBJS}
test.o:test.c sum.h
sum.o:sum.c sum.h

.PHONY:clean-all clean-objs clean-app rebuild
clean-all:clean-objs clean-app
clean-objs:
    -rm ${OBJS}
clean-app:
    -rm test
rebuild:  clean-all
    make

不过运行效果好像不太理想

laolang@laolang-Lenovo-G470:~/code/makefile/genwo/one/five$ make rebuild
rm test.o sum.o
rm test
make
make[1]: 正在进入目录 `/home/laolang/code/makefile/genwo/one/five'
gcc    -c -o test.o test.c
gcc    -c -o sum.o sum.c
gcc   test.o sum.o   -o test
make[1]:正在离开目录 `/home/laolang/code/makefile/genwo/one/five'
laolang@laolang-Lenovo-G470:~/code/makefile/genwo/one/five$


使用变量替换

在写主目标的依赖时,要写很多的.o,而且在写主程序的命令时,要写宏替换,于是在看了<Linux C 一站式学习中的>makefile相关部分后,我的Makefile 成了:

# 程序的名字
PROGRAM=test

# 程序源代码集
C_SOURCES=test.c sum.c

# .o文件
# ${C_SOURCES:.c=.o} 是一个变量替换语法
# 把所有的.c替换为.o
C_OBJS=${C_SOURCES:.c=.o}

# CC 指定 gcc 为编译器
# CCFLAGS 指定编译选项
CC=gcc
CCFLAGS=-c -Wall

# 默认目标
all:${PROGRAM}

# 创建主程序
${PROGRAM}:${C_OBJS}
    ${CC} -o $@ ${C_OBJS}

# 生成各.o文件
test.o:test.c sum.h
sum.o:sum.c sum.h

.PHNOY:clean run rebuild
# 清除文件
clean:
    -rm ${C_OBJS} ${PROGRAM}
# 运行程序
run:
    @echo "运行程序\n"
    ./${PROGRAM}

# 重新构建
rebuild:
    @echo "重新构建\n"
    make clean && make


总结:

makefile的基本语法:

目标:依赖

    命令

现阶段基本上上也就是使用自动推导依赖,从而不用写那些gcc -c -Wall test.c 或者 gcc test.o -o test,再有就是使用伪目标实现重新编译和清除目标文件和可可执行文件

然后还是有问题

1. 使用@echo进行输出时,总是会出问题,我又不想写太多的gcc命令

2.自动化变量和多个makefile的使用

3.条件判断



标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!