TCP的三次握手与四次挥手
发布人:shili8
发布时间:2025-01-12 04:32
阅读次数:0
**TCP 的三次握手与四次挥手**
TCP (Transmission Control Protocol) 是一种面向连接的传输控制协议,用于在 IP 网络中传递数据包。它提供了可靠的、有序的数据传输服务。在 TCP 通信过程中,客户端和服务器之间需要进行三次握手来建立连接,而当通信结束时,也需要进行四次挥手来释放资源。
**TCP 三次握手**
在 TCP 三次握手过程中,客户端和服务器之间进行了以下三个步骤:
1. **第一次握手(SYN)**:客户端向服务器发送一个 SYN 包,这个包包含了客户端的序列号(Sequence Number)和确认号(Acknowledgment Number)。这个包的目的地是服务器的 IP 地址和端口号。
2. **第二次握手(SYN-ACK)**:服务器收到客户端的 SYN 包后,会回复一个 SYN-ACK 包,这个包包含了服务器的序列号和确认号。这个包的目的地仍然是客户端的 IP 地址和端口号。
3. **第三次握手(ACK)**:客户端收到服务器的 SYN-ACK 包后,会回复一个 ACK 包,这个包包含了客户端的序列号和确认号。这个包的目的地仍然是服务器的 IP 地址和端口号。
以下是一个示例代码:
c// 客户端代码#include <stdio.h> #include <stdlib.h> #include <string.h> #include <sys/socket.h> #include <netinet/in.h> int main() { int sockfd = socket(AF_INET, SOCK_STREAM,0); if (sockfd < 0) { perror("socket"); exit(1); } struct sockaddr_in server_addr; server_addr.sin_family = AF_INET; server_addr.sin_port = htons(8080); inet_pton(AF_INET, "127.0.0.1", &server_addr.sin_addr); if (connect(sockfd, (struct sockaddr *)&server_addr, sizeof(server_addr)) < 0) { perror("connect"); exit(1); } char syn_msg[] = "Hello, server!"; send(sockfd, syn_msg, strlen(syn_msg),0); // 等待服务器的 SYN-ACK 包 recv(sockfd, NULL,0, MSG_DONTWAIT); // 回复一个 ACK 包 char ack_msg[] = "ACK"; send(sockfd, ack_msg, strlen(ack_msg),0); close(sockfd); return0; } //服务器代码#include <stdio.h> #include <stdlib.h> #include <string.h> #include <sys/socket.h> #include <netinet/in.h> int main() { int sockfd = socket(AF_INET, SOCK_STREAM,0); if (sockfd < 0) { perror("socket"); exit(1); } struct sockaddr_in server_addr; server_addr.sin_family = AF_INET; server_addr.sin_port = htons(8080); inet_pton(AF_INET, "127.0.0.1", &server_addr.sin_addr); if (bind(sockfd, (struct sockaddr *)&server_addr, sizeof(server_addr)) < 0) { perror("bind"); exit(1); } listen(sockfd,5); struct sockaddr_in client_addr; socklen_t client_len = sizeof(client_addr); int connfd = accept(sockfd, (struct sockaddr *)&client_addr, &client_len); if (connfd < 0) { perror("accept"); exit(1); } char syn_ack_msg[] = "SYN-ACK"; send(connfd, syn_ack_msg, strlen(syn_ack_msg),0); // 等待客户端的 ACK 包 recv(connfd, NULL,0, MSG_DONTWAIT); close(connfd); return0; }
**TCP 四次挥手**
在 TCP 四次挥手过程中,客户端和服务器之间进行了以下四个步骤:
1. **第一次挥手(FIN)**:客户端向服务器发送一个 FIN 包,这个包包含了客户端的序列号和确认号。这个包的目的地是服务器的 IP 地址和端口号。
2. **第二次挥手(ACK)**:服务器收到客户端的 FIN 包后,会回复一个 ACK 包,这个包包含了服务器的序列号和确认号。这个包的目的地仍然是客户端的 IP 地址和端口号。
3. **第三次挥手(FIN)**:服务器向客户端发送一个 FIN 包,这个包包含了服务器的序列号和确认号。这个包的目的地仍然是客户端的 IP 地址和端口号。
4. **第四次挥手(ACK)**:客户端收到服务器的 FIN 包后,会回复一个 ACK 包,这个包包含了客户端的序列号和确认号。这个包的目的地仍然是服务器的 IP 地址和端口号。
以下是一个示例代码:
c// 客户端代码#include <stdio.h> #include <stdlib.h> #include <string.h> #include <sys/socket.h> #include <netinet/in.h> int main() { int sockfd = socket(AF_INET, SOCK_STREAM,0); if (sockfd < 0) { perror("socket"); exit(1); } struct sockaddr_in server_addr; server_addr.sin_family = AF_INET; server_addr.sin_port = htons(8080); inet_pton(AF_INET, "127.0.0.1", &server_addr.sin_addr); if (connect(sockfd, (struct sockaddr *)&server_addr, sizeof(server_addr)) < 0) { perror("connect"); exit(1); } char fin_msg[] = "FIN"; send(sockfd, fin_msg, strlen(fin_msg),0); // 等待服务器的 ACK 包 recv(sockfd, NULL,0, MSG_DONTWAIT); close(sockfd); return0; } //服务器代码#include <stdio.h> #include <stdlib.h> #include <string.h> #include <sys/socket.h> #include <netinet/in.h> int main() { int sockfd = socket(AF_INET, SOCK_STREAM,0); if (sockfd < 0) { perror("socket"); exit(1); } struct sockaddr_in server_addr; server_addr.sin_family = AF_INET; server_addr.sin_port = htons(8080); inet_pton(AF_INET, "127.0.0.1", &server_addr.sin_addr); if (bind(sockfd, (struct sockaddr *)&server_addr, sizeof(server_addr)) < 0) { perror("bind"); exit(1); } listen(sockfd,5); struct sockaddr_in client_addr; socklen_t client_len = sizeof(client_addr); int connfd = accept(sockfd, (struct sockaddr *)&client_addr, &client_len); if (connfd < 0) { perror("accept"); exit(1); } char ack_msg[] = "ACK"; send(connfd, ack_msg, strlen(ack_msg),0); // 等待客户端的 FIN 包 recv(connfd, NULL,0, MSG_DONTWAIT); close(connfd); return0; }
以上是 TCP 的三次握手与四次挥手过程中的详细步骤和示例代码。