• 4063阅读
  • 0回复

pthread 与QThread混用,实现cancel功能 [复制链接]

上一主题 下一主题
离线yongjie
 

只看楼主 倒序阅读 楼主  发表于: 2013-12-19
QThread的好处是支持signal/slot。但是同步功能太差。terminate()一用,主程序也跟着死了。
试了一下与pthread混用,在windows/mingw32环境居然可以通过了!

win32上的pthread不支持UNIX上的signal机制,所以只能用pthread_cancel。大致方法如下:

static
void *pthread_worker(void *ptr)
{
    int last_state, last_type;
    pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, &last_state);
    pthread_setcanceltype(PTHREAD_CANCEL_DEFERRED, &last_type);
   //
   // real program logic, expensive operations!!
   // need to insert pthread_testcancel() inside the loop, etc.

   //
   mythread->finishFlag = true;
}

class MyThread : public QThread
{
  Q_OBJECT
    void run() Q_DECL_OVERRIDE;

public:
  bool cancelFlag;
  bool finishFlag;
}

MyThread::run()
{
     pthread_t thread_id;
     int ret = pthread_create(&thread_id, 0, pthread_worker,
                                 (void*)&threadArg);
     while (1) {
        void * statusp;
        if (cancelFlag) {
             pthread_cancel(thread_id);
             pthread_join(thread_id, &statusp);
             break;
       }
       if (finishFlag) {
            pthread_join(thread_id, &statusp);
            break;
        }
        usleep(100*1000);
    }
};

主程序要取消时,只是设置一下MyThread.cancelFlag,就可以了。
根据pthread文档,pthread_cancel好象会有一些问题。但pthread_join返回的值都是正常的!从主界面上接着做其它事也正常!

Linux上,必须用deferred,所以改成deferred模式。但要加一些pthread_testcancel()检查。


欢迎讨论或板砖。

快速回复
限100 字节
 
上一个 下一个