windows socket编程

Server:

#include <stdio.h>  
#include <winsock2.h> // 必须包含windwos.h之前
#include <Windows.h>
 
#pragma comment(lib,"ws2_32.lib") 
 
#define  PORT 6000
DWORD WINAPI clientProc(LPARAM lparam)
{	
	SOCKET sockClient = (SOCKET)lparam;
	char buf[1024];
	while (TRUE)
	{
		memset(buf, 0, sizeof(buf));
		// 接收客户端的一条数据 
		int ret = recv(sockClient, buf, sizeof(buf), 0);
		//检查是否接收失败
		if (SOCKET_ERROR == ret) 
		{
			printf("socket recv failed\n");
			closesocket(sockClient);
			return -1;
		}
		// 0 代表客户端主动断开连接
		if (ret == 0) 
		{
			printf("client close connection\n");
			closesocket(sockClient);
			return -1;
		}		
		// 发送数据
		ret = send(sockClient, buf, strlen(buf), 0);
		//检查是否发送失败
		if (SOCKET_ERROR == ret)
		{
			printf("socket send failed\n");
			closesocket(sockClient);
			return -1;
		}
	}
	closesocket(sockClient);
	return 0;
}
bool InitNetEnv()
{
	// 进行网络环境的初始化操作
	WSADATA wsa;
	if (WSAStartup(MAKEWORD(2, 2), &wsa) != 0) 
	{
		printf("WSAStartup failed\n");
		return false;
	}
	return true;
}
int main(int argc, char * argv[])
{
	if (!InitNetEnv())
	{
		return -1;
	}
	// 初始化完成,创建一个TCP的socket
	SOCKET sServer = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
	//检查是否创建失败
	if (sServer == INVALID_SOCKET)
	{
		printf("socket failed\n");
		return -1;
	}
	printf("Create socket OK\n");
	//进行绑定操作
	SOCKADDR_IN addrServ;
	addrServ.sin_family = AF_INET; // 协议簇为IPV4的
	addrServ.sin_port = htons(PORT); // 端口  因为本机是小端模式,网络是大端模式,调用htons把本机字节序转为网络字节序
	addrServ.sin_addr.S_un.S_addr = INADDR_ANY; // ip地址,INADDR_ANY表示绑定电脑上所有网卡IP
	//完成绑定操作
	int ret = bind(sServer, (sockaddr *)&addrServ, sizeof(sockaddr));
	//检查绑定是否成功
	if (SOCKET_ERROR == ret)
	{
		printf("socket bind failed\n");
		WSACleanup(); // 释放网络环境
		closesocket(sServer); // 关闭网络连接
		return -1;
	}
	printf("socket bind OK\n");
	// 绑定成功,进行监听
	ret = listen(sServer, 10);  
	//检查是否监听成功
	if (SOCKET_ERROR == ret)
	{
		printf("socket listen failed\n");
		WSACleanup();
		closesocket(sServer);
		return -1;
	}
	printf("socket listen OK\n");
	// 监听成功
	sockaddr_in addrClient; // 用于保存客户端的网络节点的信息
	int addrClientLen = sizeof(sockaddr_in);
	while (TRUE)
	{
		//新建一个socket,用于客户端
		SOCKET *sClient = new SOCKET; 
		//等待客户端的连接
		*sClient= accept(sServer, (sockaddr*)&addrClient, &addrClientLen);
		if (INVALID_SOCKET == *sClient)
		{
			printf("socket accept failed\n");
			WSACleanup();
			closesocket(sServer);
			delete sClient;
			return -1;
		}
		//创建线程为客户端做数据收发
		CreateThread(0, 0, (LPTHREAD_START_ROUTINE)clientProc, (LPVOID)*sClient, 0, 0);
	}
	closesocket(sServer);
	WSACleanup();
	return 0;
}

Client:

#include <stdio.h>
#include <winsock2.h>
#include <Windows.h>
 
#pragma comment(lib,"ws2_32.lib")
#define  PORT 6000
 
int main(int argc, char * argv[])
{
	//初始化网络环境
	WSADATA wsa;
	if (WSAStartup(MAKEWORD(2, 2), &wsa) != 0)
	{
		printf("WSAStartup failed\n");
		return -1;
	}
	// 初始化完成,创建一个TCP的socket
	SOCKET sServer = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
	if (sServer == INVALID_SOCKET)
	{
		printf("socket failed\n");
		return -1;
	}
	//指定连接的服务端信息
	SOCKADDR_IN addrServ;
	addrServ.sin_family = AF_INET;
	addrServ.sin_port = htons(PORT);
	//客户端只需要连接指定的服务器地址,127.0.0.1是本机的回环地址
	addrServ.sin_addr.S_un.S_addr = inet_addr("127.0.0.1");
	
	// 服务器Bind 客户端是进行连接
	int ret = connect(sServer,(SOCKADDR*)&addrServ,sizeof(SOCKADDR));//开始连接
	if (SOCKET_ERROR == ret)
	{
		printf("socket connect failed\n");
		WSACleanup();
		closesocket(sServer);
		return -1;
	}
	//连接成功后,就可以进行通信了
	char szBuf[1024];
	memset(szBuf,0,sizeof(szBuf));
	sprintf_s(szBuf,sizeof(szBuf),"Hello server");
	//当服务端是recv的时候,客户端就需要send,若两端同时进行收发则会卡在这里,因为recv和send是阻塞的
	ret = send(sServer, szBuf, strlen(szBuf), 0);
	if (SOCKET_ERROR == ret)
	{
		printf("socket send failed\n");
		closesocket(sServer);
		return -1;
	}
	
	ret = recv(sServer, szBuf, sizeof(szBuf), 0);
	if (SOCKET_ERROR == ret)
	{
		printf("socket recv failed\n");
		closesocket(sServer);
		return -1;
	}
	printf("%s\n",szBuf);
<span style="white-space:pre">	</span>//关闭连接
	closesocket(sServer);
	WSACleanup();
	return 0;
}

猜你喜欢

转载自blog.csdn.net/nineship/article/details/81744628