log4cpp:有关SIGSEGV的两个问题
我正在研究Linux下的cpp项目,我想构建一个日志系统来将一些重要信息写入文件。所以我用这个libraty:log4cpp
log4cpp:有关SIGSEGV的两个问题
这里是我的代码约log4cpp:
// class Log head file
class Log
{
public:
explicit Log(const char * infoCategory = nullptr, const string & pattern = string("%d: %p %c %x: %m%n"), const char * filename = "log")
: category(infoCategory == nullptr ? Category::getRoot() : Category::getRoot().getInstance(infoCategory))
{
logFile.open(filename, ios::app);
osAppender = new OstreamAppender("osAppender", &logFile);
patternLayout = new PatternLayout();
patternLayout->setConversionPattern(pattern);
osAppender->setLayout(patternLayout);
category.addAppender(osAppender);
logFile.seekp(0, ios::end);
size = logFile.tellp();
}
~Log()
{
category.shutdown();
logFile.close();
// Do NOT delete osAppender and patternLayout
}
void info(const string & info)
{
category.info(info);
}
private:
ofstream logFile;
streampos size;
Category & category;
OstreamAppender * osAppender;
PatternLayout * patternLayout;
};
现在,我可以使用Log
来记东西。例如,有一类代理这样的:
#include "Log.h"
class Agent
{
public:
~Agent()
{
terminate();
}
void initialize()
{
log.info(" initialized.");
}
void terminate()
{
log.info(" terminated.");
}
static Agent & getInstance()
{
static Agent agent;
return agent;
}
Agent()
{
}
private:
Log log;
};
功能getInstance
是产生了“单身”。它的构造函数是私有的,所以我们必须调用getInstance
来生成一个对象。由于这个对象是静态的,所以它只能初始化一次。 现在在main
,我这样写:
int main()
{
Agent & agent = Agent::getInstance();
agent.initialize();
return 0;
}
现在,如果我运行它,该项目将停止在功能Log::info
,我会得到这个错误:Signal received: SIGSEGV(Segmentation fault)
令我惊讶的是,如果我删除log.info("terminated.");
或删除log.info("initialized");
或我动议两项info
到函数initialize
或terminate
,错误就会消失。
或者,如果我在函数main
中初始化一个正常的Agent
,我的意思是我没有使用getInstance
,而是我这样做:Agent agent;
,错误也会消失。
或者,如果我在功能getInstance
新的Agent
,而不是使用static
,错误就会消失了。
这是我的第一个问题。
我的第二个问题是在这里:
请注意,在Log
析构函数评论:// do NOT delete osAppender and patternLayout
我把这样的评论,因为我觉得他们两个是它们来自指针new
,所以我可以并应该删除它们。但是如果我删除其中一个或它们两个,我会得到相同的错误:Signal received:SIGSEGV
。
问题已解决。
我得到这个问题,因为log
和agent
这里都是静态的。
这意味着他们两个将在return 0;
之后免费在功能main
之后,我们不能决定免费的顺序。
在这种情况下,agent
的虚函数被调用之前明显的log
一直是免费的,所以,当我在虚拟函数调用terminate()
,会有一个错误。
如果有人也在Linux下工作,你可以安装log4cpp并为我做一个测试吗? – Yves