《TCP/IP网络编程》阅读笔记--基于 TCP 的半关闭

news2024/11/25 20:22:21

目录

1--基于TCP的半关闭

1-1--TCP单方面完全断开的问题

1-2--shutdown()函数

1-3--半关闭的必要性

2--基于半关闭的文件传输程序


1--基于TCP的半关闭

1-1--TCP单方面完全断开的问题

        Linux 系统中的 close 函数会将 TCP Socket 的连接完全断开,这意味着不能收发数据(关闭了输入流和输出流),这可能会导致主机 A 无法收到主机 B 的数据(主机A的输入流被关闭了); 

1-2--shutdown()函数

#include <sys/socket.h>
int shutdown(int sock, int howto);
// 成功时返回 0, 失败时返回 -1
// sock 表示需要断开的 Socket 的文件描述符
// howto 表示传递断开的方式信息

        shutdown() 函数可以避免上面完全关闭导致数据丢失的问题,其通过指定断开的方式来选择性地断开输入流、输出流

        断开的方式通过第二个参数来指定,其中 SHUT_RD 表示断开输入流SHUT_WR 表示断开输出流SHUT_RDWR 表示同时断开 I/O 流

1-3--半关闭的必要性

        对于服务器端/客户端的数据传输问题,传输文件的服务器端只需连续传输文件数据即可,但客户端无法知道何时结束数据的接收;

        为了解决上述问题,服务器端应向客户端传递一个 EOF 表示文件传输结束,而客户端通过接收到 EOF 知晓文件传递结束,可以停止接收数据

        断开输出流可以向外传递 EOF(无论是设置 SHUT_WR 还是直接使用 close() 函数);

2--基于半关闭的文件传输程序

服务器端:

// gcc file_server.c -o file_server
// ./file_server 9190

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#include <sys/socket.h>

#define BUF_SIZE 30

void error_handling(char *message){
    fputs(message, stderr);
    fputc('\n', stderr);
    exit(1);
}

int main(int argc, char *argv[]){
    int serv_sd, clnt_sd;
    FILE* fp;
    char buf[BUF_SIZE];
    int read_cnt;

    struct sockaddr_in serv_adr, clnt_adr;
    socklen_t clnt_adr_sz;

    if(argc != 2){
        printf("Usage : %s <port>\n", argv[0]);
        exit(1);
    }

    fp = fopen("file_server.c", "rb");
    serv_sd = socket(PF_INET, SOCK_STREAM, 0);

    memset(&serv_adr, 0, sizeof(serv_adr));
    serv_adr.sin_family = AF_INET;
    serv_adr.sin_addr.s_addr = htonl(INADDR_ANY);
    serv_adr.sin_port = htons(atoi(argv[1]));

    bind(serv_sd, (struct sockaddr*)&serv_adr, sizeof(serv_adr));
    listen(serv_sd, 5);

    clnt_adr_sz = sizeof(clnt_adr);
    clnt_sd = accept(serv_sd, (struct sockaddr*)&clnt_adr, &clnt_adr_sz);

    while(1){
        read_cnt = fread((void*)buf, 1, BUF_SIZE, fp);
        if(read_cnt < BUF_SIZE){
            write(clnt_sd, buf, read_cnt);
            break;
        }
        write(clnt_sd, buf, BUF_SIZE);
    }

    shutdown(clnt_sd, SHUT_WR);
    read(clnt_sd, buf, BUF_SIZE);
    printf("Message from client: %s \n", buf);

    fclose(fp);
    close(clnt_sd);
    close(serv_sd);
    return 0;

}

客户端:

// gcc file_client.c -o file_client
// ./file_client 127.0.0.1 9190

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#include <sys/socket.h>

#define BUF_SIZE 30

void error_handling(char *message){
    fputs(message, stderr);
    fputc('\n', stderr);
    exit(1);
}

int main(int argc, char *argv[]){
    int sd;
    FILE* fp;
    char buf[BUF_SIZE];
    int read_cnt;
    struct sockaddr_in serv_adr;

    if(argc != 3){
        printf("Usage : %s <IP> <port>\n", argv[0]);
        exit(1);
    }

    fp = fopen("receive.dat", "wb");
    sd = socket(PF_INET, SOCK_STREAM, 0);

    memset(&serv_adr, 0, sizeof(serv_adr));
    serv_adr.sin_family = AF_INET;
    serv_adr.sin_addr.s_addr = inet_addr(argv[1]);
    serv_adr.sin_port = htons(atoi(argv[2]));

    connect(sd, (struct sockaddr*)&serv_adr, sizeof(serv_adr));

    while((read_cnt = read(sd, buf, BUF_SIZE)) != 0){
        fwrite((void*)buf, 1, read_cnt, fp);
    }

    puts("Received file data");
    write(sd, "Thank you", 10);
    fclose(fp);
    close(sd);
    return 0;
}

