我想在一个混合的C/C应用程序中使用C日志库。遗留应用程序充满了printf风格的日志记录。新图书馆也支持这一点。
C文件是用C编译器编译的,所以我不能在其中包含C日志头。
我正在努力创建一个带有C风格头文件和C源文件的C++库:
//logger.h
extern "C" {
extern void RS_LOG_INFO_PRIVATE(const char* fmt, ...);
#define LOG_INFO(...) RS_LOG_INFO_PRIVATE(__VA_ARGS__)
}
//logger.cpp
#include "logger.h"
#include <aws/core/utils/logging/LogMacros.h>
#include <utility>
template<class... Args>
void RS_LOG_INFO_PRIVATE(const char* fmt, Args&&... args) {
AWS_LOG_DEBUG(fmt, std::forward<Args>(args)...);
}
//main file
#include "logger.h"
int main() {
LOG_INFO("test %s", "me");
}
我得到undefined reference to 'RS_LOG_INFO_PRIVATE'
。nm -C
也验证了这一点:
U RS_LOG_INFO_PRIVATE(char const*, ...)
有没有办法解决这个问题,或者我应该改变我的方法?
1条答案
按热度按时间flseospp1#
如果您正在重新编译应用程序,可以认真考虑从C编译器更改为C编译器。这样做会导致各种编译问题,但解决这些问题通常并不比对C编译方式进行一些重大修改(例如,新的编译器供应商,或提高编译器警告级别)更困难。通过这种方式,您可以避免使用C风格的变量参数,并将其替换为可变参数模板调用。
如果切换到C编译器是不可行的,那么你必须让你的头文件充当C编译器的C头文件,并充当C编译器的C头文件(或为不同的编译器维护两个不同的头文件)。
假设你的C和C++编译器有兼容的CABI,那么检测使用哪个编译器的常用机制是
__cplusplus
宏。一个常见的技巧是通过使用
extern "C"
Package C头文件的内容,使C头文件可用于C++头文件。您似乎尝试过这样做,但没有检查__cplusplus
。C编译器无法理解
extern "C"
是什么,因此它被__cplusplus
检查隐藏,这将是为C编译器定义的。变量参数函数的库实现在C中实现时不应该有所不同(
#include
头文件)。然后,实现将调用实际完成调用所需的任何C++实现代码。