在macOS上找不到架构的Boost::日志符号



我真的不想问这个基本问题,但我正在尝试构建一个使用websocketpp的系统,该系统有望在某个时候部署到Ubuntu服务器上,我想为应用程序使用Boost Logging。我想既然websocketpp已经需要boost,我还不如使用它的日志记录。

我目前正在mac上测试设置,因为这就是我的全部。我的项目仍然只是一个main.cpp文件,它遵循本教程。它看起来像这样:

main.cpp

#include <iostream>
#include <boost/log/core.hpp>
#include <boost/log/trivial.hpp>
#include <boost/log/utility/setup/file.hpp>
#include <boost/log/expressions.hpp>
namespace logging = boost::log;
void init_logging(const char * logger_filename)
{
logging::add_file_log(logger_filename);
logging::core::get()->set_filter(logging::trivial::severity >= logging::trivial::info);
}

int main(int, char*[]) {
init_logging("titan_logger.log");
BOOST_LOG_TRIVIAL(trace) << "This is a trace severity message";
BOOST_LOG_TRIVIAL(debug) << "This is a debug severity message";
BOOST_LOG_TRIVIAL(info) << "This is an informational severity message";
BOOST_LOG_TRIVIAL(warning) << "This is a warning severity message";
BOOST_LOG_TRIVIAL(error) << "This is an error severity message";
BOOST_LOG_TRIVIAL(fatal) << "and this is a fatal severity message";
std::cin.get();
return 0;
} 

我一直在成功地遵循教程,直到我想使用文件记录器。然后我开始得到一个错误,结果是这样的:

...
traits<wchar_t>, std::__1::allocator<wchar_t> > >, boost::log::v2s_mt_posix::fallback_to_none>::operator()<boost::log::v2s_mt_posix::binder1st<boost::log::v2s_mt_posix::output_fun, boost::log::v2s_mt_posix::expressions::aux::stream_ref<boost::log::v2s_mt_posix::basic_formatting_ostream<char, std::__1::char_traits<char>, std::__1::allocator<char> > >&> >(boost::log::v2s_mt_posix::attribute_name const&, boost::log::v2s_mt_posix::attribute_value_set const&, boost::log::v2s_mt_posix::binder1st<boost::log::v2s_mt_posix::output_fun, boost::log::v2s_mt_posix::expressions::aux::stream_ref<boost::log::v2s_mt_posix::basic_formatting_ostream<char, std::__1::char_traits<char>, std::__1::allocator<char> > >&>) const in main.o
boost::log::v2s_mt_posix::value_extractor<boost::log::v2s_mt_posix::trivial::severity_level, boost::log::v2s_mt_posix::fallback_to_none, boost::log::v2s_mt_posix::trivial::tag::severity>::operator()(boost::log::v2s_mt_posix::attribute_name const&, boost::log::v2s_mt_posix::attribute_value_set const&) const in main.o
"boost::log::v2s_mt_posix::aux::once_block_sentry::enter_once_block() const", referenced from:
boost::log::v2s_mt_posix::aux::once_block_sentry::executed() const in main.o
"boost::log::v2s_mt_posix::core::get_logging_enabled() const", referenced from:
boost::log::v2s_mt_posix::record boost::log::v2s_mt_posix::sources::basic_composite_logger<char, boost::log::v2s_mt_posix::sources::severity_logger_mt<boost::log::v2s_mt_posix::trivial::severity_level>, boost::log::v2s_mt_posix::sources::multi_thread_model<boost::log::v2s_mt_posix::aux::light_rw_mutex>, boost::log::v2s_mt_posix::sources::features<boost::log::v2s_mt_posix::sources::severity<boost::log::v2s_mt_posix::trivial::severity_level> > >::open_record<boost::parameter::aux::tagged_argument_list_of_1<boost::parameter::aux::tagged_argument<boost::log::v2s_mt_posix::keywords::tag::severity, boost::log::v2s_mt_posix::trivial::severity_level const> > >(boost::parameter::aux::tagged_argument_list_of_1<boost::parameter::aux::tagged_argument<boost::log::v2s_mt_posix::keywords::tag::severity, boost::log::v2s_mt_posix::trivial::severity_level const> > const&) in main.o
ld: symbol(s) not found for architecture x86_64

我的猜测是,我正在使用boost库,该库是我使用几天前运行的brew install boost链接的。现在我需要为boost::Log构建boost库,但它失败了。

我是如何建立助推的我使用本教程构建了boost,但使用了g++-10std=c++14

我下载了boost_1_75_0并将其放在我的项目目录中,然后我(从项目目录)运行的完整命令是:

