Unix/Linux 编程-Makefile/gcc 构建文件

本文详细介绍如何使用Makefile进行项目的构建管理,包括简单的单文件编译、多文件编译、静态库构建及链接、动态库构建及链接等。通过具体实例展示了Makefile的强大功能。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

使用Makefile来构建文件

参考来这篇博文:http://blog.youkuaiyun.com/haoel/article/details/2886

一个最简单的Makefile 参考UNP中的代码实例

#file path for .h and .a
LIBS= /usr/local/lib/libunp.a
INCLUDE=/usr/local/include/unp/lib

#default compiler
CC=gcc
CFLAGS=-Wall -std=gnu99 -I ${INCLUDE}

#target
TARGET=byteorder
CLEANFILES= *.o *.out


all: ${TARGET}

byteorder: byteorder.o
	${CC} ${CFLAGS} -o $@ byteorder.o ${LIBS}

clean:
	rm -f ${TARGET} ${CLEANFILESl}

TLPI中构建例子的Makefile

编译fileio/copy.c

INCLUDE=../lib
SRC=../lib
CC=gcc
CPPFLAGS = -Wall -std=gnu99
CFLAGS = -I ${INCLUDE}
TARGET=copy
OBJ=copy.o ${SRC}/error_functions.o ${SRC}/get_num.o

${OBJ}:%.o:%.c
	${CC} -c ${CFLAGS} $< -o $@

${TARGET}:${OBJ}
	${CC} ${CPPFLAGS} ${OBJ} -o ${TARGET}
clean:
	rm -rf ${TARGET} ${OBJ}

编译多个文件的例子

编译fileio/copy.c, fileio/seek_io.c

INCLUDE=../lib
SRC=../lib
CC=gcc
CPPFLAGS = -Wall -std=gnu99
CFLAGS = -I ${INCLUDE}
TARGET=copy seek_io
OBJ=copy.o seek_io.o ${SRC}/error_functions.o ${SRC}/get_num.o
 
${OBJ}:%.o:%.c
	${CC} -c ${CFLAGS} $< -o $@

all:${TARGET}

copy:${filter-out seek_io.o,${OBJ}}
	${CC} ${CPPFLAGS} -o $@ $^
seek_io:${filter-out copy.o,${OBJ}}
	${CC} ${CPPFLAGS} -o $@ $^
clean:
	rm -rf ${TARGET} ${OBJ}

文件目录结构如下

使用makefile先将lib中的文件编译成libtlpi.a

然后再编译fileio中的文件并与libtlpi.a进行静态链接

INCLUDE=../lib
SRC=../lib
CC=gcc
AR=ar
CPPFLAGS = -Wall -std=gnu99 -L ${SRC} -ltlpi -lpthread
CFLAGS = -I ${INCLUDE}
TARGET=copy seek_io my_tee t_readv large_file
LIB=${SRC}/libtlpi.a
OBJ=copy.o seek_io.o my_tee.o t_readv.o large_file.o
LIBOBJ=${SRC}/error_functions.o ${SRC}/get_num.o


all:${LIB} ${TARGET}

%.o:%.c
	${CC} -c ${CFLAGS} $< -o $@

${LIB}:${LIBOBJ}
	${AR} -rcs $@ $^

copy:copy.o ${LIB}
	${CC}  $^ ${CPPFLAGS} -o $@
seek_io:seek_io.o 
	${CC}  $^ ${CPPFLAGS} -o $@
my_tee:my_tee.o ${LIB}
	${CC}  $^ ${CPPFLAGS} -o $@
t_readv:t_readv.o ${LIB}
	${CC}  $^ ${CPPFLAGS} -o $@
large_file:large_file.o ${LIB}
	${CC}  $^ ${CPPFLAGS} -o $@
clean:
	rm -rf ${TARGET} ${OBJ} ${LIB} ${LIBOBJ}

编译多个静态库并进行静态链接的例子:

INCLUDE=../lib
INCLUDE1=../users_groups
LIBSRC=../lib
LIBSRC1=../users_groups
CC=gcc
AR=ar
CPPFLAGS = -Wall -std=gnu99 -L ${LIBSRC} -L ${LIBSRC1} -ltlpi -lugid
CFLAGS = -I ${INCLUDE} -I ${INCLUDE1}
TARGET=idshow
OBJ=idwhow.o
LIB=${LIBSRC}/libtlpi.a
LIB1=${LIBSRC1}/libugid.a
LIBOBJ=${LIBSRC}/error_functions.o ${LIBSRC}/get_num.o
LIBOBJ1=${LIBSRC1}/ugid_functions.o 


all:${LIB} ${LIB1} ${TARGET}

%.o:%.c
	${CC} -c ${CFLAGS} $< -o $@

${LIB}:${LIBOBJ}
	${AR} -rcs $@ $^

${LIB1}:${LIBOBJ1}
	${AR} -rcs $@ $^

idshow:idshow.o ${LIB} ${LIB1}
	${CC} idshow.o ${CPPFLAGS} -o $@

clean:
	rm -rf ${TARGET} ${OBJ} ${LIB} ${LIB1} ${LIBOBJ} ${LIBOBJ1}

用gcc构建动态库

gcc -shared -fpic -o libvector.so addvec.c multvec.c

连接动态库

gcc -o prog21 main2.c ./libvector.so

或者

gcc -o prog21 main2.c -L. -lvector

-----------------------------------------

用ar命令构建静态库

gcc -c addvec.c multvec.c
ar rcs libvector.a addvec.o multvec.o

连接静态库

gcc -c main2.c
gcc -static -o prog2c main2.o ./libvector.a

或者

gcc -c main2.c
gcc -static -o prog2c main2.o -L. -lvector


参考链接:https://blog.youkuaiyun.com/lzb19890920/article/details/88432116

------------------------------------------

动态加载shared library

dll.c

/* A Demo to load function symbol from shared library 
* linux>gcc -rdynamic -o prog2r dll.c -ldl
*/

#include <stdio.h>
#include <stdlib.h>
#include <dlfcn.h>

int x[2] = {1, 2};
int y[2] = {3, 4};
int z[2];

int main(int argc, char * argv[])
{
    void *handle;
    void (*addvec)(int *, int *, int *, int);
    char *error;

    /* Dynamically load the shared library containing addvec() */
    handle = dlopen("./libvector.so", RTLD_LAZY);
    if(!handle) {
        fprintf(stderr, "%s\n", dlerror());
        exit(EXIT_FAILURE);
    }

    /* Get a pointer to the addvec() function we just loaded */
    addvec = dlsym(handle, "addvec");
    if((error = dlerror()) != NULL) {
        fprintf(stderr, "%s\n", error);
        exit(EXIT_FAILURE);
    }

    /* Now we can call addvec() just like any other function */
    addvec(x, y, z, 2);
    printf("z = [%d %d]\n", z[0], z[1]);

    /* Unload the shared library */
    if(dlclose(handle) < 0) {
        fprintf(stderr, "%s\n", dlerror());
        exit(EXIT_FAILURE);
    }
    return 0;
}

编译:

gcc -rdynamic -o prog2r dll.c -ldl

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值