如何编写混合 C 和 C++ 的 makefile

Posted

技术标签:

【中文标题】如何编写混合 C 和 C++ 的 makefile【英文标题】:how to write makefile mixing C and C++ 【发布时间】:2011-12-28 09:08:35 【问题描述】:

在这个 Makefile 中,我不知道如何在混合 C 和 C++ 的同一个 Makefile 中编译出 c 对象。如果我首先编译 C 对象然后运行这个 Makefile,它就可以工作。任何人都可以帮我解决它吗?提前致谢!

CXX = g++
CXXFLAGS = -Wall -D__STDC_LIMIT_MACROS


SERVER_SRC = \
    main.cpp

SERVER_SRC_OBJS = $SERVER_SRC:.cpp=.o


REDIS_SRC = \
    $(HIREDIS_FOLDER)/net.c \
    $(HIREDIS_FOLDER)/hiredis.c \
    $(HIREDIS_FOLDER)/sds.c \
    $(HIREDIS_FOLDER)/async.c

REDIS_SRC_OBJS = $REDIS_SRC:.c=.o


.SUFFIXES:
.SUFFIXES: .o .cpp
.cpp.o:
    $(CXX) $(CXXFLAGS) -I$(HIREDIS_FOLDER) \
    -c $< -o $*.o


all: server

net.o: net.c fmacros.h net.h hiredis.h
async.o: async.c async.h hiredis.h sds.h dict.c dict.h
hiredis.o: hiredis.c fmacros.h hiredis.h net.h sds.h
sds.o: sds.c sds.h


server: $(SERVER_SRC_OBJS) $(REDIS_SRC_OBJS)
    mkdir -p bin
    $(CXX) $(CXXFLAGS) -o bin/redis_main \
    -I$(HIREDIS_FOLDER) \
    $(REDIS_SRC_OBJS) \
    $(SERVER_SRC_OBJS) \
    -lpthread \
    -lrt \
    -Wl,-rpath,./


.PHONY: clean
clean:
    $(RM) -r bin/redis_main
    $(RM) ./*.gc??
    $(RM) $(SERVER_SRC_OBJS)
    $(RM) $(REDIS_SRC_OBJS)

【问题讨论】:

为什么不像为 C++ 文件一样为 C 源文件添加变量和规则? 您的错误是什么? “不工作”的症状是什么? 【参考方案1】:

G++ 可以并且将编译 .c 和 .cpp 源文件都很好。

真正需要做的是为“服务器”目标添加依赖项。例如:

OBJ = net.o hiredis.o sds.o async.o

...

all: server

server: $(OBJ)

this Howto 中有一些非常好的提示。

【讨论】:

非常感谢!我使用 CMake 来避免这个问题!【参考方案2】:

您可以先编译 C 文件,然后直接编译 CPP 文件。这可能有效(至少在我的一个项目中有效):

CXX = g++
CC = gcc
CFLAGS = -Wall -c
CXXFLAGS = -Wall -D__STDC_LIMIT_MACROS

OUTPUTDIR = ./bin/
MKDIR = mkdir -p $(OUTPUTDIR)
OBJECTC = redis.o

CSOURCES = \
     $(HIREDIS_FOLDER)/net.c \
     $(HIREDIS_FOLDER)/hiredis.c \
     $(HIREDIS_FOLDER)/sds.c \
     $(HIREDIS_FOLDER)/async.c

CXXSOURCES = \
    main.cpp 

all: server

server: 
    $(MKDIR)
    $(CC) $(CSOURCES) $(CFLAGS) -o $(OUTPUTDIR)$(OBJECTC)
    $(CXX) $(OUTPUTDIR)$(OBJECTC) $(CXXSOURCES) -o $(OUTPUTDIR)server

.PHONY: clean
clean:
    $(RM) -rf $(OUTPUTDIR)
    $(RM) ./*.gc??
    $(RM) ./*.o

如果您看到更合适的方法,请随时更改它:)

【讨论】:

小记——忘记使用 CXXFLAGS。 这也会重新编译每个构建的所有内容。因为没有指定依赖关系。

以上是关于如何编写混合 C 和 C++ 的 makefile的主要内容,如果未能解决你的问题,请参考以下文章

调试经验C++和C的混合编程以及库调用

如何在 c c++ 混合生成文件中为 c 对象添加附加规则?

如何使用子目录中的源代码为 C 和 C++ 创建 makefile

如何正确混合 C++ 和 C

Makefile的编写

如何混合 C++ Qt 对象和 Qt Jambi 对象