多个目录中的 Makefile

标签 makefile

我想构建一个应用程序,并且我有多个模块存储在多个目录中。我决定关注 this想法,即在每个目录中都有一个makefile,然后合并它。但是 - 作为一个初学者程序员 - 我仍然不知道如何做到这一点。首先,这样的“部分”makefile 会是什么样子。它们不能具有 main 函数,因为每个二进制文件只能有一个,尽管当我尝试编译它时 gcc 提示未定义对 main 的引用。其次,我不知道将所有这些模块放在一起会是什么样子。

我会很感激任何帮助,但请尽量保持你的答案简单。 Makefiles 对我来说仍然有点黑魔法。

最佳答案

在使用 makefile 进行任何操作之前,您必须知道如何在没有 makefile 的情况下进行操作。

由于您使用的是 gcc,我将假设您的源代码是 C++。

您还没有告诉我们您的目录结构是什么样的,所以我假设您在两个目录中有三个源文件:primary/main.cc , other/foo.ccother/bar.cc . (我们可以稍后处理像 foo.h 这样的头文件。)而你想要构建 myApp .

第 1 步:手工操作

要在一个命令中执行此操作,您可以使用:

gcc -Wall primary/main.cc other/foo.cc other/bar.cc -o myApp

这将编译三个源文件并将二进制对象链接到可执行文件myApp。 .

第 2 步:分段进行(在您可以使上一步完美运行之前,请勿尝试此操作。)

您可以采取中间步骤,将源文件编译为二进制目标文件,而不是使用一个命令进行构建:
gcc -Wall -c primary/main.cc -o primary/main.o
gcc -Wall -c other/foo.cc -o other/foo.o
gcc -Wall -c other/bar.cc -o other/bar.o

这将产生 alpha/main.o , beta/foo.obeta/bar.o .编译器不会提示 foobar缺少 main()函数,因为目标文件不需要一个。然后将这些对象链接到一个可执行文件中:
gcc -Wall primary/main.o other/foo.o other/bar.o -o myApp

第 3 步:在本地进行(在您可以使上一步完美运行之前,请勿尝试此操作。)

就像上一步一样,但是我们在 primary/ 中操作和 other/ :
cd primary
gcc -Wall -c main.cc -o main.o
cd ../other
gcc -Wall -c foo.cc -o foo.o
gcc -Wall -c bar.cc -o bar.o
cd ..
gcc -Wall primary/main.o other/foo.o other/bar.o -o myApp

第 4 步:使用 Makefile(在您可以使上一步完美运行之前,请勿尝试此操作。)

我们可以让 makefile 执行第 1 步,但这并不是必需的。在 primary 中写入一个 makefile (即 primary/makefile )像这样:
main.o:
    gcc -Wall -c main.cc -o main.o

(从 gcc... 开始的那个空格是一个制表符。)

现在试试这个:
cd primary
make
cd ../other
gcc -Wall -c foo.cc -o foo.o
gcc -Wall -c bar.cc -o bar.o
cd ..
gcc -Wall primary/main.o other/foo.o other/bar.o -o myApp

第 5 步:使用多个 Makefile(在您可以使上一步完美运行之前,请勿尝试此操作。)

写一个 other/makefile :
both: foo.o bar.o

foo.o:
    gcc -Wall -c foo.cc -o foo.o

bar.o:
    gcc -Wall -c bar.cc -o bar.o

和顶层目录中的 makefile,您正在构建 myApp :
myApp:
    gcc -Wall primary/main.o other/foo.o other/bar.o -o myApp

现在试试这个:
cd primary
make
cd ../other
make
cd ..
make

第 6 步:使用一个调用其他人的 Makefile(在您可以使上一步完美运行之前,请勿尝试此操作。)

编辑顶部生成文件:
myApp:
    cd primary; make
    cd other; make
    gcc -Wall primary/main.o other/foo.o other/bar.o -o myApp

现在尝试:
make

如果所有这些都有效,那么您所拥有的是一个粗糙但有效的 makefile 系统。当您准备好卸下辅助轮时,可以进行许多改进。

编辑:

如果子目录中有许多源文件(例如 other/ )并且您不想手动维护顶级 makefile 中的列表,有几种方法可以处理它。这是一:
OTHER_SOURCES := $(wildcard other/*.cc)

OTHER_OBJECTS := $(OTHER_SOURCES:.cc=.o)

myApp:
    cd primary; make
    cd other; make
    gcc -Wall primary/main.o $(OTHER_OBJECTS) -o myApp

但是你应该让这些 makefile 正常工作并理解它们,然后再尝试进一步简化。

关于多个目录中的 Makefile,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12944291/

相关文章:

makefile - 如何使 'make' 附加额外的标准 FLAGS

java - 具有 Jar 和包依赖项的 Makefile

linux - 进行安装,但不安装到默认目录?

c++ - gtest - 对 `testing::InitGoogleTest(int*, char**)' 的 undefined reference

c++ - 通用生成文件

docker - make [1]:[install-domserver-l]错误1(忽略)

makefile - 如何使 Makefile 更短?

c - 将 m32 标志添加到 Makefile 时 select() 失败

makefile - 如何记录makefile?

c - Eclipse CDT 自定义生成文件