串口 WaitForMultipleObjects函数解释及其用法

本文详细解析了Windows API中的WaitForMultipleObjects函数,包括其参数含义、返回值解释以及通过实例展示了如何使用该函数等待多个内核对象。文章深入探讨了函数的工作原理及在实际编程中的应用。

转载自:http://hi.baidu.com/vtotrktzypbcdoq/item/f7ef8f1f173b5adfbe9042f2


函数原型:DWORD WaitForMultipleObjects(
DWORD nCount, // number of handles in array
CONST HANDLE *lpHandles, // object-handle array
BOOL bWaitAll, // wait option
DWORD dwMilliseconds // time-out interval
);

WaitForMultipleObjects函数用于等待多个内核对象,前两个参数分别为要等待的内核对象的个数和句柄数组指针。如果将第三个参数bWaitAll的值设为TRUE,等待的内核对象全部变成受信状态以后此函数才返回。否则,bWaitAll为0的话,只要等待的内核对象中有一个变成了受信状态,WaitForMultipleObjects就返回,返回值指明了是哪一个内核对象变成了受信状态。

实例一:

下面的代码说明了函数返回值的作用:

         HANDLE h[2];

         h[0] = hThread1;

         h[1] = hThread2;

         DWORD dw = ::WaitForMultipleObjects(2, h, FALSE, 5000);

         switch(dw)

         {       case WAIT_FAILED:

                            // 调用WaitForMultipleObjects函数失败(句柄无效?)

                            break;

                   case WAIT_TIMEOUT:

                            // 在5秒内没有一个内核对象受信

                            break;

                   case WAIT_OBJECT_0 + 0:

                            // 句柄h[0]对应的内核对象受信

                            break;

                   case WAIT_OBJECT_0 + 1:

                            // 句柄h[1]对应的内核对象受信

                            break;

         }

参数bWaitAll为FALSE的时候,WaitForMultipleObjects函数从索引0开始扫描整个句柄数组,第一个受信的内核对象将终止函数的等待,使函数返回。

实例二:

for(int i=0;i<6;i++)
{
   for(int j=0;j<10;j++)
   {
    theport[j].rmt_host=rmt_host;
    theport[j].p=port[i*10+j];
    theport[j].n=j;
    Thread[j]=AfxBeginThread(pScan,(LPVOID)&theport[j]);
    hThread[j]=Thread[j]->m_hThread;
    Sleep(1);
   }
   WaitForMultipleObjects(10,hThread,TRUE,120000);
}

注:线程退出后,即线程对象计数值变为0后,线程才会变为受信状态。


