欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  网络运营

【TCP回声服务器】一篇文章帮助你看懂TCP!

程序员文章站 2022-03-09 22:05:32
基于TCP的回声服务器1、TCP回声服务器的概念1.1 什么是TCP?1.2 什么是回声服务器?2、TCP回声服务器的编程模型2.1 编程模型2.2 服务器端编程步骤2.3 客户端编程步骤3、代码实现3.1 服务器端代码实现3.2 客户端代码实现4、结尾1、TCP回声服务器的概念1.1 什么是TCP?  TCP 的全称为传输控制协议(TCP,Transmission Control Protocol)是一种面向连接的、可靠的、基于字节流的传输层通信协议。1.2 什么是回声服务器?  回声服务器是指...

1、TCP回声服务器的概念

1.1 什么是TCP?

  TCP 的全称为传输控制协议(TCP,Transmission Control Protocol)是一种面向连接的、可靠的、基于字节流的传输层通信协议。

1.2 什么是回声服务器?

  回声服务器是指一种收到客户端发送的消息后,将消息回传至客户端服务器,这种服务器代码简单,但功能健全,非常适合帮助初学者理解网络编程中TCP协议。

2、TCP回声服务器的编程模型

2.1 编程模型

服务器端 S 客户端 C
创建套接字socket 创建套接字socket
准备通信地址(服务器的地址) 准备通信地址(服务器的地址)
绑定套接字和通信地址 连接服务器端S
监听
等待连接
接收/发送数据 发送/接收数据
关闭套接字 关闭套接字

2.2 服务器端编程步骤

  //创建套接字

  //准备通信地址

  //绑定socket与通信地址

  //监听

  //等待连接(因为TCP是有连接的通信,所以相比UDP多一个等待连接的过程)

  //接收数据,将接收到的数据存入缓冲区

  //发送数据,将缓冲区的数据发送出去

  //关闭套接字

2.3 客户端编程步骤

  //初始化网络库

  //创建套接字

  //准备通信地址

  //连接

  //发送数据

  //接收数据

  //关闭套接字

3、代码实现

3.1 服务器端代码实现

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/socket.h>
#include <netinet/in.h>

typedef struct sockaddr* SP;

int main(int argc,const char* argv[])
{
	// 创建socket
	int sockfd = socket(AF_INET,SOCK_STREAM,0);
	if(0 > sockfd)
	{
		perror("socket");
		return EXIT_FAILURE;
	}

	// 准备地址
	struct sockaddr_in addr = {};
	addr.sin_family = AF_INET;
	addr.sin_port = htons();
	addr.sin_addr.s_addr = INADDR_ANY;
	socklen_t addrlen = sizeof(addr);

	// 绑定
	if(bind(sockfd,(SP)&addr,addrlen))
	{
		perror("bind");
		return EXIT_FAILURE;
	}

	// 监听
	if(listen(sockfd,5))
	{
		perror("listen");
		return EXIT_FAILURE;
	}

	// 等待连接
	int clifd = accept(sockfd,(SP)&addr,&addrlen);
	if(0 > clifd)
	{
		perror("accept");
		return EXIT_FAILURE;
	}

	char buf[4096] = {};
	size_t buf_size = sizeof(buf);

	for(;;)
	{
		// 接收/返回数据
		size_t ret_size = read(clifd,buf,sizeof(buf));
		if(0 == strcmp("quit",buf))
		{
			printf("通信结束!\n");
			break;
		}	
		if(0 == ret_size)
		{
			printf("连接断开!\n");
			break;
		}
		printf("recv:[%s] bits:%d\n",buf,ret_size);
		strcat(buf,":return");
		write(clifd,buf,strlen(buf)+1);
	}

	// 关闭socket
	close(clifd);
}

3.2 客户端代码实现

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <winsock2.h>

int main(int argc, char const *argv[])
{
    // 初始化网络库
    WSADATA wsaData;
    if(WSAStartup(MAKEWORD(2,2),&wsaData))
    {
        perror("WSAStartup");
        return EXIT_FAILURE;
    }

    // 创建socket
    int clifd = socket(AF_INET,SOCK_STREAM,0);
    if(0 > clifd)
    {
        perror("socket");
        return EXIT_FAILURE;
    }

    // 准备通信地址(由服务端决定)
    struct sockaddr_in addr = {};
    addr.sin_family = AF_INET;
    addr.sin_port = htons(9876);
    addr.sin_addr.s_addr = inet_addr("47.97.229.46");

    // 连接
    if(connect(clifd,(struct sockaddr*)&addr,sizeof(addr)))
    {
        perror("connect");
        return EXIT_FAILURE;
    }

    char buf[4096] = {};
    size_t buf_size = sizeof(buf);

    for(;;)
    {
        printf(">>>");
        gets(buf);
        send(clifd,buf,strlen(buf),0);
        if(0 == strcmp("quit",buf))
        {
            printf("通信结束!\n");
            break;
        }
        size_t ret_size = recv(clifd,buf,buf_size,0);
        printf("recv:[%s],bits:%d",buf,ret_size);
    }

    // 关闭socket
    closesocket(clifd);
    return 0;
}

4、结尾

  本文主要展示了TCP回声服务器的基本概念,及代码的实现,旨在更好的帮助初学者理解TCP通信的规则及格式,代码较为简单,功能实现的也很简单,但相信通过阅读本文一定能对TCP模式的通信有一个更深的认识。

本文地址:https://blog.csdn.net/weixin_48994377/article/details/108575318