用Socket API建立简易TCP服务端
1 建立一个socket
2 绑定接受客户端连接的端口 bind
3 监听网络端口 listen
4 等待接受客户端连接 accept
5 向客户端发送一条数据send
6 关闭socket closesocket
用Socket API建立简易TCP客户端
1 建立一个socket
2 连接服务器 connect
3 接收服务器信息 recv
4 关闭socket closesocket
#define WIN32_LEAN_AND_MEAN //避免引用会产生冲突的依赖库(windows.h包含有WinSock2.h的一些宏定义,防止产生重定义错误!)
#define _WINSOCK_DEPRECATED_NO_WARNINGS
#include <windows.h> //windows系统API头文件
#include <WinSock2.h> //最新windows下Socket API头文件
#include <cstdio>
/*无法解析。。。一般由于没有引入链接库文件导致,有两种方法*/
/*方法1:预编译方式。弊端:不能跨平台,在非windows平台下不支持这种方式*/
#pragma comment(lib,"ws2_32.lib")
/*方法2:在连接器中添加:链接器->输入->附加依赖项*/
------mySever.cpp
int main()
{
/*——建立简易TCP服务端——*/
/*创建WORD的版本号 和 WSADATA变量*/
WORD version = MAKEWORD(2, 2);
WSADATA data;
/*启动WindowsSocket 2.x环境*/
WSAStartup(version, &data);
/*1 建立一个socket (套接字)*/
//Parameters:[1]socket协议簇AF_INET(IPV4),[2]网络类型,SOCK_STREAM面向数据流,[3]protocol网络协议
SOCKET _sock = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
/*2 绑定接受客户端连接的端口 bind*/
//Parameters:[1]socket,[2]sockaddress Socket网络地址,[3]namelen 第二个参数的长度
sockaddr_in _sin = {}; //如果直接使用sockaddr,这个结构体中的类型不便于我们填写变量
_sin.sin_family = AF_INET;
_sin.sin_port = htons(4567); //host to net unsigned short端口号,主机上的数据类型和网络字节序不同
_sin.sin_addr.S_un.S_addr = INADDR_ANY; //inet_addr("127.0.0.1");这是本机地址,不是外网地址,这种方法可以防止外网的访问。INADDR_ANY是所有IP地址都可以访问
if (SOCKET_ERROR == bind(_sock, (sockaddr*)&_sin, sizeof(_sin)))
{
printf("错误,绑定网络端口失败...\n");
}
else
{
printf("绑定网络端口成功...\n");
}
//3 监听网络端口 listen
if (SOCKET_ERROR == listen(_sock, 5)) //最多可以有多少监听对象连接
{
printf("错误,监听网络端口失败...\n");
}
else
{
printf("监听网络端口成功...\n");
}
//4 等待接受客户端连接 accept
sockaddr_in clientAddr = {};
int nAddrLen = sizeof(sockaddr_in);
SOCKET _csock = INVALID_SOCKET;
char msgBuf[] = "Hello, I'm Server.";
while (true)
{
_csock = accept(_sock, (sockaddr*)&clientAddr, &nAddrLen); //最后一个参数传入结构体的长度
if (INVALID_SOCKET == _csock)
{
printf("错误,接收到无效客户端SOCKET. . .\n");
}
printf("新客服端加入:IP = %s \n", inet_ntoa(clientAddr.sin_addr)); //inet_ntoa需要定义宏:_WINSOCK_DEPRECATED_NO_WARNINGS
//5 向客户端发送一条数据send
send(_csock, msgBuf, strlen(msgBuf) + 1, 0);
}
//6 关闭socket closesocket
closesocket(_sock);
/*关闭清除WindowsSocket环境*/
WSACleanup();
return 0;
}
------myClient.cpp
#define WIN32_LEAN_AND_MEAN
#include<windows.h>
#include<WinSock2.h>
#include<stdio.h>
#pragma comment(lib,"ws2_32.lib")
int main()
{
/*——建立简易TCP客户端——*/
/*创建WORD的版本号 和 WSADATA变量*/
WORD version = MAKEWORD(2, 2);
WSADATA data;
/*启动WindowsSocket 2.x环境*/
WSAStartup(version, &data);
//1 建立一个socket
SOCKET _sock = socket(AF_INET, SOCK_STREAM, 0);
if (INVALID_SOCKET == _sock)
{
printf("错误,建立Socket失败...\n");
}
else {
printf("建立Socket成功...\n");
}
//2 连接服务器 connect
sockaddr_in _sin = {};
_sin.sin_family = AF_INET;
_sin.sin_port = htons(4567);//与服务端一致
_sin.sin_addr.S_un.S_addr = inet_addr("127.0.0.1");
int ret = connect(_sock, (sockaddr*)&_sin, sizeof(sockaddr_in));
if (SOCKET_ERROR == ret)
{
printf("错误,连接服务器失败...\n");
}
else {
printf("连接服务器成功...\n");
}
//3 接收服务器信息 recv
char recvBuf[256] = { };
int nlen = recv(_sock, recvBuf, 256, 0);
if (nlen > 0)
{
printf("接收到的数据:%s\n", recvBuf);
}
//4 关闭socket closesocket
closesocket(_sock);
/*关闭清除WindowsSocket环境*/
WSACleanup();
getchar();
return 0;
}