运行结果:

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/980391.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

项目(智慧教室)第四部分,页面交互功能

一。页面构思 1.标题栏 大标题&#xff1a;智慧教室管理系统 小标题&#xff1a;灯光&#xff0c;报警&#xff0c;风扇&#xff0c;温度&#xff0c;湿度&#xff0c;光照 2.样式设计 背景设置。字体设置&#xff08;字体大小&#xff0c;格式&#xff0c;颜色&#xff09; 3.…

算法之双指针题型:

双指针例题小总结&#xff1a; 力扣27&#xff1a; 移除元素 力扣题目链接 双指针分为&#xff1a; 快慢双指针&#xff1a;同一个起点&#xff0c;同向出发 相向双指针&#xff1a;从两端出发&#xff0c;方向相反&#xff0c;终会相遇 经典的双指针&#xff08;快慢双指…

ESP32用作经典蓝牙串口透传模块与手机进行串口通信

ESP32用作经典蓝牙串口透传模块与手机进行串口通信 简介ESP32开发板Arduino程序手机与ESP32开发板进行蓝牙串口透传通信总结 简介 ESP32-WROOM-32模组集成了双模蓝牙包括传统蓝牙&#xff08;BR/EDR&#xff09;、低功耗蓝牙&#xff08;BLE&#xff09;和 Wi-Fi&#xff0c;具…

python实现三维应力云图

要画三维的应力分布云图&#xff0c;包括深度&#xff08;Z轴&#xff09;、X轴、Y轴&#xff0c;可以使用Matplotlib库中的mplot3d子库来实现 import numpy as np import matplotlib.pyplot as plt from mpl_toolkits.mplot3d import Axes3D# 生成示例数据 x np.linspace(0,…

利用细胞流式术测定基因组大小和倍性

在denovo基因组测序中&#xff0c;通常会先预估基因组大小&#xff0c;杂合度等信息&#xff0c;根据基因组大小和复杂度来判断测序数据的深度&#xff0c;组装基因组的难易程度等。 预测基因组大小的方法主要有两种&#xff0c;基于Kmer频率的survey分析和基于流式细胞术&…

“指针跃动”受邀参加全球贸易服务峰会

“指针跃动”受邀参加全球贸易服务峰会 有“服”同享 共赢未来 引子 在全球化日益盛行的今天&#xff0c;贸易不再仅仅是物质的交流&#xff0c;更涉及到服务、理念、文化和科技的共享。中国国际服务贸易交易会全球贸易服务峰会&#xff0c;就是这个趋势的集中体现。在这次峰会…

连接虚拟机报错 Could not connect to ‘192.168.xxx.xxx‘ (port 22): Connection failed.

使用xshell连接虚拟机报错 Connecting to 192.168.204.129:22… Could not connect to ‘192.168.204.129’ (port 22): Connection failed. Type help’ to learn how to use Xshell prompt. 按网上的方法 是否能ping通内外网 ping www.baidu.com防火墙是否关闭 firewal…

数据分析综述

⭐️⭐️⭐️⭐️⭐️欢迎来到我的博客⭐️⭐️⭐️⭐️⭐️ &#x1f434;作者&#xff1a;秋无之地 &#x1f434;简介&#xff1a;CSDN爬虫、后端、大数据领域创作者。目前从事python爬虫、后端和大数据等相关工作&#xff0c;主要擅长领域有&#xff1a;爬虫、后端、大数据…

PyCharm 虚拟环境搭建

Anaconda搭建虚拟环境 安装 前往Anaconda官网&#xff08;https://www.anaconda.com/products/individual&#xff09;&#xff0c;下载适合您操作系统的Anaconda版本&#xff0c;建议下载最新的稳定版。这里可以直接进入这个&#xff1a;https://repo.anaconda.com/archive/ …

【python技巧】替换文件中的某几行

【python技巧】替换文件中的某几行 1. 背景描述2. 单行修改-操作步骤3. 多行修改-操作步骤 1. 背景描述 最近在写一个后端项目&#xff0c;主要的操作就是根据用户的前端数据&#xff0c;在后端打开项目中的代码文件&#xff0c;修改对应位置的参数&#xff0c;因为在目前的后…

