处理程序的模块列表中有一个错误模块 "WebSocketModule"
Handler has a bad module "WebSocketModule" in its module list
在 64 位 Windows 10 和 IIS 10 上,我正在尝试开发和测试一个本机 HTTP 模块,该模块将充当一组特定脚本文件的 WebSockets 处理程序映射。这一切都是在以 RegisterModule() 开头的本机 C++ 中完成的。我没有使用 ASP.NET 的任何部分。
当我访问应该调用处理程序的 URL 时,我收到此响应:
HTTP Error 500.21 - Internal Server Error
Handler "QuadooWebSocket" has a bad module "WebSocketModule" in its module list
Detailed Error Information:
Module IIS Web Core
Notification ExecuteRequestHandler
Handler QuadooWebSocket
Error Code 0x8007000d
More Information:
IIS core does not recognize the module.
我使用 IIS 管理器设置处理程序映射,它在 applicationHost.config 文件中创建了一个条目。
<handlers accessPolicy="Read, Script">
<other_modules />
<add name="QuadooWebSocket" path="*.qws" verb="*" modules="WebSocketModule" scriptProcessor="E:\dev\projects\trunk\target\debug\ActiveQuadoo.dll" resourceType="File" preCondition="bitness32" />
</handlers>
在此之前,我使用 "Windows Features" 控制面板安装了对 WebSockets 的支持,它还在 applicationHost.config 文件中添加了一行。
<globalModules>
<other_modules />
<add name="WebSocketModule" image="%windir%\System32\inetsrv\iiswsock.dll" />
</globalModules>
当我将 Visual Studio 附加到 w3wp.exe 时,我的代码中的 none 断点被解析。 RegisterModule() 未被调用。 DllMain() 甚至没有被调用。我的模块还实现了 IActiveScript,并且 IIS 确实为经典 ASP 请求加载了我的模块。
我的代码被构建到 32 位模块中,我在 applicationHost.config 文件中有 enable32BitAppOnWin64="true"。这适用于经典 ActiveScript/ASP 环境,但是当使用预期通过 RegisterModule() 导出加载的代码时,此设置是否也适用?如果这不是问题,那么是否需要其他步骤来为 WebSockets 启用本机 HTTP 模块?
谢谢!
时隔近两年,我决定用这几天的时间再次研究这个,终于成功了!
回答 32 位问题...是的,IIS 可以 运行 64 位 OS.
上的 32 位 WebSockets 处理程序
至于为什么它现在可以工作...我又重新运行 APPCMD.EXE
,我在配置中四处寻找,直到它看起来像这样:
<globalModules>
...
<add name="WebSocketModule" image="%windir%\System32\inetsrv\iiswsock.dll" />
<add name="WebSocketModule32" image="%windir%\SysWOW64\inetsrv\iiswsock.dll" />
<add name="QuadooWebSocket" image="E:\dev\projects\trunk\target\debug\ActiveQuadoo.dll" />
</globalModules>
<handlers accessPolicy="Read, Script">
...
<add name="QuadooWebSocket" path="*.qws" verb="*" modules="WebSocketModule32" scriptProcessor="E:\dev\projects\trunk\target\debug\ActiveQuadoo.dll" resourceType="File" preCondition="bitness32" />
...
</handlers>
<location path="Default Web Site">
<system.webServer>
<handlers>
<remove name="QuadooWebSocket" />
<add name="QuadooWebSocket" path="*.qws" verb="*" modules="QuadooWebSocket" scriptProcessor="E:\dev\projects\trunk\target\debug\ActiveQuadoo.dll" resourceType="File" requireAccess="Script" preCondition="bitness32" />
</handlers>
</system.webServer>
</location>
一个区别是我的处理程序现在已在 WebSocketModule32
模块中注册。
我可以在这里结束答案,但是在最终加载我的处理程序之后,在它真正正常工作之前我必须解决许多问题。我学到的一些知识可能对其他人有用。
由于我正在异步处理 WebSocket,因此我需要从 OnExecuteRequestHandler()
return RQ_NOTIFICATION_PENDING
。否则,IIS立即关闭连接。
切换到 WebSockets 时,这是我最终使用的顺序:
- 设置模块上下文。
- 将响应状态设置为 101。
- 加载我的脚本虚拟机。
- 写headers(例如
Sec-WebSocket-Protocol
)。
Flush()
异步。
如果 Flush()
没有立即完成,那么它将通过调用 OnAsyncCompletion()
来完成。如果它确实立即完成,请使用将从 OnAsyncCompletion()
调用的相同代码路径并执行以下操作:
- 获取
IIS_WEBSOCKET
的命名上下文。
- 将上下文转换为
IWebSocketContext
指针。
- 启动异步 reader 循环。
- Return
RQ_NOTIFICATION_PENDING
.
收到来自 ReadFragment()
的关闭事件后,我调用 IndicateCompletion(RQ_NOTIFICATION_FINISH_REQUEST)
通知 IIS 我已完成连接。在我添加之前,IIS 没有调用我的处理程序的 CleanupStoredContext()
方法。
在 64 位 Windows 10 和 IIS 10 上,我正在尝试开发和测试一个本机 HTTP 模块,该模块将充当一组特定脚本文件的 WebSockets 处理程序映射。这一切都是在以 RegisterModule() 开头的本机 C++ 中完成的。我没有使用 ASP.NET 的任何部分。
当我访问应该调用处理程序的 URL 时,我收到此响应:
HTTP Error 500.21 - Internal Server Error
Handler "QuadooWebSocket" has a bad module "WebSocketModule" in its module list
Detailed Error Information:
Module IIS Web Core
Notification ExecuteRequestHandler
Handler QuadooWebSocket
Error Code 0x8007000dMore Information:
IIS core does not recognize the module.
我使用 IIS 管理器设置处理程序映射,它在 applicationHost.config 文件中创建了一个条目。
<handlers accessPolicy="Read, Script">
<other_modules />
<add name="QuadooWebSocket" path="*.qws" verb="*" modules="WebSocketModule" scriptProcessor="E:\dev\projects\trunk\target\debug\ActiveQuadoo.dll" resourceType="File" preCondition="bitness32" />
</handlers>
在此之前,我使用 "Windows Features" 控制面板安装了对 WebSockets 的支持,它还在 applicationHost.config 文件中添加了一行。
<globalModules>
<other_modules />
<add name="WebSocketModule" image="%windir%\System32\inetsrv\iiswsock.dll" />
</globalModules>
当我将 Visual Studio 附加到 w3wp.exe 时,我的代码中的 none 断点被解析。 RegisterModule() 未被调用。 DllMain() 甚至没有被调用。我的模块还实现了 IActiveScript,并且 IIS 确实为经典 ASP 请求加载了我的模块。
我的代码被构建到 32 位模块中,我在 applicationHost.config 文件中有 enable32BitAppOnWin64="true"。这适用于经典 ActiveScript/ASP 环境,但是当使用预期通过 RegisterModule() 导出加载的代码时,此设置是否也适用?如果这不是问题,那么是否需要其他步骤来为 WebSockets 启用本机 HTTP 模块?
谢谢!
时隔近两年,我决定用这几天的时间再次研究这个,终于成功了!
回答 32 位问题...是的,IIS 可以 运行 64 位 OS.
上的 32 位 WebSockets 处理程序至于为什么它现在可以工作...我又重新运行 APPCMD.EXE
,我在配置中四处寻找,直到它看起来像这样:
<globalModules>
...
<add name="WebSocketModule" image="%windir%\System32\inetsrv\iiswsock.dll" />
<add name="WebSocketModule32" image="%windir%\SysWOW64\inetsrv\iiswsock.dll" />
<add name="QuadooWebSocket" image="E:\dev\projects\trunk\target\debug\ActiveQuadoo.dll" />
</globalModules>
<handlers accessPolicy="Read, Script">
...
<add name="QuadooWebSocket" path="*.qws" verb="*" modules="WebSocketModule32" scriptProcessor="E:\dev\projects\trunk\target\debug\ActiveQuadoo.dll" resourceType="File" preCondition="bitness32" />
...
</handlers>
<location path="Default Web Site">
<system.webServer>
<handlers>
<remove name="QuadooWebSocket" />
<add name="QuadooWebSocket" path="*.qws" verb="*" modules="QuadooWebSocket" scriptProcessor="E:\dev\projects\trunk\target\debug\ActiveQuadoo.dll" resourceType="File" requireAccess="Script" preCondition="bitness32" />
</handlers>
</system.webServer>
</location>
一个区别是我的处理程序现在已在 WebSocketModule32
模块中注册。
我可以在这里结束答案,但是在最终加载我的处理程序之后,在它真正正常工作之前我必须解决许多问题。我学到的一些知识可能对其他人有用。
由于我正在异步处理 WebSocket,因此我需要从 OnExecuteRequestHandler()
return RQ_NOTIFICATION_PENDING
。否则,IIS立即关闭连接。
切换到 WebSockets 时,这是我最终使用的顺序:
- 设置模块上下文。
- 将响应状态设置为 101。
- 加载我的脚本虚拟机。
- 写headers(例如
Sec-WebSocket-Protocol
)。 Flush()
异步。
如果 Flush()
没有立即完成,那么它将通过调用 OnAsyncCompletion()
来完成。如果它确实立即完成,请使用将从 OnAsyncCompletion()
调用的相同代码路径并执行以下操作:
- 获取
IIS_WEBSOCKET
的命名上下文。 - 将上下文转换为
IWebSocketContext
指针。 - 启动异步 reader 循环。
- Return
RQ_NOTIFICATION_PENDING
.
收到来自 ReadFragment()
的关闭事件后,我调用 IndicateCompletion(RQ_NOTIFICATION_FINISH_REQUEST)
通知 IIS 我已完成连接。在我添加之前,IIS 没有调用我的处理程序的 CleanupStoredContext()
方法。