winsock unblock client programing demo

#include <iostream>
#include <winsock2.h>
#pragma comment(lib,"ws2_32.lib")

int main(void)
{
	WSADATA WsaDat;
	if(WSAStartup(MAKEWORD(2,2),&WsaDat)!=0)
	{
		std::cout<<"Winsock error - Winsock initialization failed\r\n";
		WSACleanup();
		system("PAUSE");
		return 0;
	}
	
	// Create our socket

	SOCKET Socket=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
	if(Socket==INVALID_SOCKET)
	{
		std::cout<<"Winsock error - Socket creation Failed!\r\n";
		WSACleanup();
		system("PAUSE");
		return 0;
	}
	
	// Resolve IP address for hostname
	struct hostent *host;
	if((host=gethostbyname("localhost"))==NULL)
	{
		std::cout<<"Failed to resolve hostname.\r\n";
		WSACleanup();
		system("PAUSE");
		return 0;
	}
	
	// Setup our socket address structure
	SOCKADDR_IN SockAddr;
	SockAddr.sin_port=htons(8888);
	SockAddr.sin_family=AF_INET;
	SockAddr.sin_addr.s_addr=*((unsigned long*)host->h_addr);
	
	// Attempt to connect to server
	if(connect(Socket,(SOCKADDR*)(&SockAddr),sizeof(SockAddr))!=0)
	{
		std::cout<<"Failed to establish connection with server\r\n";
		WSACleanup();
		system("PAUSE");
		return 0;
	}
	
	// If iMode!=0, non-blocking mode is enabled.
	u_long iMode=1;
	ioctlsocket(Socket,FIONBIO,&iMode);
	
	// Main loop
	for(;;)
	{
		// Display message from server
		char buffer[1000];
		memset(buffer,0,999);
		int inDataLength=recv(Socket,buffer,1000,0);
		std::cout<<buffer;
		
		int nError=WSAGetLastError();
		if(nError!=WSAEWOULDBLOCK&&nError!=0)
		{
			std::cout<<"Winsock error code: "<<nError<<"\r\n";
			std::cout<<"Server disconnected!\r\n";
			// Shutdown our socket
			shutdown(Socket,SD_SEND);

			// Close our socket entirely
			closesocket(Socket);

			break;
		}
		Sleep(1000);
	}

	WSACleanup();
	system("PAUSE");
	return 0;
}


源文章:http://www.win32developer.com/tutorial/winsock/winsock_tutorial_3.shtm


今日写一个阻塞socket客户端时被绊了一跤:recv返回0,表明此时socket已经被服务器关掉了(具体的场景是我socket连接apache服务器,发送不带Keep-alive的http put,服务器接受完毕并相应一个不带Content-Length的201之后断开连接),而此时我往这个socket发送数据居然成功了,还返回了发送字节数....而当我closesocket(fd)之后再发送就返回-1并报10038错误了....

经分析,是apache关闭了socket的write端,所以client的recv检测到socket的read端断开,而socket的write端还没有断开,send的还可以继续发送。此时socket处于半断开状态。

你可能感兴趣的:(apache,socket,服务器,System,buffer,initialization)