Spring高手之路14——深入浅出:SPI机制在JDK与Spring Boot中的应用

文章目录 1. SPI解读&#xff1a;什么是SPI?2. SPI在JDK中的应用示例3. SPI在Spring框架中的应用3.1 传统Spring框架中的SPI思想3.2 Spring Boot中的SPI思想 4. SPI在JDBC驱动加载中的应用5. 如何通过Spring Boot自动配置理解SPI思想6. SPI&#xff08;Service Provider Inter…

库的相关操作

目录 一、创建数据库 1&#xff0c;创建数据库规则 2、创建案例 二、字符集和校验规则 1、查看系统默认字符集以及校验规则 2、查看数据库支持的字符集以及校验规则 3、校验规则对数据库的影响 三、操纵数据库 1、查看数据库和目前所在数据库 2、显示创建语句 3、修改数据库 4、…

Modbus协议详解2:通信方式、地址规则、主从机通信状态

首先我们要清楚&#xff1a;Modbus是一种串行链路上的主从协议&#xff0c;在通信线路上只能有一个主机存在&#xff0c;不会有多主机存在的情况。虽然主机只有一个&#xff0c;但是从机是可以有多个的。 Modbus的通信过程都是由主机发起的&#xff0c;从机在接收到主机的请求后…

Python Spyder下载、安装和使用教程

Spyder 是一款功能强大的 Python IDE&#xff08;集成开发环境&#xff09;&#xff0c;集编写、运行、调试 Python 程序于一身&#xff0c;可以安装到多个平台上&#xff0c;包括 Windows、Linux、Mac OS X。 图 1 Spyder Logo Spyder 除了拥有一般 IDE 普遍具有的编辑器、调…

ardupilot 安装gcc-arm-none-eabi编译工具

目录 文章目录 目录摘要0简介1.下载网站2.安装摘要 本节主要记录ardupilot使用的编译器安装过程。 0简介 gcc-arm-none-eabi是GNU项目下的软件,是一个面向裸机arm的编译器。那么说了这么多介绍,它都包含什么具体功能又怎么安装与使用呢,我们继续。 1.下载网站 gcc-arm-n…

随着iPhone 15降临,是时候扔掉所有的Lightning充电器了

自从苹果推出Lightning端口&#xff08;一直追溯到iPhone 5&#xff09;十多年后&#xff0c;你可能已经积累了相当多的Lightning电缆和配件。好吧&#xff0c;在下周的苹果活动之前&#xff0c;所有关于iPhone 15的传言都表明你不再需要它们了。 与最好的iPad和最好的MacBook…

防水出色的骨传导耳机,更适合户外运动,南卡Runner Pro 4S体验

已经接近尾声的夏季依然酷热&#xff0c;对于运动爱好者来说&#xff0c;这确实也是锻炼的好时机&#xff0c;无论是一会儿就能大汗淋漓的HIIT&#xff0c;还是是各种清凉的水上运动&#xff0c;在健身的同时&#xff0c;戴上一副耳机享受音乐&#xff0c;都会更加痛快一些。 相…

PMP认证有什么好处?

pmp项目管理认证拿到证书&#xff0c;可以升职、人脉资源拓展、得到更多的项目管理工作机会、获得同行、同事及公司上级认可、有能更履行更多工作职责、项目管理专业技能提升、战略和商业管理技能提升、领导技能提升、建立信心、证明从事职业的专业度同&#xff0c;不仅可以学到…

点云切片的实现(PCL)C++

一、实现逻辑 1、通过PCL库的getMinMax3D得到xyz轴上的最大最小值&#xff1b; 函数原型&#xff1a; pcl::getMinMax3D(const pcl::PointCloud<PointT> &cloud, POintT &min_pt, PointT &max_pt) 2、设置切片厚度&#xff0c;计算某一轴方向上的切片数量&a…

冠达管理:有色金属迎顺周期行情 板块估值降至历史低位

近期&#xff0c;A股地产链相继迸发&#xff0c;家居用品、房地产服务等细分板块持续反弹。沉寂多时的地产链上游——有色金属板块相同遭到资金青睐。证券时报数据宝统计&#xff0c;8月28日以来&#xff0c;有色金属指数累计上涨近6%&#xff0c;跑赢同期上证指数。 从个股来…