使用软件:Visual Studio 2022
步骤:
1,新建一个空项目,项目名称为Server,解决方案名称为Socket;
2,软件右方解决方案资源管理器中->右击"解决方案"Socket"->添加"新建项目"添加空项目,项目名称为Client;
3,右击"Server"->添加“现有项”,"Server"有一个头文件,一个源文件,多选并添加。"Client"同理;
特别注意:
①Server.h,Server.c属于项目"Server";Client.h,Client.c属于项目"Client";
②Server.c和Client.c中第一行对头文件的引用,/Socket为头文件位置,请做出相应更改;
③右击项目Client->项目->属性->C/C++->常规->SDL检查改为否,不做修的话"inet_addr"会出错。
4,按ctrl+F5先运行Server,再右击"Client"->调试->启动新实例;
5,开始运行。(注意:客户端输入"end"结束连接,连接断开后服务器端再次发送消息不成功,会再次进入监听状态)
服务器端头文件Server.h
#ifndef _SOCKETTCP_H_
#define _SOCKETTCP_H_
#include<WinSock2.h> //Windows平台网络库头文件
#pragma comment(lib,"ws2_32.lib") //库文件
#include<stdbool.h>
#include<stdio.h>
#define PORT 8888 //端口号 >1024
#define err(errMsg) printf("[line:%d]%s failed code %d",__LINE__,errMsg,WSAGetLastError())
//打开网络库
bool init_Socket();
//关闭网络库
bool close_Socket();
//创建服务端
SOCKET CreateServerSocket();
#endif // ! _SOCKETTCP_H_
服务器端源文件Server.c
#include"../Socket/Server.h"
#include<stdio.h>
#include<stdlib.h>
int main()
{
init_Socket();
SOCKET serfd = CreateServerSocket();
Sign:printf("IP:127.0.0.1\n");
printf("Listening port:%d \n", PORT);
printf("wait Client connect...\n");
//客户端请求连接
SOCKET clifd = accept(serfd, NULL, NULL);
if (INVALID_SOCKET == clifd)
{
err("accept");
}
//可以与客户端通信
char recvbuf[BUFSIZ] = { 0 };
char sendbuf[BUFSIZ] = { 0 };
printf("Client connected...\n");
while (true)
{
//接收消息
if (0 < recv(clifd, recvbuf, BUFSIZ, 0))
{
printf("recv:%s\n", recvbuf);
memset(recvbuf, 0, sizeof(recvbuf));
}
//给客户端发送消息
printf("send>");
gets_s(sendbuf, BUFSIZ);
if (SOCKET_ERROR == send(clifd, sendbuf, strlen(sendbuf), 0))
{
err("send");
printf("\n");
printf("Client disconnected\n");
goto Sign;
}
if (INVALID_SOCKET == clifd)
{
err("accept");
return false;
}
}
closesocket(clifd);
closesocket(serfd);
close_Socket();
system("pause");
return 0;
}
bool init_Socket()
{
WSADATA wsadata;
if(0 != WSAStartup(MAKEWORD(2, 2), &wsadata))
{
printf("WSAStartup failed code %d", WSAGetLastError());
return false;
}
//WSA Windows异步套接字
//parm1 请求的Socket版本
//parm2 传出参数
return true;
}
bool close_Socket()
{
if (0 != WSACleanup())
{
printf("WSACleanup failed code %d", WSAGetLastError());
return false;
}
return true;
}
SOCKET CreateServerSocket()
{
//1 创建空的Socket
//af 地址协议族
//type 传输协议类型: 流式套接字 数据报套接字
//protocol 使用的具体传输协议
SOCKET fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (fd == INVALID_SOCKET)
{
err("socket");
return INVALID_SOCKET;
}
//2 绑定端口与ip地址
struct sockaddr_in addr;
addr.sin_family = AF_INET;
addr.sin_port = htons(PORT);
addr.sin_addr.S_un.S_addr =ADDR_ANY;
if (SOCKET_ERROR == bind(fd, &addr, sizeof(addr)))
{
err("bind");
return false;
}
//监听
listen(fd, 10);
return fd;
}
客户端头文件Client.h文章来源:https://www.toymoban.com/news/detail-502517.html
#ifndef _SOCKETTCP_H_
#define _SOCKETTCP_H_
#include<WinSock2.h> //Windows平台网络库头文件
#pragma comment(lib,"ws2_32.lib") //库文件
#include<stdbool.h>
#include<stdio.h>
#define PORT 8888 //端口号 >1024
#define err(errMsg) printf("[line:%d]%s failed code %d",__LINE__,errMsg,WSAGetLastError())
//打开网络库
bool init_Socket();
//关闭网络库
bool close_Socket();
//创建客户端
SOCKET CreateClientSocket(const char *ip);
#endif // ! _SOCKETTCP_H_
客户端源文件Client.c文章来源地址https://www.toymoban.com/news/detail-502517.html
#include"../Socket/Client.h"
#include<stdio.h>
#include<stdlib.h>
int main()
{
init_Socket();
SOCKET fd = CreateClientSocket("127.0.0.1");
printf("Server connected...\n");
printf("tip:Enter 'end' to end the connection\n");
//发送消息
char recvbuf[BUFSIZ] = { 0 };
char sendbuf[BUFSIZ] = { 0 };
char endbuf[BUFSIZ] = {"end"};
while (true)
{
//发送消息
printf("send>");
gets_s(sendbuf, BUFSIZ);
//输入'end'断开连接
if (strcmp(sendbuf,endbuf)== 0)
{
return false;
}
if (SOCKET_ERROR == send(fd, sendbuf, strlen(sendbuf), 0))
{
err("send");
}
//接收消息
if (0 < recv(fd, recvbuf, BUFSIZ, 0))
{
printf("recv:%s\n", recvbuf);
memset(recvbuf, 0, sizeof(recvbuf));
}
}
closesocket(fd);
close_Socket();
system("pause");
return 0;
}
bool init_Socket()
{
WSADATA wsadata;
if (0 != WSAStartup(MAKEWORD(2, 2), &wsadata))
{
printf("WSAStartup failed code %d", WSAGetLastError());
return false;
}
//WSA Windows异步套接字
//parm1 请求的Socket版本
//parm2 传出参数
return true;
}
bool close_Socket()
{
if (0 != WSACleanup())
{
printf("WSACleanup failed code %d", WSAGetLastError());
return false;
}
return true;
}
SOCKET CreateClientSocket(const char *ip)
{
//1 创建空的Socket
//af 地址协议族
//type 传输协议类型: 流式套接字 数据报套接字
//protocol 使用的具体传输协议
SOCKET fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (fd == INVALID_SOCKET)
{
err("socket");
return INVALID_SOCKET;
}
//2 与服务器建立连接
struct sockaddr_in addr;
addr.sin_family = AF_INET;
addr.sin_port = htons(PORT);
addr.sin_addr.S_un.S_addr =inet_addr(ip);
if (INVALID_SOCKET == connect(fd, (struct sockaddr*)&addr, sizeof(addr)))
{
err("connect");
return false;
}
return fd;
}
到了这里,关于Socket实现双机通信的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!