cd boost_1_75_0

./bootstrap.sh

./b2 -link=static toolset=gcc cxxflags=-std=c++14 --build-dir=../build --with-log --with-regex --with-random --with-system --with-thread --with-filesystem --with-date_time

我遵循了这条评论的第二条建议,并将所有静态库放在它们自己的名为lib_boost的文件夹中。该应用程序被称为Titan,这就是下面命令中的含义。

make命令:

g++ -Wall -I/Users/QuantumHoneybees/Desktop/Titan/Titan/boost_1_75_0 -std=c++14 -lpthread main.cpp -o titan -L./lib_boost  -lboost_log_setup-mt   -lboost_log-mt -lboost_filesystem-mt  -lboost_thread-mt -lboost_system-mt

我的驼背

这个SO线程似乎有同样的问题,但使用了cmake。问题是。。。我确实链接了thread库。我只是觉得联系不好。我认为问题的一部分是我使用了静态链接。。。我正在尝试优化运行时,我其实并不关心二进制大小。所以我有意使用静态链接。

我想我没有正确地链接库。。。我不是一个完全的C++新手,但我很擅长链接错误。。。我真的不知道这里可能出了什么问题。如有任何帮助,我们将不胜感激。谢谢


更新:(但不是一个干净的解决方案)

所以事实证明有几个问题:

  1. 删除和取消链接的自制软件安装版本,这导致了的一些假阴性

  2. 我必须链接到静态编译的.a文件直接用于CCD_ 20文件。

  3. 我还必须使用clang重建Boost,并切换make以使用

这是最后一个(非常丑陋)命令:

clang++ -Wall -I/Users/QH/Desktop/Titan/Titan/boost_1_75_0 -std=c++14 -lpthread main.cpp -o titan -L/Users/QH/Desktop/Titan/Titan/boost_1_75_0/stage/lib -lboost_system -lboost_thread -lboost_thread -lboost_filesystem /Users/QH/Desktop/Titan/Titan/boost_1_75_0/stage/lib/libboost_log.a

它是有效的,但它显示了许多关于导致错误的相同boost::log::v2s_mt_posix::方法的警告,但老实说,我不在乎在这一点上修复它们。

出于某种原因,如果我用-lboost_log替换最后一个库,我会再次得到相同的未定义引用错误。我希望这能帮助别人找到答案!


对于未来的旅行者,以下是全套工作步骤(感谢@AndreySemashev:

  1. 将boost zip和cd下载到目录中,类似于boost_1_75_0(您的版本可能不同)

  2. 运行./bootstrap.sh

  3. 运行以下操作:./b2 link=static cxxstd=14 --build-dir=../build --with-log --with-regex --with-random --with-system --with-thread --with-filesystem --with-date_time*

  4. 要进行编译,请运行clang++ -Wall -I./boost_1_75_0 -std=c++14 -lpthread main.cpp -o titan -L./boost_1_75_0/stage/lib -lboost_system -lboost_thread -lboost_thread -lboost_filesystem -lboost_log_setup -lboost_log

当您指定-lboost_log时,链接器默认情况下会尝试查找共享库。只有在找不到它的情况下,它才会查找静态库。

在Boost.Log中,静态库和共享库中的符号被不同地篡改,使它们不兼容。默认情况下,库采用静态链接。为了启用动态链接,在编译使用Boost.Log的代码时,必须定义BOOST_LOG_DYN_LINKBOOST_ALL_DYN_LINK(前者意味着只有Boost.Log动态链接,后者意味着所有Boost库都动态链接)。


其他一些注意事项:

  • 您必须确保用于构建Boost的C++标准库与您的应用程序相匹配。例如,您不能用libc++构建Boost,也不能用libstdc++构建代码——这两个标准库定义了不同的符号,并具有不同的ABI,因此您的代码不会与Boost链接
  • 您必须确保Boost是使用与您的代码相同或更高版本的C++构建的。否则,您可能无法链接,因为缺少符号(例如,涉及C++11功能的方法在C++03 Boost库中不可用)
  • 在构建Boost和代码时,必须确保影响ABI的编译器选项和宏的定义方式相同。否则,您可能会遇到ABI不兼容问题,这很难诊断和调试
  • b2命令行中,应指定不带短划线的-link=static,并且可以使用cxxstd=14而不是cxxflags=-std=c++14
  • 如果您正在使用Boost。从boost/log/utility/setup目录中记录功能,除了boost_log之外,您可能还需要链接到boost_log_setup库。boost_log_setup依赖于boost_log并提供额外的库设置帮助程序

最新更新