gpt4 book ai didi

c - 套接字事务未通过

转载 作者:太空宇宙 更新时间:2023-11-04 08:57:54 24 4
gpt4 key购买 nike

我正在编写一个在将页面发送到浏览器时遇到问题的网络服务器。它正确发送第一个文件(这个文件包括两个 css 文件)。但是,在发送第二个文件后,浏览器停止请求数据。它总是遗漏完成页面所需的 css 文件之一。

这是一些交易:

GET / HTTP/1.1
Host: website.com
Connection: keep-alive
Cache-Control: max-age=0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
User-Agent: Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.31 (KHTML, like Gecko) Chrome/26.0.1410.43 Safari/537.31
Accept-Encoding: gzip,deflate,sdch
Accept-Language: en-US,en;q=0.8
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.3

HTTP/1.1 OK 200
Server: thserver
Date: Mon Apr 15 17:29:51 2013
Content-Length: 564

Data received: GET /main.css HTTP/1.1
Host: website.com
Connection: keep-alive
Accept: text/css,*/*;q=0.1
User-Agent: Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.31 (KHTML, like Gecko) Chrome/26.0.1410.43 Safari/537.31
Referer: http://website.com/
Accept-Encoding: gzip,deflate,sdch
Accept-Language: en-US,en;q=0.8
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.3

HTTP/1.1 OK 200
Server: thserver
Date: Mon Apr 15 17:29:51 2013
Content-Length: 386

如果有人也知道验证 http 事务的好方法,那也会有所帮助。我确实查看了 chrome 的开发工具并显示它正在等待接收最后一个文件,但我似乎从未在服务器上收到请求。

另外,我用telnet模拟了一个浏览器,效果很好。这是我输入的内容:

GET / 
GET /index.css
GET /main.css

它每次都发回文件。

代码继续使用 read(2) 轮询套接字,但在第三个文件的请求应该到达时继续返回 EAGAIN 或 EWOULDBLOCK。

这是套接字 io 的代码:

const int port_number   = 80;
const int timeout = 5000000;
const int wait_time = 10000;

PORT_CALL {

/* declarations here */

read_client:

result = read( socket[ 0 ], &header_buffer[ bytes_read ], BUFFER_SIZE - bytes_read );

if( result < 0 ){
if( errno & ( EWOULDBLOCK | EAGAIN ) ){

if( bytes_read > 0 ){

bytes_read = 0;
read_timeout = 0;
goto respond_request;
}
if( read_timeout < timeout ){
read_timeout += wait_time;
usleep( wait_time );
goto read_client;
}
}
goto exit_thread;

} else if( result > -1 ){
bytes_read += result;
goto read_client;
}
respond_request:

/* respond stuff start */

/* respond stuff end */

goto read_client;

exit_thread:

这是涉及创建套接字的代码

temp->socket_descriptor = socket( AF_INET, SOCK_STREAM, 0 );

temp->server_address.sin_family = AF_INET;
temp->server_address.sin_addr.s_addr = INADDR_ANY;
temp->server_address.sin_port = htons( * temp->port_number );

if( bind( temp->socket_descriptor,
( struct sockaddr * ) &temp->server_address,
sizeof( temp->server_address ) ) < 0 ) ..

listen( temp->socket_descriptor, 10 );

wait_for_client:

new_socket = accept( temp->socket_descriptor,
( struct sockaddr * ) &client_address,
&address_length );

我知道我可能要求太多了。如果有人知道一个好的调试工具可以让我解决这个问题,我也将非常感激。如果有人建议使用调试器工具帮助我解决问题,我也会将其视为一个答案。

编辑:写入和读取函数现在在循环中,但问题仍然存在。

最佳答案

如果您刚刚学习如何使用数据包捕获进行调试,也许 wireshark 更容易上手。它提供了一个 GUI,可以轻松定义简单规则并直观地检查捕获。这当然是一个品味问题,所以只是一个建议。

至于代码,很难说出问题可能是什么,因为它离SSCCE 还差得远。 .不过我有一些建议,

  1. 如果您要检查诸如 if( filename ) 之类的内容,则在释放它之后 filename = NULL;
  2. 如果你想将缓冲区清零,对其进行 memset 或遍历其整个大小。 for( ; header_buffer[ i ]; i++ ) header_buffer[ i ] = 0; 中的测试看起来很危险。
  3. 准备从返回 0 的套接字读取和写入,以及 < 0。
  4. 循环写入。

你的读取循环是直到它有完整的请求,还是直到它有超过 0 个字节?看起来像后者,那是不对的。

编辑,添加以下文字:示例中的代码仍然不是很完整(write fex 在哪里?),所以很难猜出确切的问题。然而,有几个非常致命的缺陷。

  1. 不应像现在这样测试 errno,if( errno & ( EWOULDBLOCK | EAGAIN ) )。在 Linux 上,您可以测试 if (errno == EWOULDBLOCK),因为 EAGAIN 和 EWOULDBLOCK 是相同的。在它们不同的系统上,使用两个带有 || 的测试它们之间。如果 errno 是 fex ECONNRESET,则当前代码返回非零值(在 Linux 上)。

  2. 现在代码在技术上涵盖了读取返回 0,但不是特例。读取返回 0 意味着连接正在关闭,您不应再读取套接字。

关于您的 Web 服务器中可能存在的问题的一个疯狂猜测(与上面的 #2 相关)是客户端在接收到第三个文件之前断开连接,并且服务器在关闭的套接字上保持忙碌循环。

我建议浏览 Beejs guide或者一些关于系统和套接字编程的书。

关于c - 套接字事务未通过,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16026856/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com