⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 chk_thread1.cpp

📁 一个不错
💻 CPP
字号:
/* Copyright is licensed under GNU LGPL.                 by I.J.Wang 2003   Test Wy_Thread Part-I   Basic thread check   Build: make chk_thread1*/#include "tsthread.h"#include "wy_atdestroy.h"#include "wy_uty.h"#include <cstdlib>#include <iostream>#if WY_THREAD_VERSION!=31#error Test code is for WY_THREAD_VERSION 31#endif// Check Wy_ThreadIDstatic void chk_threadid(void){ const ::pthread_t SelfID=::pthread_self(); // constructor {  Wy_ThreadID t0,t1(t0);  if(t0.is_default()==false) {    WY_THROW( WyRet() );  }  if(t1.is_default()==false) {    WY_THROW( WyRet() );  }  if(t0!=t1) {    WY_THROW( WyRet() );  }  if(t0==t1) {  } else {    WY_THROW( WyRet() );  }  if(::pthread_equal(t0._pthread_id(),SelfID)) {    WY_THROW( WyRet() );       // assertion failed  }  if(Wy_ThreadID::_thread_equal(t0,t1)==false) {  // default obj's are equ    WY_THROW( WyRet() );  } } {  Wy_ThreadID t0,t1;  t1.reset(SelfID);  Wy_ThreadID t2(t1);  if(t0.is_default()==false) {    WY_THROW( WyRet() );  }  if(t1.is_default()) {    WY_THROW( WyRet() );  }  if(t2.is_default()) {    WY_THROW( WyRet() );  }  if(t0==t1) {    WY_THROW( WyRet() );  }  if(t1!=t2) {    WY_THROW( WyRet() );  }  if(Wy_ThreadID::_thread_equal(t0,t1)==true) {    WY_THROW( WyRet() );  }  if(Wy_ThreadID::_thread_equal(t1,t2)==false) {    WY_THROW( WyRet() );  } } // reset {  Wy_ThreadID t0,t1;  t1.reset(SelfID);  Wy_ThreadID t2(t1);  t0.reset();  if(t0.is_default()==false) {    WY_THROW( WyRet() );  }  t1.reset();  if(t1.is_default()==false) {    WY_THROW( WyRet() );  }  t1.reset(t2);  if(t1.is_default()) {    WY_THROW( WyRet() );  }  if(t1!=t2) {    WY_THROW( WyRet() );  } } // chk move ctor {  char buf[2*sizeof(Wy_ThreadID)];  ::memset(buf,0,sizeof(buf));  Wy_ThreadID*p=reinterpret_cast<Wy_ThreadID*>(buf);  new(p) Wy_ThreadID();  new(p+1) Wy_ThreadID(*p,Wy::ByMove);  if((p+1)->is_default()==false) {    (p+1)->~Wy_ThreadID();    WY_THROW( WyRet() );  }  (p+1)->~Wy_ThreadID(); }};class T_ErrInfo : public Wy_RepInfo {    T_ErrInfo(const T_ErrInfo&);  public:    T_ErrInfo(const char* cstr) throw() : Wy_RepInfo(cstr) {};    size_t get_reply(char* buf, size_t blen) const throw()       { return Wy_RepInfo::get_reply(buf,blen); };    void set_reply(const char* buf, size_t blen) throw()       {};};static T_ErrInfo ei("Test Failed");static const WyReply TEST_FAIL(ei);// Check default TsThread object properties//static WyRet chk_default_attr(TsThread& thrd){ Wy_Thread::ThreadState st; WyRet tret; WyRet r; if(thrd.is_default()==false) {   WY_RETURN(TEST_FAIL); } st=thrd.thread_state(); if(st!=Wy_Thread::Null) {   WY_RETURN(TEST_FAIL); } if(thrd.thread_id().is_default()==false) {   WY_RETURN(TEST_FAIL); } if((r=thrd.cancel())!=Wym_ESRCH) {   WY_RETURN(TEST_FAIL); } if((r=thrd.wait_not(Wy_Thread::Stopped))!=Ok) {   WY_RETURN(TEST_FAIL); } if((r=thrd.wait_not(Wy_Thread::Active))!=Ok) {   WY_RETURN(TEST_FAIL); } tret=thrd.exitcode(); if(!tret.is_default()) {   WY_RETURN(TEST_FAIL); } {  Wy_Thread::CancelType ct( thrd.set_canceltype(Wy_Thread::Deferred) );  if(ct!=Wy_Thread::Deferred) {    thrd.set_canceltype(ct);    WY_RETURN(TEST_FAIL);  } } return(Ok);};// begin() the default TsThread thrd configured as the arguments// and chk for expected behavior//static void ck_thread_0(TsThread& thrd,TsThread::ExitType etype,WyReply ec,WyTimeSpec delay)try { WyRet r; if((r=chk_default_attr(thrd))!=Ok) {   WY_THROW(r); } if((r=thrd.begin())!=Ok) {   WY_THROW(r); } if((r=thrd.begin())!=Wym_EBADF) {   WY_THROW(r); } const WyTimeSpec TM0( Wy::now() ); WyTimeSpec tm; if((r=thrd.wait_not(Wy_Thread::Null))!=Ok) {   WY_THROW(r); } if(thrd.thread_state()!=Wy_Thread::Active) {   WY_THROW( WyRet() ); } if(thrd.thread_id().is_default()) {   WY_THROW( WyRet() ); } switch(etype) {   case TsThread::Return: {                      if((r=thrd.wait_not(Wy_Thread::Active))!=Ok) {                        WY_THROW(r);                      }                      tm= Wy::now()-TM0;                      if(thrd.thread_state()!=Wy_Thread::Stopped) {                        WY_THROW( WyRet() );                      }                      if(thrd.exitcode()!=ec) {                        WY_THROW( thrd.exitcode() );                      }                      if(((tm-delay).abs())>WyTimeSpec(0,50000000)) {                        Wy::cerr << "Inaccurate delay: > 0.05 second\n";                        //WY_THROW( WyRet() );                      }                      if((r=thrd.reset())!=Ok) {                        WY_THROW(r);                      }                      if((r=chk_default_attr(thrd))!=Ok) {                        WY_THROW(r);                      }                   }; break;   case TsThread::Exit: {                      if((r=thrd.wait_not(Wy_Thread::Active))!=Ok) {                        WY_THROW(r);                      }                      tm= Wy::now()-TM0;                      if(thrd.thread_state()!=Wy_Thread::Stopped) {                        WY_THROW( WyRet() );                      }                      if(thrd.exitcode()!=ec) {                        WY_THROW( thrd.exitcode() );                      }                      if(((tm-delay).abs())>WyTimeSpec(0,50000000)) {                        Wy::cerr << "Inaccurate delay: > 0.05 second\n";                        //WY_THROW( WyRet() );                      }                      if((r=thrd.reset())!=Ok) {                        WY_THROW(r);                      }                      if((r=chk_default_attr(thrd))!=Ok) {                        WY_THROW(r);                      }                   }; break;   case TsThread::Cancel: {                      Wy::sleep(delay);                      if((r=thrd.cancel())!=Ok) {                        WY_THROW(r);                      }                      if((r=thrd.wait_not(Wy_Thread::Active))!=Ok) {                        WY_THROW(r);                      }                      tm= Wy::now()-TM0;                      if(thrd.thread_state()!=Wy_Thread::Stopped) {                        WY_THROW( WyRet() );                      }                      if(thrd.exitcode()!=ec) {                        WY_THROW( thrd.exitcode() );                      }                      if(((tm-delay).abs())>WyTimeSpec(0,50000000)) {                        Wy::cerr << "Inaccurate delay: > 0.05 second\n";                        //WY_THROW( WyRet() );                      }                      if((r=thrd.reset())!=Ok) {                        WY_THROW(r);                      }                      if((r=chk_default_attr(thrd))!=Ok) {                        WY_THROW(r);                      }                   }; break;   case TsThread::Reset: {                      Wy::sleep(delay);                      if((r=thrd.reset())!=Ok) {                        WY_THROW(r);                      }                      tm= Wy::now()-TM0;                      if(((tm-delay).abs())>WyTimeSpec(0,50000000)) {                        Wy::cerr << "Inaccurate delay: > 0.05 second\n";                        //WY_THROW( WyRet() );                      }                      if((r=chk_default_attr(thrd))!=Ok) {                        WY_THROW(r);                      }                   }; break;   default:        WY_TERMINATE(""); }; // chk reset() again (diff code path) if((r=thrd.reset())!=Ok) {   WY_THROW(r); } if((r=chk_default_attr(thrd))!=Ok) {   WY_THROW(r); }}catch(const WyRet& e) { Wy::cerr << Wy::wrd(e) << '\n'; throw;}catch(...) { throw;};static void ck_thread_a(void){ const WyTimeSpec TDelay(0,500000000);   // 0.5 sec WyRet r; if(Wy_Thread::max_threads()!=512) {   WY_THROW( WyRet() ); } // chk stopped by return {   TsThread thrd1(TsThread::Return,Wym_EIO,TDelay);   ck_thread_0(thrd1,TsThread::Return,Wym_EIO,TDelay); } // chk stopped by exit {   TsThread thrd1(TsThread::Exit,Wym_EINVAL,TDelay);   ck_thread_0(thrd1,TsThread::Exit,Wym_EINVAL,TDelay); } // chk stopped by cancel {   TsThread thrd1(TsThread::Cancel,Wym_ETHRDCAN,TDelay);   ck_thread_0(thrd1,TsThread::Cancel,Wym_ETHRDCAN,TDelay); } // chk stopped by reset {   TsThread thrd1(TsThread::Reset,WyRet(),TDelay);   ck_thread_0(thrd1,TsThread::Reset,WyRet(),TDelay); } // chk stopped by destroy TsThread object {   {     TsThread thrd1(TsThread::Reset,WyRet(),TDelay);     if((r=thrd1.begin())!=Ok) {       WY_THROW( WyRet() );     }   } }};// non Wy_Thread created thread function//static void* nw_thread_routine(void* arg){ // chk tbase_ptr() if(Wy_Thread::tbase_ptr()!=0) {   WY_TERMINATE(""); } // chk thread_self() const ::pthread_t SelfID=::pthread_self(); if(Wy_ThreadID::_thread_equal(Wy_Thread::thread_self(),SelfID)==false) {   WY_THROW( WyRet() ); } if(::pthread_equal(Wy_Thread::thread_self()._pthread_id(),SelfID)==0) {   WY_THROW( WyRet() ); } // chk cancel_point(), just verify available Wy_Thread::cancel_point(); // chk exit(WyRet) Wy_Thread::exit( WyRet(Wym_E41) );};// chk some static member in none Wy_Thread created thread//static void ck_thread_nwy(void){ pthread_t tid; void* tres; int v; if((v=::pthread_create(&tid,NULL,nw_thread_routine,NULL))!=0) {   WY_THROW( WyRet(WyReply(v)) ); } if((v=::pthread_join(tid, &tres))!=0) {   WY_THROW( WyRet(WyReply(v)) ); } if((int)tres!=Wym_E41->c_repcode()) {   WY_THROW( WyRet() ); }};//-------------------// HThread runs ck_thread_a in tmain()//class HThread : public Wy_Thread {  public:    HThread() : Wy_Thread() {};    ~HThread() throw() { Wy_Thread::tmain_close(); };  protected:    WyRet tmain(void) {         ck_thread_a();         return(Ok);       };};static WyRet exaust_threads(void){ const WyTimeSpec TDelay(0,10000000);   // 0.01 sec WyRet r; TsThread thrd1(TsThread::Cancel,Wym_ETHRDCAN,WyTimeSpec(1,0)); if((r=thrd1.begin())!=Ok) {   WY_RETURN(r); } TsThread thrd2(TsThread::Return,Wym_EIO,TDelay); if((r=thrd2.begin())!=Ok) {   WY_RETURN(r); } TsThread thrd3(TsThread::Exit,Wym_EINVAL,TDelay); if((r=thrd3.begin())!=Ok) {   WY_RETURN(r); } return exaust_threads();};static const WyStr chdr(                  "+---------------+\n"                  "| main() caught:|\n"                  "+---------------+\n");int main(void) throw()try { WyRet r; Wy::cout << "Checking wy_thread.cpp, basic ...\n"; if(WyStr(Wy_Thread::class_name)!="Wy_Thread") {   WY_THROW(WyRet() ); } #ifdef WY_DEBUG   if(wy_created_cnt!=wy_joined_cnt) {     WY_THROW( WyRet() );   } #endif chk_threadid(); // chk main thread id {  const ::pthread_t SelfID=::pthread_self();  if(Wy_ThreadID::_thread_equal(Wy_Thread::wy_main_thrd_id,SelfID)==false) {    WY_THROW( WyRet() );  }  if(::pthread_equal(Wy_Thread::wy_main_thrd_id._pthread_id(),SelfID)==0) {    WY_THROW( WyRet() );  }  Wy::cout << "Wy::wrd(Wy_ThreadID())=\"" << Wy::wrd(Wy_ThreadID()) << "\"\n"; } // chk ck_thread_a() {   if(Wy_Thread::active_threads()!=0) {     WY_THROW( WyRet() );   }   ck_thread_a();   if(Wy_Thread::active_threads()!=0) {     Wy::cerr << "active_threads()=" << Wy_Thread::active_threads() << '\n';     WY_THROW( WyRet() );   }   #ifdef WY_DEBUG     if(wy_created_cnt!=wy_joined_cnt) {       WY_THROW( WyRet() );     }   #endif } // chk ck_thread_a() concurrently in different threads {   const size_t Num_HThreads=20;   HThread ht[Num_HThreads];   for(size_t i=0; i< Num_HThreads; ++i) {     if((r=ht[i].begin())!=Ok) {       WY_THROW(r);     }     if((r=ht[i].begin())!=Wym_EBADF) {       WY_THROW(r);     }   }   for(size_t i=0; i< Num_HThreads; ++i) {     if((r=ht[i].wait_not(Wy_Thread::Active))!=Ok) {       WY_THROW(r);     }   }   if(Wy_Thread::active_threads()!=0) {     WY_THROW( WyRet() );   } } // chk some static functions in non Wy_Thread created thread ck_thread_nwy(); // chk thread exausted r=exaust_threads(); if((r!=Wym_EAGAIN)&&(r!=Wym_ENOMEM)    &&(r!=Wym_ENFILE)       // on SUSE10 this can occur (g++ v4.03)   ) {   WY_THROW(r); } #ifdef WY_DEBUG   if(wy_created_cnt!=wy_joined_cnt) {     WY_THROW( WyRet() );   }   Wy::cout << wy_created_cnt << " threads have been created\n";   // for now 125 is correct   Wy::cout << wy_act_max << " maximal active threads\n"; #endif Wy::cout << "Checked Ok\n"; return(0);}catch(const WyRet& e) { Wy::cerr << chdr << Wy::wrd(e) << '\n'; return(-1);}catch(const std::exception& e) { Wy::cerr << chdr << "std::exception\n"; return(-1);}catch(...) { Wy::cerr << chdr << "unidentified stack unwound\n"; return(-1);};

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -