您的位置:首页 > 其它

POSIX pthread线程库的封装-主动对象

2009-02-25 13:56 363 查看
// oamRunner.h 对POSIX pthread 线程库进行面向对象封装

#ifndef OAMRUNNER_H_
#define OAMRUNNER_H_

////////////////////////////////////////////////////////////////////////////////
/// @file oamRunner.h
/// @brief This file contains the OamRunner class declaration.
///
/// Related files: The implementation is in oamRunner.cc
/// Other related files are:
///
/////////////////////////////////////////////////////////////////////////////////

#include <pthread.h>

class OamRunner;

/////////////////////////////////////////////////////////////////////////////////
/// @class OamThreadRunner
///
/// Description: The ThreadRunner class is the helper of the Runner class
///
/////////////////////////////////////////////////////////////////////////////////
class OamThreadRunner
{
public:
// the definition of the thread status
enum
{
RUN,
PEND,
STOP
};

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamThreadRunner::OamThreadRunner.
///
/// @brief Constructor
///
/////////////////////////////////////////////////////////////////////////////////
OamThreadRunner();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamThreadRunner::~OamThreadRunner.
///
/// @brief Destructor
///
/////////////////////////////////////////////////////////////////////////////////
virtual ~OamThreadRunner();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamThreadRunner::stop.
///
/// @brief Method to stop the thread.
///
/// @returns - true if OK, false if error.
///
/////////////////////////////////////////////////////////////////////////////////
bool stop();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamThreadRunner::start.
///
/// @brief Method to start the thread.
///
/// @param runner - input - Runner object pointer.
///
/// @returns - true if OK, false if error.
///
/////////////////////////////////////////////////////////////////////////////////
bool start(OamRunner * runner);

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamThreadRunner::suspend.
///
/// @brief Method to suspend the thread.
///
/// @returns - true if OK, false if error.
///
/////////////////////////////////////////////////////////////////////////////////
bool suspend();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamThreadRunner::resume.
///
/// @brief Method to resume the thread.
///
/// @returns - true if OK, false if error.
///
/////////////////////////////////////////////////////////////////////////////////
bool resume();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamThreadRunner::wait.
///
/// @brief Method to wait the thread.
///
/// @returns - true if OK, false if error.
///
/////////////////////////////////////////////////////////////////////////////////
bool wait();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamThreadRunner::isRunning.
///
/// @brief Method to check the status of the thread.
///
/// @returns - true if running, false if not running.
///
/////////////////////////////////////////////////////////////////////////////////
bool isRunning();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamThreadRunner::self.
///
/// @brief Method to get the id of the thread.
///
/// @returns - the thread id.
///
/////////////////////////////////////////////////////////////////////////////////
pthread_t self();

private:
static void * threadFunc(void * args);

// the thread id
pthread_t tid_m;

// the status of the thread
int status_m;
};

/////////////////////////////////////////////////////////////////////////////////
/// @class OamRunner
///
/// Description: The OamRunner class is the thread interface which is provided to the
/// application.
///
/////////////////////////////////////////////////////////////////////////////////
class OamRunner
{
friend class OamThreadRunner;

public:
/////////////////////////////////////////////////////////////////////////////////
/// Name: OamRunner::OamRunner.
///
/// @brief Constructor
///
/////////////////////////////////////////////////////////////////////////////////
OamRunner();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamRunner::~OamRunner.
///
/// @brief Destructor
///
/////////////////////////////////////////////////////////////////////////////////
virtual ~OamRunner();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamRunner::stop.
///
/// @brief Method to stop the thread.
///
/// @returns - true if OK, false if error.
///
/////////////////////////////////////////////////////////////////////////////////
virtual bool stop();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamRunner::start.
///
/// @brief Method to start the thread.
///
/// @returns - true if OK, false if error.
///
/////////////////////////////////////////////////////////////////////////////////
virtual bool start();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamRunner::suspend.
///
/// @brief Method to suspend the thread.
///
/// @returns - true if OK, false if error.
///
/////////////////////////////////////////////////////////////////////////////////
virtual bool suspend();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamRunner::resume.
///
/// @brief Method to resume the thread.
///
/// @returns - true if OK, false if error.
///
/////////////////////////////////////////////////////////////////////////////////
virtual bool resume();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamRunner::wait.
///
/// @brief Method to wait the thread.
///
/// @returns - true if OK, false if error.
///
/////////////////////////////////////////////////////////////////////////////////
virtual bool wait();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamRunner::isRunning.
///
/// @brief Method to check the status of the thread.
///
/// @returns - true if running, false if not running.
///
/////////////////////////////////////////////////////////////////////////////////
virtual bool isRunning();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamRunner::self.
///
/// @brief Method to get the id of the thread.
///
/// @returns - the thread id.
///
/////////////////////////////////////////////////////////////////////////////////
pthread_t self();

protected:

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamRunner::run.
///
/// @brief this is implemented by the application, it is the thread method.
///
/// @returns - this could be designated by the application.
///
/////////////////////////////////////////////////////////////////////////////////
virtual int run();

private:

// the object of the runner helper.
OamThreadRunner runner_m;
};

#endif

// oamTask.h 利用oamRunner实现主动对象类

#ifndef OAMTASK_H_
#define OAMTASK_H_

////////////////////////////////////////////////////////////////////////////////
/// @file oamTask.h
/// @brief This file contains the OamTask class declaration.
///
/// Related files: The implementation is in oamTask.cc
/// Other related files are:
///
/////////////////////////////////////////////////////////////////////////////////

#include "oamRunner.h"

/////////////////////////////////////////////////////////////////////////////////
/// @class CommonData
///
/// Description: The CommonData class is used to store the raw data.
///
/////////////////////////////////////////////////////////////////////////////////
class CommonData
{
public:
/////////////////////////////////////////////////////////////////////////////////
/// Name: CommonData::CommonData
///
/// @brief Constructor
///
/////////////////////////////////////////////////////////////////////////////////
CommonData();

/////////////////////////////////////////////////////////////////////////////////
/// Name: CommonData::CommonData
///
/// @brief Constructor
///
/// @param rawData - input - the buffer address
///
/// @param length - input - the length of the rawData
///
/////////////////////////////////////////////////////////////////////////////////
CommonData(char * rawData , int length);

/////////////////////////////////////////////////////////////////////////////////
/// Name: CommonData::~CommonData
///
/// @brief Destructor
///
/////////////////////////////////////////////////////////////////////////////////
virtual ~CommonData();

/////////////////////////////////////////////////////////////////////////////////
/// Name: CommonData::getLength
///
/// @brief Method to get the length of the raw data
///
/// @returns - the length of the raw data.
///
/////////////////////////////////////////////////////////////////////////////////
int getLength() const;

/////////////////////////////////////////////////////////////////////////////////
/// Name: CommonData::setLength
///
/// @brief Method to set the length of the raw data
///
/// @param length - input - The length of the raw data.
///
/////////////////////////////////////////////////////////////////////////////////
void setLength(int length);

/////////////////////////////////////////////////////////////////////////////////
/// Name: CommonData::getData
///
/// @brief Method to get the raw data
///
/// @returns - the pointer of the raw data.
///
/////////////////////////////////////////////////////////////////////////////////
char * getData() const;

/////////////////////////////////////////////////////////////////////////////////
/// Name: CommonData::setData
///
/// @brief Method to set the raw data
///
/// @param rawData - input - The pointer of the raw data.
///
/////////////////////////////////////////////////////////////////////////////////
void setData(char * rawData);

private:
// the length of the raw data
int length_m;

// the pointer of the raw data
char * rawData_m;
};

/////////////////////////////////////////////////////////////////////////////////
/// @class OamTask
///
/// Description: The OamTask class is the active object class
///
/////////////////////////////////////////////////////////////////////////////////

class OamTask:public OamRunner
{
public:
/////////////////////////////////////////////////////////////////////////////////
/// Name: OamTask::OamTask
///
/// @brief Constructor
///
/////////////////////////////////////////////////////////////////////////////////
OamTask();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamTask::~OamTask
///
/// @brief Destructor
///
/////////////////////////////////////////////////////////////////////////////////
virtual ~OamTask();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamTask::initialize
///
/// @brief Method to initialize the oam task
///
/// @returns - 0 if success, else -1.
///
/////////////////////////////////////////////////////////////////////////////////
int initialize();

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamTask::putq
///
/// @brief Method to put the data into the queue
///
/// @param commonData - input - the common data object which will be enqueue.
///
/// @returns - 0 if success, else -1.
///
/////////////////////////////////////////////////////////////////////////////////
int putq(CommonData & commonData);

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamTask::getq
///
/// @brief Method to put the data into the queue
///
/// @param commonData - input - the common data reference
///
/// @param commonData - output - the common data which carries the data
///
/// @returns - 0 if success, else -1.
///
/////////////////////////////////////////////////////////////////////////////////
int getq(CommonData & commonData);

protected:
// the logic handler which is implemented by the derived-class
virtual int handle(CommonData * pData);

private:
// the definition pf the pipe type.
enum
{
FD_READ = 0,
FD_WRITE,
FD_MAX
};

// the thread method.
virtual int run();

// the FD of the queue.
int queue_m[FD_MAX];
};

#endif

// oamRunner.cc
///////////////////////////////////////////////////////////////////////////////////
///
/// Related files: The definition is in oamRunner.h
/// Other related files are:
///
///////////////////////////////////////////////////////////////////////////////////

#include "oamRunner.h"

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
OamRunner::OamRunner(){}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
OamRunner::~OamRunner(){}

//--------------------------------------------------------------------
// This is a protected API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
int OamRunner::run()
{
return 0;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamRunner::stop()
{
return runner_m.stop();
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamRunner::start()
{
return runner_m.start(this);
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamRunner::suspend()
{
return runner_m.suspend();
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamRunner::resume()
{
return runner_m.resume();
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamRunner::wait()
{
return runner_m.wait();
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
pthread_t OamRunner::self()
{
return runner_m.self();
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamRunner::isRunning()
{
return runner_m.isRunning();
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
OamThreadRunner::OamThreadRunner():tid_m(0) , status_m(STOP)
{}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
OamThreadRunner::~OamThreadRunner()
{
status_m = STOP;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamThreadRunner::stop()
{
if (status_m != STOP)
{
pthread_cancel(this->self());
status_m = STOP;

return true;
}

return false;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamThreadRunner::start(OamRunner * runner)
{
if (status_m == STOP &&
pthread_create(&tid_m , 0 , OamThreadRunner::threadFunc , runner) != 0)
{
return false;
}

if (status_m == STOP)
{
status_m = RUN;
}

return true;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamThreadRunner::suspend()
{
return true;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamThreadRunner::resume()
{
return true;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamThreadRunner::wait()
{
return ((pthread_join(this->self() , 0) == 0)?true:false);
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
pthread_t OamThreadRunner::self()
{
return tid_m;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamRunner.h for details.
//--------------------------------------------------------------------
bool OamThreadRunner::isRunning()
{
pthread_testcancel();

return (status_m == STOP? false:true);
}

/////////////////////////////////////////////////////////////////////////////////
/// Name: OamThreadRunner::threadFunc
///
/// @brief This is the thread method, pthread will run this method when
/// it is started.
///
/// @param args - input - Parameter which will be passed by the pthread_create.
//
/// @returns - if the thread is exit, return 0, else some error occur.
///
/////////////////////////////////////////////////////////////////////////////////
void * OamThreadRunner::threadFunc(void * args)
{
OamRunner * runner = (OamRunner *)args;

runner->run();

return 0;
}

// oamTask.cc
///////////////////////////////////////////////////////////////////////////////////
/// Related files: The definition is in oamTask.h
/// Other related files are:
///////////////////////////////////////////////////////////////////////////////////

#include "oamTask.h"

#include <unistd.h>
#include <string.h>

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
CommonData::CommonData():length_m(0) , rawData_m(0)
{}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
CommonData::CommonData(char * rawData , int length)
:length_m(length) , rawData_m(rawData)
{}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
CommonData::~CommonData()
{
rawData_m = 0;
length_m = 0;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
int CommonData::getLength() const
{
return length_m;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
void CommonData::setLength(int length)
{
length_m = length;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
char * CommonData::getData() const
{
return rawData_m;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
void CommonData::setData(char * rawData)
{
rawData_m = rawData;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
OamTask::OamTask()
{
queue_m[FD_READ] = -1;
queue_m[FD_WRITE] = -1;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
OamTask::~OamTask()
{
if (queue_m[FD_READ] != -1)
{
close(queue_m[FD_READ]);
queue_m[FD_READ] = -1;
}

if (queue_m[FD_WRITE] != -1)
{
close(queue_m[FD_WRITE]);
queue_m[FD_WRITE] = -1;
}
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
int OamTask::initialize()
{
if (pipe(queue_m) == -1)
{
return -1;
}

return 0;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
int OamTask::putq(CommonData & commonData)
{
int length = commonData.getLength();
char * data = commonData.getData();

if (length <= 0 || data == 0)
{
return -1;
}

if (write(queue_m[FD_WRITE] , &length , sizeof(int)) != sizeof(int))
{
return -1;
}

if (write(queue_m[FD_WRITE] , data , length) != length)
{
return -1;
}

return 0;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
int OamTask::getq(CommonData & commonData)
{
int length = 0;
if (read(queue_m[FD_READ] , &length , sizeof(int)) != sizeof(int))
{
return -1;
}

if (length <= 0)
{
return -1;
}

char * data = new char[length];
memset(data , 0x00 , length);

if (read(queue_m[FD_READ] , data , length) != length)
{
return -1;
}

commonData.setLength(length);
commonData.setData(data);

return 0;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
int OamTask::handle(CommonData * pData)
{
return 0;
}

//--------------------------------------------------------------------
// This is a public API. Refer to oamTask.h for details.
//--------------------------------------------------------------------
int OamTask::run()
{
while (isRunning())
{
CommonData commonData;
if (getq(commonData) == -1)
{
return -1;
}

if (handle(&commonData) == -1)
{
char * data = commonData.getData();
delete [] data;
data = 0;

return -1;
}

char * data = commonData.getData();
delete [] data;
data = 0;
}

return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: