Winsock服务器Bind失败错误10047问题求助
Winsock bind()错误10047的排查与解决
问题描述
参照两年前的教程编写Winsock服务器代码,已将sockaddr_in.sin_family设置为AF_INET,但调用bind()时出现错误10047。已尝试执行netsh winsock reset命令并重启电脑、修改hosts文件确认本地回环地址正确,但问题仍未解决。
服务器代码
#pragma once #include <WinSock2.h> #include <tchar.h> #include<WS2tcpip.h> #include <map> #include <string> #include <iostream> /* struct sockaddr_in { unsigned short sin_port; unsigned short sin_family; struct in_addr sin_addr; char sin_zero[8]; }; */ class Log { int OutputMessageLogLevel = 1; //will output to a .txt log file if its a warning or higher int LogLevel = 0; //0 will be generic print public: void SetLogLevel(int NewLogLevel) { LogLevel = NewLogLevel; } void print(std::string Message) { if (LogLevel == 0) { std::cout << Message << std::endl; } else { if (LogLevel == 1) { std::cout << "[Warning] " + Message << std::endl; } else { if (LogLevel == 2) { std::cout << "[Error] " + Message << std::endl; } } } } }; int main() { Log logger; SOCKET ServerSocket, AcceptSocket; int port = 55555; WSADATA wsaData; int wsaerr; WORD WindowsVersionRequested = MAKEWORD(2, 2); wsaerr = WSAStartup(WindowsVersionRequested, &wsaData); if (wsaerr != 0) { logger.print("The Winsock dll is not found ):"); return wsaerr; } else { std::string WSAStatus = wsaData.szSystemStatus; logger.print("The Winsock dll is found (: "); logger.print("Status: " + WSAStatus); } ServerSocket = INVALID_SOCKET; ServerSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); if (ServerSocket == INVALID_SOCKET) { logger.print("Error at socket(): "); return 0; } else { logger.print("socket() is Good to go"); } logger.print("Now binding server socket..."); sockaddr_in service; //buffer to store numerical binary representation of the IP address. also see struct sockaddr_in above //The IP address is returned in network byte order. service.sin_family = AF_INET; //To use IPV4 configuration or whatever InetPton(AF_INET, _T("127.0.0.1"), &service); //127.0.0.1 will loop back to your own machine for local testing service.sin_port = htons(port); //port is 55555 the integer which we initialize up top if (bind(ServerSocket, (SOCKADDR*)&service, sizeof(service)) == SOCKET_ERROR) { logger.print("bind() failed: "); std::cout << WSAGetLastError() << std::endl; closesocket(ServerSocket); return 0; } else { logger.print("bind() is okay,Success binding socket"); } //int listen(SOCKET s, int backlog); if (listen(ServerSocket, 1) == SOCKET_ERROR) { logger.print("Could not listen for Socket: "); return -1; } else { logger.print("Could not listen for Socket: "); } logger.print("Accepting Connections..."); AcceptSocket = accept(ServerSocket, NULL, NULL); if (AcceptSocket == INVALID_SOCKET) { logger.print("Accept Failed: "); return -1; } { logger.print("Accepted Connection!"); system("pause"); WSACleanup(); } };
运行输出
The Winsock dll is found (: Status: Running socket() is Good Now binding server socket... bind() failed: 10047
错误原因与解决方法
错误原因
错误10047的核心是地址族不匹配:
InetPton(AF_INET, ...)的第三个参数应指向in_addr类型变量(即sockaddr_in的sin_addr成员),但你传入了整个sockaddr_in结构体的指针&service,导致IP地址数据覆盖了之前设置的sin_family,使其不再是AF_INET。- 代码中注释的
sockaddr_in结构体定义错误(sin_port和sin_family顺序写反),这也可能误导了你对结构体的理解。
解决步骤
修正
InetPton调用参数
将第三个参数改为&service.sin_addr,确保IP地址写入正确位置:InetPton(AF_INET, _T("127.0.0.1"), &service.sin_addr);初始化结构体避免垃圾数据
在填充sockaddr_in前,用memset将整个结构体初始化为0:memset(&service, 0, sizeof(service));修正结构体注释
替换错误的注释为正确的sockaddr_in定义:struct sockaddr_in { short sin_family; // 地址族,如AF_INET u_short sin_port; // 端口号,网络字节序 struct in_addr sin_addr;// IP地址 char sin_zero[8]; // 填充用,使大小与sockaddr一致 };
修改完成后重新编译运行,bind()即可正常执行。
内容的提问来源于stack exchange,提问作者Ethereal
相关产品推荐
相关产品推荐

