【问题标题】:Makefile header directory errorsMakefile 头目录错误
【发布时间】:2015-09-06 02:19:48
【问题描述】:

我正试图找出我们在 make 中不断遇到的错误。我有几个源文件位于assign1 目录以及includes 目录(包含bb.h)。我要做的是在创建gq.o 文件时包含bb.h 头文件。由于此错误,除gq.o 之外的所有其他目标文件都可以正常编译:

z1755294@hopper:~/assign1/assign1$ make
g++ -c fr.cc
g++ -c vw.cc
g++ -c ac.cc
g++ -c pg.cc
g++ -c gq.cc -I./includes
g++ -o output fr.o gq.o vw.o ac.o pg.o
gq.o: In function `main':
gq.cc:(.text+0x0): multiple definition of `main'
fr.o:fr.cc:(.text+0x0): first defined here
vw.o: In function `main':
vw.cc:(.text+0x0): multiple definition of `main'
fr.o:fr.cc:(.text+0x0): first defined here
collect2: error: ld returned 1 exit status
Makefile:12: recipe for target 'output' failed
make: *** [output] Error 1

这是我的 Makefile:

output: fr.o vw.o ac.o pg.o gq.o
        g++ -o fr.o gq.o vw.o ac.o pg.o output

fr.o: fr.cc pg.h
        g++ -c fr.cc

vw.o: vw.cc ac.h
        g++ -c vw.cc

ac.o: ac.cc ac.h pg.h
        g++ -c ac.cc

pg.o: pg.cc pg.h
        g++ -c pg.cc

gq.o: gq.cc ac.h includes/bb.h
        g++ -c gq.cc -I./includes/bb.h

clean:
        -rm *.o

fr.cc, gq.cc and vw.cc all have main functions inside each of them.  
ac.cc and fr.cc both have fl(); function they have in common.
gq.cc and vw.cc both have x2(); function they have in common.

我无权编辑以下任何文件。目标是创建一个 makefile,这样如果 bb.h 文件被某人更改,那么 makefile 仍然可以工作。

这是每个文件的文件结构:

ac.cc

#include "ac.h"
#include "pg.h"
#include <iostream>
using std::cout;
using std::endl;

void  y7(void)
{
  cout << "y7()" << endl;
}

void  x2(void)
{
  cout << "x2()" << endl;
  f1();
}

ac.h

void y7(void);

void x2(void);

fr.cc

#include <iostream>
using std::cout;
using std::endl;

#include "pg.h"

int main()
{
  cout << "program fr" << endl;

  f1();

  return 0;

}

gq.cc

#include <iostream>
using std::cout;
using std::endl;

#include "ac.h"
#include "bb.h"

int main()
{
  cout << "program gq" << endl;

  x2();

  cout << "CONST111: " << CONST111 << endl;
  cout << "CONST222: " << CONST222 << endl;

  return 0;

}

pg.cc

#include "pg.h"
#include <iostream>
using std::cout;
using std::endl;

void  f1(void)
{
  cout << "f1()" << endl;
}

void  g3(void)
{
  cout << "g3()" << endl;
}

pg.h

void f1(void);

void g3(void);

vw.cc

#include <iostream>
using std::cout;
using std::endl;

#include "ac.h"

int main()
{
  cout << "program vw" << endl;

  x2();

  return 0;

}

包括/bb.h

define CONST111   42
#define CONST222   84

【问题讨论】:

  • 这是错误的:-I./includes/bb.h,它应该只指向 目录,而不是文件:-I./includes。当然bb.h 必须存在于该目录中。
  • 好的,我用你的建议解决了这个问题,现在我得到了:g++ -o fr.o gq.o vw.o ac.o pg.o output g++: error: output: No such file或目录 Makefile:12: 目标“输出”的配方失败 make: *** [输出] 错误 1
  • 更改: g++ -o fr.o gq.o vw.o ac.o pg.o output 到: g++ -o output fr.o gq.o vw.o ac.o pg.o

标签: c++ unix makefile


【解决方案1】:

改变

gq.o: gq.cc ac.h bb.h
        g++  -c gq.cc -I./includes/bb.h 

