gpt4 book ai didi

c - 尝试接受套接字连接,检索并处理消息,然后将此消息写入终端

转载 作者:太空宇宙 更新时间:2023-11-04 04:52:36 25 4
gpt4 key购买 nike

我需要编写一个程序来通过套接字检索和处理消息。我毫不费力地理解了创建套接字、绑定(bind)套接字、监听传入连接然后接受它的过程。我无法从为接受的连接创建的文件流中接收消息。我的代码如下(我已经包含了几乎所有代码以供引用,但我认为问题出现在连接被接受之后......):

int sockfd; // the socket file descriptor
int conn_fd; // the accepted connection file descriptor
FILE *conn_fs; // the file stream for the accepted connection
char *conn_buff;
//char conn_buff[LINE_MAX]; // a buffer to store the data received from the accepted connection

int main(int argc, char *argv[]) {
int port = 0;
if ((argc != 2) || (sscanf(argv[1], "%d", &port) != 1)) {
fprintf(stderr, "Usage: %s [PORT]\n", argv[0]);
exit(1);
}

if (port < 1024) {
fprintf(stderr, "Port must be greater than 1024\n");
exit(1);
}

struct sockaddr_in servaddr; // socket address structure (socket in address)
// set all bytes in socket address structure to zero, and fill in the relevant data members
memset(&servaddr, 0, sizeof(servaddr));
servaddr.sin_family = AF_INET;
servaddr.sin_addr.s_addr = htonl(INADDR_ANY);
servaddr.sin_port = htons(port); // port is the first argument given in the terminal

// tell the user the servaddr structure has been initialised.
//printf("servaddr structure has been initialised..\n\ncreating socket..\n");

// create the socket using IPv4 (AF_INET) and 2-way comms (SOCK_STREAM)
if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) < 0) { // socket() returns < 0 if an error occurs
printf("error: creating the socket..\nexitting..\n");
exit(EXIT_FAILURE);
}

// tell the user the socket has been created
//printf("socket created..\n\nbinding socket..\n");

// bind the socket to the socket address structure defined above
if (bind(sockfd, (struct sockaddr *) &servaddr, sizeof(servaddr)) < 0) { // bind() returns < 0 if an error occurs
printf("error: binding the socket..\nexitting..\n");
exit(EXIT_FAILURE);
}

// tell the user the socket is "bound"
//printf("socket is now \"bound\"..\n\nmarking the socket as passive..\n");

// set the socket to accept incoming connections (listen)
if (listen(sockfd, SOMAXCONN) < 0) { // listen() returns < 0 if an error occurs
printf("error: marking the socket as a passive socket in the function listen()..\nexitting..\n");
exit(EXIT_FAILURE);
}

// tell the user the socket is listening for incoming connections
printf("socket is now passive (listening)..\n\naccepting incoming connections..\n");

// accept an incoming connection
if (conn_fd = accept(sockfd, NULL, NULL) < 0) { // accept() returns < 0 if an error occurs
printf("error: accepting an incoming connection..\nexitting..\n");
exit(EXIT_FAILURE);
}

// tell the user a connection has been accepted
printf("a connection has been accepted..\n\ncreating a file stream for this connection..\n");
/*
// open a file stream associated with conn_fd
if ((conn_fs = fdopen(conn_fd, "r+")) == NULL) { // fdopen() returns NULL if an error occurs
printf("error: associating a stream to the connections file descriptor in the function fdopen()..\nexitting..\n");
exit(EXIT_FAILURE);
}

// echo out the incoming message
/*while (fgets(conn_buff, LINE_MAX, conn_fd) != NULL) { // fill the conn_buff buffer with data from the file stream conn_fs. returns NULL on error or EOF
//while (read(conn_fd,conn_buff,sizeof(char)*LINE_MAX) > 0) {
printf(conn_buff);printf("OH HAIIIIIIIIIIIIIIIIIIIIIIIIII\n");
} printf("OH HAI\n");*/

size_t len = 100;
ssize_t read;
while ((read = getline(&conn_buff, &len, conn_fs)) != -1) {
printf("Retrieved line of length %zu :\n", read);
printf("%s", conn_buff);
}

free(conn_buff);

// check if there was an error
if (ferror(conn_fs) != 0) { // returns nonzero if the error indicator is set for conn_fs (eg, if fgets() above returned NULL due to an error)
printf("error: an error occurred whilst retrieving data from the stream..\nexitting..\n");
exit(EXIT_FAILURE);
}

// close the file stream associated with conn_fd
if (close((int) conn_fs) != 0) { // close the file stream
printf("error: closing the file stream..\nexitting..\n");
exit(EXIT_FAILURE);
}


exit(EXIT_SUCCESS);
}

当我运行该程序时,它会在 while ((read = getline(... 循环) 内停止。如果我按回车键刷新缓冲区,则会得到“检索到的长度为 1 的行: “来自终端。我发现程序(出于某种原因我无法理解)正在从标准输入读取。它等待我输入任何内容,一旦我刷新缓冲区(即按回车键),它就会将它全部发送回我。关闭程序的唯一方法是使用 Ctrl+C。因此,我认为我的 if ((conn_fs = fdopen(conn_fd, "r+")) == NULL) {声明。

我已经尝试了许多不同的从流中读取的方法(fread()、read()、getline()、fgets()、fgetc()...),它们都具有相同的效果。然后当我意识到问题一定出在我打开文件流的方式时,我尝试使用 fopen() 但无济于事。

我可能犯了一个愚蠢的错误,但有人可以帮我解决这个问题吗?

最佳答案

客户端永远不会关闭连接。

关于c - 尝试接受套接字连接,检索并处理消息,然后将此消息写入终端,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13674698/

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