主要makefile中的未定义参考

Undefined reference in main Makefile

本文关键字:未定义 参考 makefile 主要      更新时间:2023-10-16

我在Linux中做了一个示例项目,但是在运行MaineFile

时我会遇到错误

项目信息:

project/database文件夹具有文件database.h,database.cpp,bulid-database,makefile

database.h

/*data base file*/
#include<iostream>
using namespace std;
class mydatabase
{
public:
    mydatabase(int a , int b);
    int sum(){return m_a +m_b;}
    int diff(){return m_a -m_b;}
    int mul(){return m_a *m_b;}
    float div(){return m_a /m_b;}
    int reminder(){return m_a %m_b;}
private:
    int m_a , m_b;
};

database.cpp

#include "database.h"
mydatabase::mydatabase(int a ,int b):m_a(a) , m_b(b)
{
}

Bulid-Database

make
if [ -f libdatabase.a ];
then
   echo "Database-Library Build Success"
   cp libdatabase.a ../LIBs/
else
    echo "databse-Library Build Failure"
fi

makefile

HEADERFILES = $(wildcard *.h)
CPPFILES = $(wildcard *.cpp)
OBJFILES = $(patsubst %.cpp,%.o ,$(wildcard *.cpp))
$(OBJFILES): %.o : %.cpp $(HEADERFILES)
    g++ -c -o $@ $<
    ar ruv libdatabase.a $@
    ranlib libdatabase.a

project/main文件夹有main.cpp,makefile

main.cpp

#include "database.h"
#include <iostream>
int main()
{
    mydatabase *obj = new mydatabase(10 ,5);
    std::cout<<"sum is"<<obj->sum()<<endl;
    std::cout<<"diff is"<<obj->diff()<<endl;
    std::cout<<"mul is"<<obj->mul()<<endl;
    std::cout<<"div is"<<obj->div()<<endl;
    std::cout<<"reminder is"<<obj->reminder()<<endl;
    getchar();
    return 0;
}

makefile

CC        = g++
INCPATH  = -I. 
       -I.. 
       -I../database
LIBPATH  = -L../LIBs
LDFLAGS   = ${LIBPATH}/libdatabase.a
CFLAGS    = ${INCPATH} 
testdate:main.o
    $(CC) $(CFLAGS) -o testdate main.o $(LDFLAGS)
main.o:main.cpp
    $(CC) $(CFLAGS) -c -o main.o main.cpp

问题:数据库使文件工作正常,但是Makefile我有一些问题,例如

错误: main.o:在函数main': main.cpp:(.text+0x92): undefined reference to myDatabase :: myDatabase(int,int)'收集2:LD返回1退出状态

此行是错误的:

$(CC) $(CFLAGS) -o testdate $(LDFLAGS) main.o

应该在行上的对象main.o之后指定库。这是由于链接器处理对象的方式。查看此示例:

gcc -o test someobject.o library.a

链接器将:

  1. 查找someobject.o的所有未定义引用并存储它们
  2. 然后打开library.a并通过library.a
  3. 解决未定义的参考
  4. 然后关闭library.a

如果对象和库以相反的方式,则链接器打开library.a,在其表中没有不确定的引用并将其关闭。然后,它尝试和编译someobject.o,而未定义的参考文献永远不会满足

编辑:这是GCC的众所周知的警告,这里可以看到更详细的堆栈跨流说明,并且选项--start-group--end-group可以帮助解决A的依赖B的情况,而B取决于A。

是您的Makefile。您想要:

libdatabase.a

-ldatabase

main编译线的末尾