gq.o: gq.cc ac.h
         g++ -c gq.cc -I./includes 

gq.o: gq.cc ac.h includes/bb.h
         g++ -c gq.cc -I./includes 

构建失败的原因是 bb.h 不在同一个目录中。您将bb.h 列为要求,并且由于它不存在,因此尝试生成它但找不到合适的规则。您需要不将 bb.h 列为要求或指定文件及其路径,以便 make 看到它存在。您还需要只使用-I./includes 指定g++ 将在其中查找bb.h 的搜索目录。

您还需要更改此设置:

output: fr.o vw.o ac.o pg.o gq.o
    g++ -o fr.o gq.o vw.o ac.o pg.o output

这有很多问题。首先,您试图将具有冲突符号的对象链接起来,并且您使用 -o 标志是错误的。根据 cmets 和您的编辑,我认为您想要的是:

output: fr.o vw.o ac.o pg.o gq.o
        g++ -o fr fr.o pg.o
        g++ -o gq gq.o ac.o pq.o
        g++ -o vw vw.o ac.o pg.o

这将生成三个二进制文件,frgqvw,以带有 main() 符号的三个文件命名。每个只列出解析外部符号所需的对象。

【讨论】:

  • 我确实改变了它,现在又出现另一个错误:g++ -c fr.cc g++ -c vw.cc g++ -c ac.cc g++ -c pg.cc g++ -I./includes -c gq .cc g++ fr.o gq.o vw.o ac.o pg.o -o output gq.o: In function main': gq.cc:(.text+0x0): multiple definition of main' fr.o:fr.cc:(.text+0x0): 首先定义在这里vw.o:在函数main': vw.cc:(.text+0x0): multiple definition of main' fr.o:fr.cc:(.text+0x0) 中:首先在此处定义 collect2:错误:ld 返回 1 退出状态 Makefile:12:目标“输出”的配方失败: *** [输出] 错误 1
  • 我发布了带有更新的问题,你能帮我解决这个问题吗?
  • 非常感谢,它编译得很好。只是一个简单的问题,如果任何源文件发生更改,make 会再次工作吗?此外,当它编译时,当我键入 make clean 时,文件 fr、gq 和 vw 仍然会说。这不应该被清除吗?如果没有,如何删除这些文件?
  • 由于您建议的输出部分中的那些文件是可执行文件,我如何创建一个规则来构建所有这些文件?
  • 哦,我现在明白了,名称 output 或 all 只是用于生成可执行文件的命令,但实际上并没有创建名为 all 或 output 的名称(在我们的例子中)。现在我明白了
【解决方案2】:

我可以在这个Makefile 中看到至少两个错误,但如果不知道文件布局就无法判断:

这是我的修复:

output: fr.o vw.o ac.o pg.o gq.o
        g++ -o output fr.o gq.o vw.o ac.o pg.o

fr.o: fr.cc pg.h
            g++ -c fr.cc

vw.o: vw.cc ac.h
            g++ -c vw.cc

ac.o: ac.cc ac.h pg.h
            g++ -c ac.cc

pg.o: pg.cc pg.h
            g++ -c pg.cc

gq.o: gq.cc ac.h includes/bb.h # need to give path to bb.h
            g++ -c gq.cc -I./includes

clean:
            -rm *.o

如果您仍然有问题将您的文件布局发布到问题中。您可以使用这个:

find .

在您的项目文件夹中。

【讨论】:

  • 我添加了 find 。以上信息,如果您能帮我解决这个问题,我将不胜感激。
  • @user3325133 您应该将文件结构添加到原始问题中。我已经修改了我的答案,以便它使用您发布的文件结构构建。我错过了将完整(相对)路径放到bb.h
  • 我已经为每个文件添加了文件结构,你能帮我获取makefile来编译吗?
  • @user3325133 Makefile 应该做什么?该文件列表中有 3 个程序,而您的 Makefile 仅尝试构建一个。
  • 目标是创建一个makefile,这样如果对任何源代码文件进行更改,可以通过在命令行键入make来重建项目。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-06-29
  • 1970-01-01
相关资源
最近更新 更多