基于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 什么是回聲服務器?
??回聲服務器是指一種收到客戶端發送的訊息后,將訊息回傳至客戶端服務器,這種服務器代碼簡單,但功能健全,非常適合幫助初學者理解網路編程中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://www.uj5u.com/qita/54061.html
標籤:其他
上一篇:對于鴻蒙的一點見解
下一篇:Python基礎入門
