Main Page | Class Hierarchy | Alphabetical List | Class List | File List | Class Members | Related Pages | Examples

ArThread_WIN.cpp

00001 /*
00002 MobileRobots Advanced Robotics Interface for Applications (ARIA)
00003 Copyright (C) 2004, 2005 ActivMedia Robotics LLC
00004 Copyright (C) 2006, 2007 MobileRobots Inc.
00005 
00006      This program is free software; you can redistribute it and/or modify
00007      it under the terms of the GNU General Public License as published by
00008      the Free Software Foundation; either version 2 of the License, or
00009      (at your option) any later version.
00010 
00011      This program is distributed in the hope that it will be useful,
00012      but WITHOUT ANY WARRANTY; without even the implied warranty of
00013      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00014      GNU General Public License for more details.
00015 
00016      You should have received a copy of the GNU General Public License
00017      along with this program; if not, write to the Free Software
00018      Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00019 
00020 If you wish to redistribute ARIA under different terms, contact 
00021 MobileRobots for information about a commercial version of ARIA at 
00022 robots@mobilerobots.com or 
00023 MobileRobots Inc, 19 Columbia Drive, Amherst, NH 03031; 800-639-9481
00024 */
00025 
00026 #include "ArExport.h"
00027 // ArThread.cc -- Thread classes
00028 
00029 
00030 #include "ariaOSDef.h"
00031 #include <list>
00032 #include "ArThread.h"
00033 #include "ArLog.h"
00034 #include "ArSignalHandler.h"
00035 
00036 
00037 static DWORD WINAPI run(void *arg)
00038 {
00039   ArThread *t=(ArThread*)arg;
00040   void *ret=NULL;
00041 
00042   if (t->getBlockAllSignals())
00043     ArSignalHandler::blockCommonThisThread();
00044 
00045   if (dynamic_cast<ArRetFunctor<void*>*>(t->getFunc()))
00046     ret=((ArRetFunctor<void*>*)t->getFunc())->invokeR();
00047   else
00048     t->getFunc()->invoke();
00049 
00050   return((DWORD)ret);
00051 }
00052 
00053 void ArThread::init()
00054 {
00055   ArThread *main;
00056   ThreadType pt;
00057   MapType::iterator iter;
00058 
00059   pt=GetCurrentThread();
00060 
00061   ourThreadsMutex.lock();
00062   if (ourThreads.size())
00063   {
00064     ourThreadsMutex.unlock();
00065     return;
00066   }
00067   main=new ArThread;
00068   main->myJoinable=true;
00069   main->myRunning=true;
00070   main->myThread=pt;
00071   ourThreads.insert(MapType::value_type(pt, main));
00072   ourThreadsMutex.unlock();
00073 }
00074 
00075 
00076 AREXPORT ArThread * ArThread::self()
00077 {
00078   ThreadType pt;
00079   MapType::iterator iter;
00080 
00081   ourThreadsMutex.lock();
00082   pt=GetCurrentThread();
00083   iter=ourThreads.find(pt);
00084   ourThreadsMutex.unlock();
00085 
00086   if (iter != ourThreads.end())
00087     return((*iter).second);
00088   else
00089     return(NULL);
00090 }
00091 
00092 AREXPORT void ArThread::cancelAll()
00093 {
00094   DWORD ret=0;
00095   MapType::iterator iter;
00096 
00097   ourThreadsMutex.lock();
00098   for (iter=ourThreads.begin(); iter != ourThreads.end(); ++iter)
00099     TerminateThread((*iter).first, ret);
00100   ourThreads.clear();
00101   ourThreadsMutex.unlock();
00102 }
00103 
00104 AREXPORT int ArThread::create(ArFunctor *func, bool joinable,
00105                   bool lowerPriority)
00106 {
00107   DWORD ret=0, err;
00108 
00109   myJoinable=joinable;
00110   myFunc=func;
00111   myRunning=true;
00112 
00113   myThread=CreateThread(0, 0, &run, this, 0, &ret);
00114   err=GetLastError();
00115   if (myThread == 0)
00116   {
00117     ArLog::log(ArLog::Terse, "ArThread::create: Failed to create thread.");
00118     return(STATUS_FAILED);
00119   }
00120   else
00121   {
00122     if (myName.size() == 0)
00123       ArLog::log(ourLogLevel, "Created anonymous thread with ID %d", 
00124          myThread);
00125     else
00126       ArLog::log(ourLogLevel, "Created %s thread with ID %d", myName.c_str(),
00127          myThread);
00128     ourThreadsMutex.lock();
00129     ourThreads.insert(MapType::value_type(myThread, this));
00130     ourThreadsMutex.unlock();
00131     if (lowerPriority)
00132       SetThreadPriority(myThread, THREAD_PRIORITY_IDLE);
00133     return(0);
00134   }
00135 }
00136 
00137 AREXPORT int ArThread::doJoin(void **iret)
00138 {
00139   DWORD ret;
00140 
00141   ret=WaitForSingleObject(myThread, INFINITE);
00142   if (ret == WAIT_FAILED)
00143   {
00144     ArLog::log(ArLog::Terse, "ArThread::doJoin: Failed to join on thread.");
00145     return(STATUS_FAILED);
00146   }
00147 
00148   return(0);
00149 }
00150 
00151 AREXPORT int ArThread::detach()
00152 {
00153   return(0);
00154 }
00155 
00156 AREXPORT void ArThread::cancel()
00157 {
00158   DWORD ret=0;
00159 
00160   ourThreadsMutex.lock();
00161   ourThreads.erase(myThread);
00162   ourThreadsMutex.unlock();
00163   TerminateThread(myThread, ret);
00164 }
00165 
00166 AREXPORT void ArThread::yieldProcessor()
00167 {
00168   Sleep(0);
00169 }
00170 
00171 
00172 AREXPORT void ArThread::threadStarted(void)
00173 {
00174   if (myName.size() == 0)
00175     ArLog::log(ourLogLevel, "Anonymous thread (%d) is running",
00176            myThread);
00177   else
00178     ArLog::log(ourLogLevel, "Thread %s (%d) is running", 
00179            myName.c_str(), myThread);
00180 }
00181 
00182 AREXPORT void ArThread::logThreadInfo(void)
00183 {
00184   if (myName.size() == 0)
00185     ArLog::log(ourLogLevel, "Anonymous thread (%d) is running",
00186            myThread);
00187   else
00188     ArLog::log(ourLogLevel, "Thread %s (%d) is running", 
00189            myName.c_str(), myThread);
00190 }

Generated on Tue Feb 20 10:51:41 2007 for Aria by  doxygen 1.4.0