HttpAddFragmentToCache和操作系统错误50



我正在尝试在应用程序中创建嵌入式web服务器。为此,我使用http。sys来自Windows的HTTP服务器组件。当我不尝试使用HttpAddFragmentToCache时,一切都很好。

我所做的到目前为止(删除任何错误检查,但没有片段缓存它工作正常):

HttpInitialize( HTTPAPI_VERSION_1, HTTP_INITIALIZE_SERVER );
HttpCreateHttpHandle( FQueueHandle )
HttpAddUrl( FQueueHandle, PWideChar( W ) );
...
HttpRemoveUrl( FQueueHandle, PWideChar( W ) );
HttpTerminate( HTTP_INITIALIZE_SERVER );

现在当一个请求来自于一个帮助线程:

HttpReceiveHttpRequest( FQueueHandle, FRequestID, 0, FRequest^, FRequestBufferSize, @Bytes );
// if needed:
HttpReceiveRequestEntityBody( FQueueHandle, FRequestId, 0, @FRequestContent[ 0 ], Longword( N ), @BytesRead )
// Fill in chunks...
// Respond
HttpSendHttpResponse( FQueueHandle, FRequestId, 0, FResponse, nil, N );

我想改变的是添加一些静态文档到片段缓存(在上面的省略号处):

Chunk.DataChunkType           := hctFromMemory;
Chunk.FromMemory.pBuffer      := @Content[ 0 ];
Chunk.FromMemory.BufferLength := Length( Content );
Policy.Policy                 := hcpUserInvalidates;
Policy.SecondsToLive          := 0;
Result := HttpAddFragmentToCache( FQueueHandle, PWideChar( W ), Chunk, Policy );

注意:在我的代码中,所有重叠的参数都是可选的nil/NULL,这解释了为什么你可能会错过这个参数。

这将产生结果50(不支持该请求)。我试着从内存和文件句柄中添加片段,所有不同的策略。检查在反汇编中传递的值是否正确,检查传递给HttpAddFragmentToCache的字符串是否确实是传递给HttpAddUrl的字符串的有效子url(如果不是,您会得到操作系统错误2,因此也不是它)。

我的问题是:这可能是什么?我尝试以最直接的方式使用这个API调用,我可以看到(这是API的设计目的),但显然我做错了…

更新:

看起来用HttpAddFragmentToCache函数添加的片段有一个最大大小:

当上面的代码被替换为:

Chunk.FromMemory.BufferLength := Min( 256*1024, Length( Content ) );

无错误;当被

取代时
Chunk.FromMemory.BufferLength := Min( 256*1024 + 1, Length( Content ) );

它失败。显然有尺寸限制,而且……我找到它了:

http://support.microsoft.com/kb/820129

UriMaxUriBytes 262144 (bytes)4096(4k) - 16777216(16MB)字节任意比这更大的响应值不在内核中缓存响应缓存。

这留下两个选项:1。为较大的文件保留多个片段。或2。

解决了这个问题:每个片段缓存的大小是有限制的;默认为256KB。

如果没有实现的所有源代码,这有点困难。

什么时候调用HttpAddFragmentToCache ?它应该在客户端TThread实例中调用HttpReceiveHttpRequest()之前。

例如,你的HttpReceiveHttpRequest()调用听起来有点奇怪。你应该使用

HttpReceiveRequestEntityBody( FQueueHandle, FRequest^.RequestID, ... ) 

看看我们的SynCrtSock单元中的THttpApiServer类,这是http。系统服务器。它还不支持缓存,但至少主初始化和线程池可以正常工作。

相关内容

  • 没有找到相关文章

最新更新