15,471
社区成员
发帖
与我相关
我的任务
分享
...
if(nCount>64 && nCount<=128)
{
hGroupEvent.GroupEvent2.nEvent=nCount-64;
memcpy(hGroupEvent.GroupEvent2.reg_event,lpHandles+64,hGroupEvent.GroupEvent2.nEvent*sizeof(void *));
hGroupEvent.GroupEvent1.nEvent=64;
memcpy(hGroupEvent.GroupEvent1.reg_event,lpHandles,hGroupEvent.GroupEvent1.nEvent*sizeof(void *));
SetEvent(hWFMO.g_hEvent1);
SetEvent(hWFMO.g_hEvent2);
...
WaitForSingleObject(hWFMO.g_hRegEvent,INFINITE);
... //继续处理
...
static void __stdcall WFMO_Thread1(void)
{
while(IsStart)
{
WaitForSingleObject(hWFMO.g_hEvent1,INFINITE);
hWFMO.ret=WaitForMultipleObjects(hGroupEvent.GroupEvent1.nEvent,hGroupEvent.GroupEvent1.reg_event,FALSE, INFINITE);
hGroupEvent.GroupEvent1.nEvent=0;
SetEvent(hWFMO.g_hRegEvent);
}
}
static void __stdcall WFMO_Thread2(void)
{
while(IsStart)
{
WaitForSingleObject(hWFMO.g_hEvent2,INFINITE);
...
hWFMO.ret=WaitForMultipleObjects(.....);
SetEvent(hWFMO.g_hRegEvent);
}
}
...
WaitForMultiEx.h
DWORD WINAPI WaitForMultipleExpressions(DWORD nExpObjects,const HANDLE* phExpObjects,DWORD dwMilliSeconds);
WaitForMultiEx.cpp
#define _WIN32_WINNT 0x0403
#include<windows.h>
#include<process.h>
#include<malloc.h>
#include "WaitForMultiEx.h"
#define ERROR_SELECT_TOO_LONG 32766
#define ERROR_TOO_MANY_SELECTS 32767
typedef struct{
DWORD nExpObjects;
HANDLE *phExpObjects;
}EXPRESSION,*LPEXPRESSION;
unsigned __stdcall WFME_ExpressionThread(void *lpParam)
{
//wait for all of kernel objects in a expression to be signaled or a APC to be added to APC Queue in a thread
LPEXPRESSION lpExpression=(LPEXPRESSION)lpParam;
WaitForMultipleObjectsEx(lpExpression->nExpObjects,lpExpression->phExpObjects,true,INFINITE,true);
return 0;
}
void CALLBACK WFME_ExpressionAPC(ULONG_PTR dwParam)
{
//only add it to a thread`s APC Queue to stop thread`s waiting
}
DWORD WINAPI WaitForMultipleExpressions(DWORD nExpObjects,const HANDLE* phExpObjects,DWORD dwMilliSeconds)
{
//wait for a group of expressions
//if one expression which a group of kernel objects in is signaled,the function return
//if the first expressiont is satisfied,the function return WAIT_OBJECT_0,
//if the second expression is satisfied,the function return WAIT_OBJECT_1,
//and so on...
//the format of the handle array named phExpObjects:
//1.each expression is separated by NULL
//2.it`s not more than 63 object handles in a expression
//3.it`s not more than 64 expressions in the handle array
EXPRESSION Expressions[MAXIMUM_WAIT_OBJECTS];
HANDLE *phExpObjectsTmp,ahThreads[MAXIMUM_WAIT_OBJECTS];
//allocate the space on stack
phExpObjectsTmp=(HANDLE*)_alloca((nExpObjects+1)*sizeof(HANDLE));
CopyMemory(phExpObjectsTmp,phExpObjects,nExpObjects*sizeof(HANDLE));
phExpObjectsTmp[nExpObjects]=NULL;
DWORD dwRet=0;
DWORD NumExps=0,ExpsNum=0;
DWORD BeginPos=0,CurPos=0;
HANDLE hSemOnlyOne;
hSemOnlyOne=CreateSemaphore(NULL,1,1,NULL); //create a semaphore to add it to the NULL handle position in phExpObjectsTmp array
while(dwRet!=WAIT_FAILED&&CurPos<=nExpObjects){
//ReSolve the phExpObjectsTmp Array
while(phExpObjectsTmp[CurPos]!=NULL)
CurPos++;
phExpObjectsTmp[CurPos]=hSemOnlyOne;
Expressions[NumExps].phExpObjects=&phExpObjectsTmp[BeginPos];
Expressions[NumExps].nExpObjects=CurPos-BeginPos+1;
if(Expressions[NumExps].nExpObjects>MAXIMUM_WAIT_OBJECTS){
dwRet=WAIT_FAILED;
SetLastError(ERROR_SELECT_TOO_LONG);
}
BeginPos=++CurPos;
if(++NumExps>=MAXIMUM_WAIT_OBJECTS&&CurPos<=nExpObjects){
dwRet=WAIT_FAILED;
SetLastError(ERROR_TOO_MANY_SELECTS);
}
}
if(dwRet!=WAIT_FAILED){
//the format of the handle array named phExpObjects is correct
unsigned int dwThreadId;
for(ExpsNum=0;ExpsNum<NumExps;ExpsNum++)
ahThreads[ExpsNum]=(HANDLE)_beginthreadex(NULL,0,WFME_ExpressionThread,(void*)&Expressions[ExpsNum],0,&dwThreadId);
dwRet=WaitForMultipleObjects(NumExps,ahThreads,false,dwMilliSeconds); //wait for one of threads to be signaled
if(dwRet==WAIT_TIMEOUT){
dwRet=WaitForSingleObject(hSemOnlyOne,0);
if(dwRet==WAIT_TIMEOUT){
//one expression is satisfied
dwRet=WaitForMultipleObjects(NumExps,ahThreads,false,INFINITE);
}
else{
//no expression is satisfied
dwRet=WAIT_TIMEOUT;
}
}
for(ExpsNum=0;ExpsNum<NumExps;ExpsNum++){
//stop the rest threads` waiting by add APC to their APC Queues
if(dwRet==WAIT_TIMEOUT||(dwRet-WAIT_OBJECT_0)!=ExpsNum)
QueueUserAPC(WFME_ExpressionAPC,ahThreads[ExpsNum],0);
CloseHandle(ahThreads[ExpsNum]);
}
}
return dwRet;
}
HANDLE hEvent[] = {hExit, h1, h2, h3, h4};
while(1)
{
DWORD dwWait = WaitForMultipleObjects(_countof(hEvent), hEvent, FALSE, 0);
switch(dwWait)
{
case(WAIT_FAILED): //错误
{
ASSERT(0);
break;
}
case(WAIT_TIMEOUT)://no event signaled
{
break;
}
case(WAIT_OBJECT_0 + 0)://thread Exit event
{
return 1;
}
case(WAIT_OBJECT_0 + 1)://h1
{
//add your code
break;
}
case(WAIT_OBJECT_0 + 2)://h2
case(WAIT_OBJECT_0 + 3)://h3
case(WAIT_OBJECT_0 + 4)://h4
{
//add your code
break;
}
default:
{
break;
}
}
}