C ';错误的文件描述符';接受的套接字上出现错误
我正试图进入网络编程领域,并一直遵循有关套接字的指南。我用C编写了一个简单的Windows TCP服务器和客户端,但似乎无法让它们正常工作。客户端连接第二次时,服务器抛出“坏文件描述符”错误并关闭。我不明白刚刚由C ';错误的文件描述符';接受的套接字上出现错误,c,sockets,networking,C,Sockets,Networking,我正试图进入网络编程领域,并一直遵循有关套接字的指南。我用C编写了一个简单的Windows TCP服务器和客户端,但似乎无法让它们正常工作。客户端连接第二次时,服务器抛出“坏文件描述符”错误并关闭。我不明白刚刚由accept()创建的文件描述符怎么可能是坏的。我对此做了研究,只发现有人在阅读之前关闭了文件,而我没有 代码如下: 服务器 #include <stdio.h> #include <stdlib.h> #include <winsock2.h> i
accept()
创建的文件描述符怎么可能是坏的。我对此做了研究,只发现有人在阅读之前关闭了文件,而我没有
代码如下:
服务器
#include <stdio.h>
#include <stdlib.h>
#include <winsock2.h>
int main(int argc, char *argv[])
{
WSADATA WSAData;
WSAStartup(MAKEWORD(2,0), &WSAData);
SOCKET sock, newsock;
int portno, clilen;
char buffer[256];
SOCKADDR_IN serv_addr, cli_addr;
int n;
sock = socket(AF_INET, SOCK_STREAM, 0);
if (sock < 0)
{
perror("Error opening socket");
exit(1);
}
memset((char *) &serv_addr, 0, sizeof(serv_addr));
portno = 5001;
serv_addr.sin_family = AF_INET;
serv_addr.sin_addr.s_addr = INADDR_ANY;
serv_addr.sin_port = htons(portno);
if (bind(sock, (SOCKADDR *) &serv_addr, sizeof(serv_addr)) < 0)
{
perror("Eror on binding");
exit(1);
}
listen(sock, 5);
clilen = sizeof(cli_addr);
newsock = accept(sock, (SOCKADDR *) &cli_addr, &clilen);
if (newsock < 0)
{
perror("Error on accept");
exit(1);
}
memset(buffer, 0, 256);
n = read(newsock, buffer, 255);
if (n < 0)
{
perror("Error reading from socket");
exit(1);
}
printf("Here is the message : %s\n", buffer);
n = write(newsock, "I got your message", 18);
if (n < 0)
{
perror("Error writing to socket");
exit(1);
}
WSACleanup();
return 0;
}
你看到我的代码有什么问题吗?提前感谢您的帮助 我会将其放在注释中,但请尝试使用函数而不是read()。这是因为read()不调用套接字API,所以就Windows而言,文件描述符无效
同样,在您的客户端中,您应该使用而不是write()。谢谢,它现在可以工作了!这是否意味着windows套接字API的实现方式与linux套接字不同?就像在中一样,我的套接字变量真的是文件描述符,还是仅仅是专门为winsock设计的标识符?在Windows上,任何东西真的是文件描述符,还是只是一堆乱七八糟的东西假装是文件描述符?你说得对。那么,所有这些胡涂都是同一种胡涂吗?
sock
和stdin
是同一类型的东西吗?如果不是的话,它们有什么区别?回到TCP/IP网络在Windows中出现之前,winsock是一个第三方库,不可能将这些新型的“socket”对象与现有的文件句柄系统集成,因此,winsock函数创建的文件描述符在winsock库之外没有任何意义,这意味着您必须使用recv而不是读取。不知何故,当winsock成为操作系统的一部分时,这种情况并没有得到改善。
#include <stdio.h>
#include <stdlib.h>
#include <winsock2.h>
int main(int argc, char *argv[])
{
WSADATA WSAData;
WSAStartup(MAKEWORD(2,0), &WSAData);
SOCKET sock;
int portno, n;
SOCKADDR_IN serv_addr;
HOSTENT *server;
char buffer[256];
if (argc < 3)
{
fprintf(stderr, "Usage : %s hostname port\n", argv[0]);
exit(0);
}
portno = atoi(argv[2]);
sock = socket(AF_INET, SOCK_STREAM, 0);
if (sock < 0)
{
perror("Error opening socket\n");
exit(1);
}
server = gethostbyname(argv[1]);
if (server == NULL)
{
perror("Error, no such host");
exit(1);
}
memset((char *) &serv_addr, 0, sizeof(serv_addr));
serv_addr.sin_family = AF_INET;
memcpy((char *) &serv_addr.sin_addr.s_addr, (char *) server->h_addr, server->h_length);
serv_addr.sin_port = htons(portno);
if (connect(sock, (SOCKADDR *) &serv_addr, sizeof(serv_addr)) < 0)
{
perror("Error connecting to server");
exit(1);
}
printf("Please enter your message : ");
memset(buffer, 0, 256);
fgets(buffer, 255, stdin);
n = write(sock, buffer, strlen(buffer));
if (n < 0)
{
perror("Error writing to socket");
exit(1);
}
memset(buffer, 0, 256);
n = read(sock, buffer, 255);
if (n < 0)
{
perror("Error reading from socket");
exit(1);
}
printf("%s\n", buffer);
WSACleanup();
return 0;
}
C:\...myfolder>server
*here it does nothing until I start the client with "client 127.0.0.1 5001" in another window*
Error reading from socket: Bad file descriptor