00001 /*----------------------------------------------------------------------------- 00002 Name: TestThread.cpp 00003 Project: xmlBlaster.org 00004 Copyright: xmlBlaster.org, see xmlBlaster-LICENSE file 00005 Comment: Testing the Thread cleanup 00006 -----------------------------------------------------------------------------*/ 00007 #include "TestSuite.h" 00008 #include <iostream> 00009 00010 using namespace std; 00011 using namespace org::xmlBlaster::util; 00012 using namespace org::xmlBlaster::util::thread; 00013 00022 namespace org { namespace xmlBlaster { namespace test { 00023 00024 class TestThread : public Thread { 00025 00026 private: 00027 string ME; 00028 Global& global_; 00029 I_Log& log_; 00030 bool blocking_; 00031 bool doRun_; 00032 org::xmlBlaster::util::thread::Mutex *invocationMutex_; 00033 public: 00034 TestThread(Global& global, string name, bool blocking) 00035 : ME(name), 00036 global_(global), 00037 log_(global.getLog("test")), 00038 invocationMutex_(0) 00039 { 00040 blocking_ = blocking; 00041 doRun_ = true; 00042 } 00043 00044 ~TestThread() 00045 { 00046 if (log_.call()) log_.call(ME, "destructor"); 00047 if (!blocking_) { 00048 doRun_ = false; 00049 join(); 00050 } 00051 } 00052 00053 void run() 00054 { 00055 log_.info(ME, "start run"); 00056 if (blocking_) { 00057 sleepSecs(30); 00058 } 00059 else { 00060 while (doRun_) { 00061 if (log_.trace()) log_.trace(ME, "run: going to sleep"); 00062 sleep(20); 00063 } 00064 if (log_.trace()) log_.trace(ME, "run: coming out of non-blocking run loop"); 00065 } 00066 log_.info(ME, "stopped run"); 00067 } 00068 00069 void testThread() 00070 { 00071 log_.info(ME, "testThread() start"); 00072 const bool detached = false; 00073 start(detached); 00074 sleepSecs(2); 00075 log_.info(ME, "testThread() end"); 00076 } 00077 00078 void testRecursiveThread() 00079 { 00080 log_.info(ME, "testRecursiveThread() start"); 00081 int count = 0; 00082 bool recursive = global_.getProperty().get("xmlBlaster/invocationMutex/recursive", true); 00083 invocationMutex_ = new Mutex(recursive); 00084 callRecursive(count); 00085 delete invocationMutex_; 00086 log_.info(ME, "testRecursiveThread() end"); 00087 } 00088 00089 void callRecursive(int count) { 00090 Lock lock(*invocationMutex_); 00091 count++; 00092 log_.info(ME, "testRecursiveThread() count=" + lexical_cast<string>(count)); 00093 if (count > 4) { 00094 return; 00095 } 00096 callRecursive(count); 00097 } 00098 00099 void setUp(int args=0, char *argc[]=0) { 00100 if (log_.trace()) { 00101 for (int i=0; i < args; i++) { 00102 log_.trace(ME, string(" setUp invoked with argument ") + string(argc[i])); 00103 } 00104 } 00105 } 00106 00107 void tearDown() { 00108 } 00109 }; 00110 00111 }}} // namespace 00112 00113 using namespace org::xmlBlaster::test; 00114 00115 int main(int args, char *argc[]) 00116 { 00117 org::xmlBlaster::util::Object_Lifetime_Manager::init(); 00118 00119 Global& glob = Global::getInstance(); 00120 glob.initialize(args, argc); 00121 00122 TestThread *testObj = new TestThread(glob, "TestThread", false); 00123 testObj->setUp(args, argc); 00124 testObj->testRecursiveThread(); 00125 testObj->testThread(); 00126 testObj->tearDown(); 00127 delete testObj; 00128 00129 testObj = new TestThread(glob, "TestThread", true); 00130 testObj->setUp(args, argc); 00131 testObj->testThread(); 00132 testObj->tearDown(); 00133 delete testObj; 00134 testObj = NULL; 00135 00136 org::xmlBlaster::util::Object_Lifetime_Manager::fini(); 00137 return 0; 00138 } 00139 00140