1

我正在制作一项服务,它正在侦听登录事件。如果发生此事件,我的应用程序应启动一个新线程,该线程将完成工作。

我的问题是,每次登录事件发生时如何启动一个新线程,如果线程完成工作,则正确关闭它的句柄。我的问题是,我不知道会发生多少登录事件,所以我不能使用WaitForMultipleObjects,因为它的第一个参数是它应该等待的线程数。

while ( WaitForSingleObject( ghSvcStopEvent, 0 ) != WAIT_OBJECT_0 )
{
  DWORD dwEventFlags;
  BOOL bRes;

  // WTSWaitSystemEvent waits until a logon event ocurs
  bRes = WTSWaitSystemEvent( WTS_CURRENT_SERVER_HANDLE, WTS_EVENT_LOGON, &dwEventFlags );
  if ( dwEventFlags == WTS_EVENT_NONE )
  {
    ShowErrorText( "Cancelling waiting for logon event. Service shutting down.", 0, true );
  }
  if ( bRes )
  {
    // Someone has logged on
    HANDLE hThread = CreateThread( NULL, 0, ServiceWorkerThread, NULL, 0, &dwThreadID );
  }
  else
  {
    ShowErrorText( "WTSWaitSystemEvent failed.", GetLastError(), true );
  }
}//while

有人可以帮助我吗?

谢谢!

4

1 回答 1

0

如果您可以使用 C++11(从 VS2010 开始),那么您就是一个可以为您完成工作的使用条件变量

条件变量的概念是:一个允许线程一起通信的变量。如果你通知它,你会向插入它的其他线程发送一个信号

如果您对其执行 cv.wait(...) ,您将等待其他线程发出信号表明事情已经发生,然后再次测试您的状况。

这是一个例子

服务器.h

#include <condition_variable>
#include <mutex>

class CServer
{
    std::condition_variable & cv;
    std::mutex & mut;
    bool & flag;
public:
    ~CServer(void);
    CServer::CServer(std::condition_variable & cv,
                     std::mutex & mut,
                     bool & flag);

    CServer::CServer(CServer &);
    int Notify();
    int DisplayNotification();

    std::condition_variable & getCondVar(){return cv;}
    std::mutex & getMutex(){return mut;}
    bool & getFlag(){return flag;}
};

服务器.cpp

#include "Server.h"
#include <iostream>
using namespace std;





CServer::~CServer(void)
{
}

CServer::CServer(std::condition_variable & cv_,
                 std::mutex & mut_,
                 bool & flag_):
cv(cv_),
mut(mut_),
flag(flag_)
{

}

CServer::CServer(CServer &toCopy):
cv(toCopy.getCondVar()),
mut(toCopy.getMutex()),
flag(toCopy.getFlag())
{
    flag=false;
    cout<<"Copy constructor"<<std::endl;
}

int CServer::Notify()
{
    {
        std::lock_guard<std::mutex> lk(mut);
        flag=true;
        std::cout << "ready for notfication"<<endl;
    }
    cv.notify_one();
    return 0;
}

int CServer::DisplayNotification()
{
    // wait for the worker
    {
        std::unique_lock<std::mutex> lk(mut);
        cv.wait(lk, [this]{return this->getFlag();});
    }
    cout<<"Notification displayed"<<endl;
    return 0;
}

客户端.h

#include <chrono>
#include "Server.h"
class CClient
{
    CServer & serv;
    std::chrono::seconds sleepTime;
    bool finishedWork;
public:
    CClient(CServer & serv, 
            std::chrono::seconds sleepTime);
    ~CClient(void);
    int work();
};

客户端.cpp

#include "Client.h"
#include <thread>
using namespace std;


CClient::CClient(CServer & serv_,
                 std::chrono::seconds sleepTime_):
serv(serv_),
sleepTime(sleepTime_),
finishedWork(false)
{
}


CClient::~CClient(void)
{
}

int CClient::work()
{
    this_thread::sleep_for(sleepTime);
    finishedWork=true;
    serv.Notify();
    return 0;
}

主文件

#include "Client.h"
#include <thread>
using namespace std;

int main()
{
    std::chrono::seconds sleepTime=std::chrono::seconds(10);

    //create client and server
    condition_variable cv;
    mutex mut;
    bool flag=false;

    CServer serv(cv,mut, flag);
    CClient cli(serv,sleepTime);

    //thread with the server
    thread thServ(&CServer::DisplayNotification,serv);

    ////thread with the client
    thread thCli (&CClient::work,cli);

    ////join threads
    thServ.join();
    thCli.join();
    return 0;
}

有什么问题可以问我

希望有帮助

于 2014-01-27T20:50:27.303 回答