<think>好的,我现在需要解释C语言中WaitForSingleObject(hThread_Recv, INFINITE)这个函数用法。首先,我应该回忆一下WaitForSingleObject的基本作用,它是用于等待一个内核对象变成有信号状态的函数。参数有两个,第一个是句柄hThread_Recv,第二个是超时时间INFINITE。 接下来,要确定hThread_Recv的类型。用户提到的是hThread_Recv,看起来像是一个线程句柄。线程句柄在创建线程时由CreateThread函数返回,或者通过其他方式获取。当线程结束时,线程对象会变为有信号状态,所以WaitForSingleObject在这里的作用可能是等待这个线程结束。 然后,第二个参数是INFINITE,这是Windows API中定义的一个宏,通常值为0xFFFFFFFF。这个参数表示函数会无限等待,直到线程变为有信号状态,也就是线程结束为止。如果设置成其他数值,比如毫秒数,函数会在超时后返回,即使线程还未结束。 需要说明函数的返回值。当WaitForSingleObject成功等待到对象有信号时,返回WAIT_OBJECT_0。如果有错误发生,比如句柄无效,可能会返回WAIT_FAILED。但在这个调用中,用户使用了INFINITE,所以函数会一直阻塞,直到线程结束,不会因为超时而返回WAIT_TIMEOUT。 另外,需要注意线程句柄的正确性。如果hThread_Recv是一个无效的句柄,函数会失败。同时,调用WaitForSingleObject后,可能需要关闭句柄,避免资源泄漏,但这一步通常在创建线程后由CloseHandle来处理,具体取决于线程的创建方式。 还要考虑多线程编程中的常见问题。比如,主线程调用WaitForSingleObject等待子线程结束,这样可以保证主线程在子线程完成后继续执行后续操作。这对于同步线程之间的操作非常有用。 可能的应用场景包括:等待一个网络接收线程完成接收任务,或者在程序退出前确保所有子线程都已正确终止。使用INFINITE参数时,需要确保被等待的线程确实会结束,否则程序会永远阻塞在那里,造成死锁。 需要提醒用户注意死锁风险。如果被等待的线程因为某些原因无法正常结束,比如陷入死循环或者等待其他资源,那么调用WaitForSingleObject的线程也会一直被阻塞,导致整个程序无法继续执行。因此,在不确定线程是否能安全结束的情况下,可能需要设置一个合理的超时时间,而不是使用INFINITE。 另外,关于线程句柄的释放问题。如果多个线程引用了同一个句柄,需要确保在不再需要时正确关闭句柄,避免资源泄漏。通常,每个线程句柄在创建后,当不再需要时应该调用CloseHandle来关闭,但要注意不要在还有线程在使用该句柄时关闭它。 总结一下,这个函数调用的目的是让当前线程等待hThread_Recv所代表的线程结束,无限期等待直到该线程终止。这是多线程编程中常用的同步机制,确保线程执行的顺序性或资源的正确释放。</think>在C语言中,`WaitForSingleObject(hThread_Recv, INFINITE);` 是Windows API中用于线程同步的关键函数。以下是逐步解释: --- ### **1. 函数作用** - **核心功能**:阻塞当前线程,直到指定的内核对象(如线程、进程、事件等)变为**有信号状态**。 - **应用场景**:常用于等待一个线程结束(通过线程句柄),或等待其他同步对象(如互斥锁、信号量)。 --- ### **2. 参数解析** - **`hThread_Recv`** - 类型:`HANDLE`(句柄) - 说明:一个线程句柄,通常由 `CreateThread` 或类似函数返回。当该线程终止时,其句柄会自动变为有信号状态。 - **`INFINITE`** - 类型:`DWORD`(超时时间,单位:毫秒) - 说明:表示无限等待。若设为具体数值(如 `1000`),则最多等待1秒后超时返回。 --- ### **3. 返回值** - **成功时**:返回 `WAIT_OBJECT_0`,表示目标对象已变为有信号状态。 - **超时**:返回 `WAIT_TIMEOUT`(仅当第二个参数为非 `INFINITE` 时可能)。 - **错误时**:返回 `WAIT_FAILED`,可通过 `GetLastError()` 获取错误代码。 --- ### **4. 典型用法** #### **示例:等待线程结束** ```c HANDLE hThread = CreateThread(/* 创建线程参数 */); // 主线程阻塞,直到hThread对应的线程结束 DWORD dwResult = WaitForSingleObject(hThread, INFINITE); if (dwResult == WAIT_OBJECT_0) { printf("线程已结束!\n"); } CloseHandle(hThread); // 关闭句柄释放资源 ``` --- ### **5. 注意事项** 1. **死锁风险** - 若被等待的线程因逻辑错误无法终止(如死循环),调用线程将**永久阻塞**。 - 建议在关键代码中添加超时机制(例如 `WaitForSingleObject(hThread, 5000)`)。 2. **句柄管理** - 需确保 `hThread_Recv` 是有效的线程句柄。 - 使用后应调用 `CloseHandle()` 释放资源,避免内存泄漏。 3. **多线程同步** - 结合其他同步机制(如互斥锁、事件)可实现复杂线程协作。 --- ### **6. 替代函数** - **`WaitForMultipleObjects`**:等待多个对象变为有信号状态。 - **`Sleep`**:单纯让当前线程休眠,不依赖对象信号。 --- ### **总结** `WaitForSingleObject(hThread_Recv, INFINITE);` 的作用是让当前线程暂停执行,直到 `hThread_Recv` 对应的线程结束。它是Windows多线程编程中实现同步的基础工具,需谨慎处理句柄和超时逻辑以避免阻塞问题。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值