【问题标题】:Calling SetEvent with an invalid handle [closed]使用无效句柄调用 SetEvent [关闭]
【发布时间】:2012-10-03 23:13:16
【问题描述】:

我有一个应用程序,其中一个线程调用 SetEvent,另一个线程等待该事件。但是,从未调用过 CreateEvent。

SetEven 返回 false (ERROR_INVALID_HANDLE),WaitForSingleObject 返回 WAIT_FAILED

昨天,我们提交了一些明显不相关的内容:.rc 中的两行代码从工具栏中删除了按钮。

突然,在 realease-XP-32 上,WaitForSingleObject 返回 WAIT_TIMEOUT

但我想知道:

1- 为什么资源中的提交(显然不相关)确实改变了 WaitForSingleObject 的返回?

2- 当我从 Visual Studio 启动应用程序 (XP32) 时,我得到的行为与直接启动应用程序时不同。 WaitForSingleObject() 返回 WAIT_FAILED 而不是超时。知道为什么吗?

【问题讨论】:

  • 未定义的行为是一件美好的事情......
  • 究竟什么是“WaitEvent”?让 WaitForSingleObject() 阻塞未初始化的句柄值并不是最大的谜。
  • 我刚刚编辑过,感谢您的注意:WaitForSingleObject

标签: c++ multithreading events memory initialization


【解决方案1】:

由于您从未调用过CreateEvent,因此您的SetEventWaitForSingleObject 使用的是未初始化的变量。未初始化变量的内容是不确定的,因此您最终将未知值传递给SetEventWaitForSingleObject。看来,对于旧代码,内存使用模式碰巧导致未初始化变量的值不是有效句柄的情况,所以你得到了ERROR_INVALID_HANDLE。进行更改后,内存使用模式发生了变化,现在未初始化变量的值恰好是有效句柄,因此WaitForSingleObject 函数尽职尽责地等待它。该句柄恰好引用了未发出信号的对象,因此WaitForSingleObject 调用超时并返回WAIT_FAILED

换句话说,看似无关的更改暴露了一个预先存在的错误。使用未初始化的数据可能会导致这样的非局部效应。

【讨论】:

    【解决方案2】:

    如果您正在执行 WaitForSingleObject(),那么该调用是否真的失败了?也许它也抛出了无效句柄错误,所以它看起来只是“接收事件”。也有可能在更改 RC 文件之前从未实际编译过损坏的 CreateEvent() 代码。无论如何,不​​看代码就无法判断。

    【讨论】:

    • 在 XP32 版本上,WaitForSingleObject 返回 WAIT_TIMEOUT。你是完全正确的,我会仔细检查以前版本的确切回报是多少。关于 CreateEvent,整个系统都没有调用该事件。
    • WaitForSingleObject 通常会失败。因为 WaitForSingleObject 然后返回一个 TIME_OUT,所以只有 xp32“具有未完成的提交”。
    猜你喜欢
    • 2019-04-21
    • 1970-01-01
    • 1970-01-01
    • 2018-06-20
    • 1970-01-01
    • 1970-01-01
    • 2013-06-17
    • 2019-08-23
    • 1970-01-01
    相关资源
    最近更新 更多