SleepEx 是否保证在超时之前调用所有挂起的完成回调

Does SleepEx guarantee that all pending completion callbacks get called before timeout?

本文关键字:挂起 回调 调用 是否 超时 SleepEx      更新时间:2023-10-16

我有一个使用重叠IO进行网络通信的C++程序。主线程有一个调用SleepEx(5, true);的循环。还有两个TCP套接字。我假设在可警报等待期间调用完成回调。还假设当SleepEx被调用时,我的两个TCP连接都收到了一些数据。现在的问题是,如果第一次完成回调的时间超过 5 毫秒会发生什么?SleepEx是在调用第一个回调后返回,还是也调用第二个回调?换句话说,SleepEx是否保证调用所有计划的完成回调?这并不清楚,因为文档说当至少有一个事件满足时,它将返回......

您的代码不得假定在 SleepEx() 返回之前将调用两个 APC。 相反,它不能假定不会仅仅因为指定的等待期已过期而调用挂起的 APC。

您可以依赖的唯一行为是,如果一个或多个 APC 处于挂起状态,则至少将执行一个。

一般来说,最佳做法是在循环中等待 APC,而不执行任何其他操作,在等待中使用无限超时。 如果您需要定期执行某些操作,则可以使用可等待计时器定期生成 APC。

或者,您可以使用 WaitForSingleObjectEx() 或 WaitForMultipleObjectsEx() 来检测何时触发了可等待计时器或其他同步对象,同时仍处理 APC。

但是,如果必须执行某些无法在 APC 中处理或由同步对象触发的定期操作,则可以使用嵌套循环:内部循环除了重复调用等待之外什么都不做(超时期限减少循环已经运行的时间),外部循环执行定期操作。

如果必须执行一些无法被挂起的 APC 延迟的定期操作,则需要在单独的线程中执行此操作。 请注意,由于 Windows 不是实时操作系统,因此您仍然无法保证任何给定的操作将在任何特定时间范围内发生,尽管您可以通过增加线程优先级来降低风险。