作为一项学校作业,我正在用C编写一个简单的HTTP Web服务器。我已经准备好了大部分代码,但send()
/write()
需要发送消息的长度。
这就是我正在挣扎的地方。fseek()
不工作,因此ftell()
返回"非法查找"errno
。在确定了方法并检索到正确的响应代码后,我使用fprintf()
直接写入文件流。
static void response(FILE *response, int code, char *path, int fd)
{
FILE *body;
char *line = makestring(300) //Creates an empty string of size 300
... // Replace code in between with other code block
if(code == 200){
http_ok(response); //A function with fprintf's to write the headers.
body = fopen(path, "w");
while(!feof(body)){
fgets(line, 300, body);
fprintf(response, "%srn", line);
}
fclose(body);
}
... // Replace up to this point
fseek(response, 0L, SEEK_END);
int response_size = ftell(response);
rewind(response);
send(fd, response, response_size, 0);
}
现在,这是我的代码的简化版本,只包括状态200。问题是正确返回响应,然后在浏览器中打开页面。但是,response_size
变量始终打印到-1
。
现在继续执行状态代码301 Moved Permanently,它根本不起作用。此代码可以替换两个"…"的之间的另一个if
语句
...
if(code == 301){
http_moved(response, path);
}
...
http函数的总体外观类似于
void http_ok/moved(FILE *response)
{
fprintf(response, "Correct codes and headers for the response type herern")
...
fprintf(response, "rnrn")
}
响应FILE
是使用fdopen(sockfd, "w")
在套接字的文件描述符上打开的,因此它不是正常的fopen()
。据我所知,这意味着fseek()
不会按预期工作。
至于问题本身,当我使用文件描述符时,如何获得合适的http响应长度?
如果保证响应指向一个文件,我会使用:
#include <sys/stat.h>
struct stat st;
if (fstat(fileno(response)), &st) == -1) {
/* handle error */
} else {
response_size = (int)st.st_size;
}