Raymond Chen 2008年06月06日
一位用户发现,如果将进程ID增加3,然后传递给OpenProcess
函数,该函数仍然能够成功执行。这是怎么一回事呢?
首先,我必须明确指出,您所观察到的现象是实现上的一种偶然结果,并非功能规范的一部分。您传递了故意错误的参数,您期望得到什么结果呢?这个问题的背景是“我们发现了这种行为,但我们无法解释”,而不是“我们正在使用这种技巧,希望得到确认它是否正确”。
事实上,您已经知道答案了。
- 为什么进程和线程ID是4的倍数?
- 内核句柄总是4的倍数
正如我们之前讨论的,为了便捷,Windows NT内核使用句柄管理器来分配进程和线程ID,而句柄管理器会忽略句柄的最低两位。因此,向进程ID增加3并不会影响进程ID到对象的映射。
这种机制是特定于基于Windows NT的内核的。基于Windows 95内核的Windows版本在映射进程ID到进程上采用了不同的机制,这个机制是严格不变的。如果您增加3,OpenProcess
函数会将您的进程ID视为无效并拒绝它。至于Windows CE如何处理这种情况,我就不得而知了。
再次强调,您在基于Windows NT的内核中观察到的行为只是一种实现上的偶然现象,随时都可能发生变化。谁知道呢,也许内核团队在阅读了这篇文章之后,会决定让OpenProcess
变得更加严格。
预先发布的Yuhong Bao评论:“在Windows 95中,进程ID是一个指向内部数据结构的指针,通过与一个常量进行异或操作来混淆。”