【发布时间】:2020-03-05 09:22:29
【问题描述】:
我正在尝试创建一个使用我的 earlier created shared library, which by the way is now static 的可执行文件,其中包括 openSSL 静态库。因此,我使用了与创建该库相同的 Makefile,并对其进行了破解以使其在这里工作。看起来是这样的
LIBBASE=/home/AB/Documents/APP/APP_2.17.0
OPENSSL1.0.2p_INSTALL_LOC=/home/AB/Documents/APP/OpenSSL-1.0.2p-installation
CC=gcc
CXX=g++
CFLAGS= -Wall -g -pedantic
CPPFLAGS= -Wall -g -pedantic
RM= rm -f
.PHONY: all clean
c_src=$(shell find . -iname "*.c")
$(info source=$(c_src))
cpp_src=$(shell find . -iname "*.cpp")
$(info cppsource=$(cpp_src))
INC=-I$(LIBBASE)/include
$(info includes=$(INC))
# need to link pthread library here as well
LIB = -pthread
# aforementioned library
LIB+=-L$(LIBBASE)/lib
LIB+= -l:libSCA.a
#need to add SSL related libraries
LIB+= -L$(OPENSSL1.0.2p_INSTALL_LOC)/lib
LIB+= -l:libssl.a -l:libcrypto.a -static-libgcc
# As mentioned, we need to link dl and libz libraries as well
LIB+= -ldl -lz
$(info links=$(LIB))
obj=$(c_src:.c=.o) $(cpp_src:.cpp=.o)
all: APP
clean:
$(RM) *.o APP
$(shell find $(APPBASE) -type f -iname "*.o" -exec rm -rf {} \;)
.c.o:
${CXX} -static ${CPPFLAGS} $(INC) -c $< -o $@
#${CC} -static ${CFLAGS} $(INC) -c $< -o $@
.cpp.o:
${CXX} -static ${CPPFLAGS} $(INC) -c $< -o $@
APP: $(obj)
$(LINK.cxx) $^ -o $@ $(LIB)
但是我无法让它工作。我得到了很多未定义的对我的库定义的符号的引用。我已经注意在 cpp 文件中的这些符号周围使用 extern C,但它似乎没有帮助。
顺便说一句,还有比这更直接或更简单的方法吗?
此外,在浏览此处的各种答案时,我发现.c.o 之类的目标已经过时,不应再使用。是否有最新的、详尽的、 实用的 Makefile 权威指南(问太多了)??
更新 1:所以在这里我可以访问日志,我注意到我得到的所有未定义的引用错误都与我静态链接到我的共享库的 SSL 库定义的符号有关。我的错误日志示例:
/home/AB/Documents/APP/APP_2.17.0_Linux/libAPP.so: undefined reference to `SSL_CTX_free'
/home/AB/Documents/APP/APP_2.17.0_Linux/libAPP.so: undefined reference to `X509_set_issuer_name'
所以我想制作一个静态库,可以在内部链接(或者更确切地说是合并)libssl.a。 Modified my aforementioned makefile 并创建了一个静态 libAPP.a。但我仍然不断收到这些错误。
我终于在这个 makefile 中添加了 libssl.a 和 libcrypto.a,瞧,很多错误都得到了修复。我仍然有一些与dlopen 和 pthreads 相关的错误,所以我也添加了这些错误。我还使用 CXX 编译器编译所有内容,以消除由于名称混淆引起的问题。
现在让我感到困扰的是,与 SSL 相关的符号应该已经存在于 libAPP.a 中(尽管 nm 将它们报告为 undefined 并且可能需要自己提出另一个问题:D )。但我仍然需要在此处指定libSSL.a 和libcrypto.a 以便链接器找到它们!那么创建存档(libAPP.a)而不是共享库(libAPP.so)有什么好处呢?
最后在链接阶段,我的链接器找不到lz
/usr/bin/ld: cannot find -lz
只是为了它,我尝试将相同的标志添加到创建该存档的 makefile 中,并且找到它没有问题。有什么建议吗??
【问题讨论】:
-
GnuMake 手册有一些启发性的章节。
-
当然可以,我确定。但是自己处于生产环境中,我希望你明白我的时间很短(现在不是哪个开发人员:))。如果您有快速修复或可以指出其中的明显缺陷或建议更简单的方法来解决此类问题,我将不胜感激!
-
@thebusybee 顺便说一句,当我放松并想学习新东西时,我一定会看看这些章节
-
首先你应该明白你的问题不在于make或makefile。如果您遇到链接错误,则意味着问题在于您的编译或链接命令错误。因此,试图将它归咎于 make 或 makefile 不会让你有任何收获。如果您不熟悉如何将编译器和链接器与共享库一起使用,一个有用的练习是尝试直接在 shell 提示符下运行编译命令,直到您弄清楚哪些是正确的。那么你可以考虑如何以最有效的方式将它们放入你的 makefile 中。
-
按照惯例,
CXXFLAGS是 C++ 编译器的标志,而CPPFLAGS是 C 预处理器的标志。
标签: c++ c makefile linker mixed-mode