C++ Library containing a lot of needful things: Stack Trace, Command Line Parser, Resource Handling, Configuration Files, Unix Command Execution, Directories, Regular Expressions, Tokenizer, Function Trace, Standard Extensions.
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
245 lines
11 KiB
245 lines
11 KiB
20 years ago
|
/** @file
|
||
|
|
||
|
$Id$
|
||
|
|
||
|
$Date$
|
||
|
$Author$
|
||
|
|
||
|
@copy © Marc Wäckerlin
|
||
|
@license LGPL, see file <a href="license.html">COPYING</a>
|
||
|
|
||
|
$Log$
|
||
19 years ago
|
Revision 1.3 2005/11/29 12:39:42 marc
|
||
|
make it compilable with gcc 4.0.2 and newer doxygen
|
||
|
|
||
20 years ago
|
Revision 1.2 2005/04/07 20:42:38 marc
|
||
|
renamed loggerhierarchy from mrw.gccfunctiontrace to mrw.fn
|
||
|
|
||
20 years ago
|
Revision 1.1 2005/03/11 21:07:55 marc
|
||
|
initial version
|
||
|
|
||
|
|
||
|
1 2 3 4 5 6 7 8
|
||
|
5678901234567890123456789012345678901234567890123456789012345678901234567890
|
||
|
*/
|
||
|
|
||
|
#include <log4cxx/propertyconfigurator.h>
|
||
|
#include <log4cxx/helpers/properties.h>
|
||
|
#include <cppunit/TestFixture.h>
|
||
|
#include <cppunit/ui/text/TestRunner.h>
|
||
|
#include <cppunit/extensions/HelperMacros.h>
|
||
|
#include <cppunit/extensions/TestFactoryRegistry.h>
|
||
13 years ago
|
#include <mrw/file.hxx>
|
||
|
#include <mrw/regexp.hxx>
|
||
|
#include <mrw/string.hxx>
|
||
|
#include <mrw/stacktrace.hxx>
|
||
20 years ago
|
#include <map>
|
||
|
|
||
17 years ago
|
#if (__GNUC__==3 && __GNUC_MINOR__<4 || __GNUC__<3) \
|
||
|
&& defined(_REENTRANT) && !defined(_MT)
|
||
19 years ago
|
#define _MT
|
||
|
#endif
|
||
|
|
||
20 years ago
|
namespace HalloWelt {
|
||
|
|
||
|
class A {
|
||
|
public:
|
||
|
void method() {
|
||
|
}
|
||
|
};
|
||
|
|
||
19 years ago
|
void fn(int) {
|
||
20 years ago
|
A().method();
|
||
|
A().method();
|
||
|
}
|
||
|
|
||
|
void fn1() {
|
||
19 years ago
|
fn(1);
|
||
|
fn(2);
|
||
20 years ago
|
}
|
||
|
|
||
|
}
|
||
|
|
||
|
void anotherFunction() {
|
||
|
HalloWelt::fn1();
|
||
|
}
|
||
|
|
||
19 years ago
|
#ifdef _MT
|
||
13 years ago
|
#include <boost/thread/thread.hxx>
|
||
20 years ago
|
//#include <unistd.h> // sleep, the one from boost::thread does not work!
|
||
|
class Thread {
|
||
|
public:
|
||
|
void operator()() {
|
||
|
anotherFunction();
|
||
|
}
|
||
|
};
|
||
|
#endif
|
||
|
|
||
|
namespace mrw {
|
||
|
class AutoFunctionTraceLog4CxxTest: public CppUnit::TestFixture {
|
||
|
public:
|
||
|
void testcase() {
|
||
|
mrw::StackTrace::createSymtable();
|
||
19 years ago
|
#ifdef _MT
|
||
20 years ago
|
try {mrw::File::remove("mrwautofunctiontracelog4cxx_test-mt.log");}
|
||
|
#else
|
||
|
try {mrw::File::remove("mrwautofunctiontracelog4cxx_test.log");}
|
||
|
#endif
|
||
|
catch (...) {}
|
||
|
log4cxx::helpers::Properties properties;
|
||
18 years ago
|
std::string name, cont;
|
||
|
properties.setProperty((name="log4j.rootLogger",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF, A1",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="DEBUG",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn.global",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn.allocator",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn.std.*",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn.log4cxx",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn.boost",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn.Thread",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn.mrw",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn.std",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn.new",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn.CppUnit",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.logger.mrw.fn.__gnu_cxx",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="OFF",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.appender.A1",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="org.apache.log4j.FileAppender",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.appender.A1.layout",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="org.apache.log4j.PatternLayout",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
19 years ago
|
#ifdef _MT
|
||
18 years ago
|
properties.setProperty((name="log4j.appender.A1.layout.ConversionPattern",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="%t-%-27c%m%n",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.appender.A1.filename",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="mrwautofunctiontracelog4cxx_test-mt.log",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
20 years ago
|
#else
|
||
18 years ago
|
properties.setProperty((name="log4j.appender.A1.layout.ConversionPattern",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="%-27c%m%n",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
|
properties.setProperty((name="log4j.appender.A1.filename",
|
||
|
log4cxx::String(name.begin(), name.end())),
|
||
|
(cont="mrwautofunctiontracelog4cxx_test.log",
|
||
|
log4cxx::String(cont.begin(), cont.end())));
|
||
20 years ago
|
#endif
|
||
|
log4cxx::PropertyConfigurator::configure(properties);
|
||
19 years ago
|
#ifdef _MT
|
||
20 years ago
|
// sleep(4); // to be reproducable, wait for "main" flag
|
||
|
Thread threadFunction;
|
||
|
boost::thread::thread thread1(threadFunction);
|
||
|
boost::thread::thread thread2(threadFunction);
|
||
|
boost::thread::thread thread3(threadFunction);
|
||
|
#endif
|
||
|
anotherFunction();
|
||
19 years ago
|
#ifdef _MT
|
||
20 years ago
|
thread1.join();
|
||
|
thread2.join();
|
||
|
thread3.join();
|
||
|
#endif
|
||
|
}
|
||
|
void checkfile() {
|
||
|
mrw::RegExp match
|
||
20 years ago
|
("^mrw\\.fn\\.anotherFunction ( ? ? ?)\\\\ anotherFunction\\(\\)\n"
|
||
|
"mrw\\.fn\\.HalloWelt\\.fn1 \\1 \\\\ HalloWelt::fn1\\(\\)\n"
|
||
19 years ago
|
"mrw\\.fn\\.HalloWelt\\.fn \\1 \\\\ HalloWelt::fn\\(int\\)\n"
|
||
20 years ago
|
"mrw\\.fn\\.HalloWelt\\.A\\.method \\1 \\\\ HalloWelt::A::method\\(\\)\n"
|
||
|
"mrw\\.fn\\.HalloWelt\\.A\\.method \\1 / HalloWelt::A::method\\(\\)\n"
|
||
|
"mrw\\.fn\\.HalloWelt\\.A\\.method \\1 \\\\ HalloWelt::A::method\\(\\)\n"
|
||
|
"mrw\\.fn\\.HalloWelt\\.A\\.method \\1 / HalloWelt::A::method\\(\\)\n"
|
||
19 years ago
|
"mrw\\.fn\\.HalloWelt\\.fn \\1 / HalloWelt::fn\\(int\\)\n"
|
||
|
"mrw\\.fn\\.HalloWelt\\.fn \\1 \\\\ HalloWelt::fn\\(int\\)\n"
|
||
20 years ago
|
"mrw\\.fn\\.HalloWelt\\.A\\.method \\1 \\\\ HalloWelt::A::method\\(\\)\n"
|
||
|
"mrw\\.fn\\.HalloWelt\\.A\\.method \\1 / HalloWelt::A::method\\(\\)\n"
|
||
|
"mrw\\.fn\\.HalloWelt\\.A\\.method \\1 \\\\ HalloWelt::A::method\\(\\)\n"
|
||
|
"mrw\\.fn\\.HalloWelt\\.A\\.method \\1 / HalloWelt::A::method\\(\\)\n"
|
||
19 years ago
|
"mrw\\.fn\\.HalloWelt\\.fn \\1 / HalloWelt::fn\\(int\\)\n"
|
||
20 years ago
|
"mrw\\.fn\\.HalloWelt\\.fn1 \\1 / HalloWelt::fn1\\(\\)\n"
|
||
|
"mrw\\.fn\\.anotherFunction \\1/ anotherFunction\\(\\)\n$");
|
||
19 years ago
|
#ifdef _MT
|
||
20 years ago
|
std::string log(mrw::File::read("mrwautofunctiontracelog4cxx_test-mt.log"));
|
||
19 years ago
|
typedef std::map<unsigned long, std::string> Logs;
|
||
|
Logs logs;
|
||
20 years ago
|
for (std::string::size_type pos(0), last(0);
|
||
|
(pos=log.find('\n', pos+1))!=std::string::npos; last=pos) {
|
||
|
std::string::size_type dash(log.find('-', last));
|
||
19 years ago
|
CPPUNIT_ASSERT_MESSAGE("\"-\" not found",
|
||
|
dash!=std::string::npos);
|
||
20 years ago
|
logs[mrw::to<unsigned long>(log.substr(last, dash-last))] +=
|
||
|
log.substr(dash+1, pos-dash);
|
||
|
}
|
||
19 years ago
|
CPPUNIT_ASSERT_EQUAL((Logs::size_type)4, logs.size()); // 4 threads
|
||
|
for (Logs::iterator it(logs.begin()); it!=logs.end(); ++it)
|
||
|
CPPUNIT_ASSERT_MESSAGE("The following text does not match the "
|
||
|
"Expectation:\n--------------------\n"
|
||
|
+it->second+"--------------------",
|
||
|
match(it->second));
|
||
20 years ago
|
mrw::File::remove("mrwautofunctiontracelog4cxx_test-mt.log");
|
||
|
#else
|
||
19 years ago
|
CPPUNIT_ASSERT_MESSAGE
|
||
|
("The following text does not match the "
|
||
|
"Expectation:\n--------------------\n"
|
||
|
+mrw::File::read("mrwautofunctiontracelog4cxx_test.log")
|
||
|
+"--------------------",
|
||
|
match(mrw::File::read("mrwautofunctiontracelog4cxx_test.log")));
|
||
20 years ago
|
mrw::File::remove("mrwautofunctiontracelog4cxx_test.log");
|
||
|
#endif
|
||
|
}
|
||
|
CPPUNIT_TEST_SUITE(AutoFunctionTraceLog4CxxTest);
|
||
|
CPPUNIT_TEST(testcase);
|
||
|
CPPUNIT_TEST(checkfile);
|
||
|
CPPUNIT_TEST_SUITE_END();
|
||
|
};
|
||
|
CPPUNIT_TEST_SUITE_REGISTRATION(AutoFunctionTraceLog4CxxTest);
|
||
|
}
|
||
|
|
||
|
int main() {
|
||
|
CppUnit::TextUi::TestRunner runner;
|
||
|
runner.addTest(CppUnit::TestFactoryRegistry::getRegistry().makeTest());
|
||
|
return runner.run() ? 0 : 1;
|
||
|
}
|