TCP/IP网络编程(一) 理解网络编程和套接字

文章目录

    • 理解网络编程和套接字
      • 网络编程和套接字概要
      • 构建套接字
      • 编写 Hello World 服务器端
      • 构建请求连接套接字
      • 在Linux平台下运行
    • 基于Linux的文件操作
      • 打开文件
      • 关闭文件
      • 将数据写入文件
      • 读取文件中的数据

理解网络编程和套接字

网络编程和套接字概要

网络编程就是编写程序使两台联网的计算机相互交换数据

为了与远程计算机进行数据传输,需要连接因特网,而编程种的套接字就是用来连接该网络的工具。

构建套接字

1.调用soecket函数创建套接字

#include<sys/socket.h>
int socket(int domain, int type, int protocol);——>成功返回文件描述符,失败返回-1

2.调用bind函数给套接字分配地址

#include<sys/socket.h>
int bind(int sockfd, struct sockaddr *myaddr, socklen_t addrlen);——>成功返回0,失败返回-1

3.调用listen函数将套接字转化为可接受连接的状态

#include<sys/socket.h>
int listen(int sockfd, int backlog);——>成功时返回0,失败返回-1

4.调用accept函数接受连接请求

#include<sys/socket.h>
int accept(int sockfd, struct sockaddr *addr, socklen_t *addrlen);——>成功时返回文件描述符,失败返回-1

网络编程中接受连接请求的套接字创建过程总结如下:

1.调用soecket函数创建套接字

2.调用bind函数给套接字分配地址

3.调用listen函数将套接字转化为可接受连接的状态

4.调用accept函数接受连接请求

编写 Hello World 服务器端

服务器端(server)是能受理连接请求的程序

hello_server.c

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#include <sys/socket.h>void error_handling(char *message);int main(int argc, char *argv[])
{int serv_sock;int clnt_sock;struct sockaddr_in serv_addr;struct sockaddr_in clnt_addr;socklen_t clnt_addr_size;char message[]="Hello World!";if(argc!=2){printf("Usage : %s <port>\n", argv[0]);exit(1);}serv_sock=socket(PF_INET, SOCK_STREAM, 0);if(serv_sock == -1)error_handling("socket() error");memset(&serv_addr, 0, sizeof(serv_addr));serv_addr.sin_family=AF_INET;serv_addr.sin_addr.s_addr=htonl(INADDR_ANY);serv_addr.sin_port=htons(atoi(argv[1]));if(bind(serv_sock, (struct sockaddr*) &serv_addr, sizeof(serv_addr))==-1 )error_handling("bind() error"); if(listen(serv_sock, 5)==-1)error_handling("listen() error");clnt_addr_size=sizeof(clnt_addr);  clnt_sock=accept(serv_sock, (struct sockaddr*)&clnt_addr,&clnt_addr_size);if(clnt_sock==-1)error_handling("accept() error");  write(clnt_sock, message, sizeof(message));close(clnt_sock);	close(serv_sock);return 0;
}void error_handling(char *message)
{fputs(message, stderr);fputc('\n', stderr);exit(1);
}

构建请求连接套接字

客户端程序只有调用socket函数创建套接字和调用connect函数向服务器发出连接请求两个步骤

hello_client.c

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#include <sys/socket.h>void error_handling(char *message);int main(int argc, char* argv[])
{int sock;struct sockaddr_in serv_addr;char message[30];int str_len;if(argc!=3){printf("Usage : %s <IP> <port>\n", argv[0]);exit(1);}sock=socket(PF_INET, SOCK_STREAM, 0);if(sock == -1)error_handling("socket() error");memset(&serv_addr, 0, sizeof(serv_addr));serv_addr.sin_family=AF_INET;serv_addr.sin_addr.s_addr=inet_addr(argv[1]);serv_addr.sin_port=htons(atoi(argv[2]));if(connect(sock, (struct sockaddr*)&serv_addr, sizeof(serv_addr))==-1) error_handling("connect() error!");str_len=read(sock, message, sizeof(message)-1);if(str_len==-1)error_handling("read() error!");printf("Message from server: %s \n", message);  close(sock);return 0;
}void error_handling(char *message)
{fputs(message, stderr);fputc('\n', stderr);exit(1);
}

请求连接函数

#include<sys/socket.h>
int connect(int sockfd,struct sockaddr *serv_addr, socklen_t addrlen);——>成功返回0,失败返回-1

在Linux平台下运行

gcc hello_server.c -o hserver
./hserver 9190

现在已经打开了服务端,但是调用的accept函数还没有返回,接下来运行客服端

gcc hello_client.c -o hclient
./hclient 192.168.233.20 9190
输出: Hello World!

基于Linux的文件操作

打开文件

#include <sys/type.h>
#include <sys/stat.h>
#include <fcnt.h>int open(const char *path, int flag);——>成功返回文件描述符,失败返回-1path   文件名的字符串地址flag   文件打开模式信息

文件打开模式

打开模式				含义
O_CREAT			   必要时创建文件
O_TRUNC			   删除全部现有数据
O_APPEND		   维持现有数据,保存末尾
O_RDONLY		   只读打开
O_WRONLY	   	   只写打开
O_RDWR			   读写打开

关闭文件

#include<unistd.h>int close(int fd);——>成功返回0,失败返回-1

将数据写入文件

#include<unistd.h>
ssize_t write(int fd, const void *buf, size_t nbytes);——>成功时返回写入的字节数,失败返回-1buf保存要传输数据的缓冲地址nbytes要传输的字节数

函数定义中,size_t是通过typedef声明的unsigned int类型,对于ssize_t来说s代表signed,ssize_t为signed int类型

lower_open.c

#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>void error_handling(char* message);int main(void)
{int fd;char buf[]="Let's go!\n";fd=open("data.txt", O_CREAT|O_WRONLY|O_TRUNC);if(fd==-1)error_handling("open() error!");printf("file descriptor: %d \n", fd);if(write(fd, buf, sizeof(buf))==-1)error_handling("write() error!");close(fd);return 0;
}void error_handling(char* message)
{fputs(message, stderr);fputc('\n', stderr);exit(1);
}

读取文件中的数据

与write函数对应,read函数是用来接受数据的

#include<unistd.h>ssize_t read(int fd, void *buf, size_t nbytes)——>成功返回接受的字节数,失败返回-1

lower_read.c

#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>#define BUF_SIZE 100void error_handling(char* message);int main(void)
{int fd;char buf[BUF_SIZE];fd=open("data.txt", O_RDONLY);if( fd==-1)error_handling("open() error!");printf("file descriptor: %d \n" , fd);if(read(fd, buf, sizeof(buf))==-1)error_handling("read() error!");printf("file data: %s", buf);close(fd);return 0;
}void error_handling(char* message)
{fputs(message, stderr);fputc('\n', stderr);exit(1);
}

ps:

在文中出现好多次void error_handling(char* message)函数,这个是打印错误信息的,也可以用perror函数,例如
#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>int main()
{int fd = open(data.txt, O_RDONLY);if(fd == -1){perror("open:");}
}

更多资料点击 GitHub 欢迎各位读者去Star

⭐学术交流群Q 754410389 持续更新中~~~

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

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

相关文章

安装完SSL证书之后会过期吗?

在建立安全的互联网连接时&#xff0c;SSL证书被广泛应用于加密数据传输&#xff0c;保护用户隐私和敏感信息的安全。然而&#xff0c;SSL证书并不是永久有效的&#xff0c;它们都有一个特定的有效期。本文将详细介绍SSL证书的有效期&#xff0c;解释为什么它们会过期以及如何管…

java八股文面试[多线程]——Synchronized的底层实现原理

笔试&#xff1a;画出Synchronized 线程状态流转实现原理图 synchronized关键字解决的是多个线程之间访问资源的同步性&#xff0c;synchronized 翻译为中文的意思是同步&#xff0c;也称之为”同步锁“。 synchronized的作用是保证在同一时刻&#xff0c; 被修饰的代码块或方…

目标检测的训练过程

数据集准备(Dataset preparation): 收集或创建带有注释的数据集&#xff0c;其中包括图像或帧以及标注&#xff0c;指定了其中物体的位置和类别。标注通常包括边界框坐标&#xff08;x、y、宽度、高度&#xff09;和相应的类别标签。数据预处理&#xff1a; 将图像调整为模型能…

Day49|leetcode 121. 买卖股票的最佳时机、122.买卖股票的最佳时机II

leetcode 121. 买卖股票的最佳时机 题目链接&#xff1a;121. 买卖股票的最佳时机 - 力扣&#xff08;LeetCode&#xff09; 视频链接&#xff1a;动态规划之 LeetCode&#xff1a;121.买卖股票的最佳时机1_哔哩哔哩_bilibili 题目概述 给定一个数组 &#xff0c;它的第 个元…

从探索到明确,比特币与美股等传统资产相关性如何?

早期阶段&#xff0c;比特币经历了一段摸索和模仿的时期&#xff0c;这是因为当比特币刚刚出现时&#xff0c;比特币的价值和用途在这一阶段并不明确&#xff0c;人们对其性质和潜力还不太了解。 然而&#xff0c;随着时间的推移&#xff0c;比特币去中心化、固定供应上限等特点…

2024王道408数据结构P144 T18

2024王道408数据结构P144 T18 思考过程 首先还是先看题目的意思&#xff0c;让我们在中序线索二叉树里查找指定结点在后序的前驱结点&#xff0c;这题有一点难至少对我来说…我讲的不清楚理解一下我做的也有点糊涂。在创建结构体时多两个变量ltag和rtag&#xff0c;当ltag0时…

巨人互动|游戏出海游戏出海的趋势如何

随着全球游戏市场的不断扩大和消费者需求的多元化&#xff0c;游戏出海作为游戏行业的重要战略之一&#xff0c;正面临着新的发展趋势。本文小编将讲讲游戏出海的趋势&#xff0c;探讨一下未来游戏出海的发展方向与前景。 巨人互动|游戏出海&2023国内游戏厂商加快“出海”发…

Git操作

Git 操作方法 Git 是一个分布式版本控制系统&#xff0c;用于管理项目的源代码。 gitee新建仓库提示如下 具体介绍看下面 1. 创建仓库 初始化本地仓库 使用以下命令在本地目录中初始化一个新的 Git 仓库&#xff1a; git init克隆远程仓库 使用以下命令克隆一个远程仓库…

CentOS下查看 ssd 寿命

SSD写入量达到设计极限&#xff0c;颗粒擦写寿命耗尽后会导致磁盘写入速度非常缓慢&#xff0c;读取正常。 使用smartctl及raid卡管理软件查看硬盘smart信息可以发现Media_Wearout_Indicator值降为1&#xff0c;表明寿命完全耗尽。 涉及范围 所有SSD处理方案 查看SSD smart信…

使用WSL修改docker文件存储位置

按照以下说明将其重新定位到其他驱动器/目录&#xff0c;并保留所有现有的Docker数据。 首先&#xff0c;右键单击Docker Desktop图标关闭Docker桌面&#xff0c;然后选择退出Docker桌面&#xff0c;然后&#xff0c;打开命令提示符&#xff1a; wsl --list -v您应该能够看到&a…

AI自动驾驶也“区分人种”?有色人种和儿童面临更高碰撞风险

8月27日消息&#xff0c;随着人工智能&#xff08;AI&#xff09;的快速发展&#xff0c;尤其是在自动驾驶汽车领域&#xff0c;这项技术给人类带来了巨大的便利。 然而&#xff0c;据最新的研究发现&#xff0c;自动驾驶汽车中的行人检测软件可能存在一些严重问题&#xff0c;…

【Java架构-版本控制】-Git进阶

本文摘要 Git作为版本控制工具&#xff0c;使用非常广泛&#xff0c;在此咱们由浅入深&#xff0c;分三篇文章&#xff08;Git基础、Git进阶、Gitlab搭那家&#xff09;来深入学习Git 文章目录 本文摘要1. Git分支管理2. Git分支本质2.1 分支流转流程(只新增文件)2.2 分支流转流…

项目 - 后端技术栈转型方案

前言 某开发项目的后端技术栈比较老了&#xff0c;现在想换到新的技术栈上。使用更好的模式、设计思想、更合理的架构等&#xff0c;为未来的需求迭代做铺垫。怎么办呢&#xff1f;假设系统目前在线上运行着的&#xff0c;直接整体换的话耗时太久&#xff0c;且中间还有新的需…

1.6 编写双管道ShellCode

本文将介绍如何将CMD绑定到双向管道上&#xff0c;这是一种常用的黑客反弹技巧&#xff0c;可以让用户在命令行界面下与其他程序进行交互&#xff0c;我们将从创建管道、启动进程、传输数据等方面对这个功能进行详细讲解。此外&#xff0c;本文还将通过使用汇编语言一步步来实现…

pdf如何删除其中一页?了解一下这几种删除方法

pdf如何删除其中一页&#xff1f;随着电子文档的广泛应用&#xff0c;PDF已成为最常见的文档格式之一。然而&#xff0c;有时候你可能会发现&#xff0c;你的PDF文档中包含了一些多余的页面&#xff0c;或者你需要删除其中的某一页。那么&#xff0c;该如何删除PDF中的页面呢&a…

【Java List与对象】List<T>对象和对象List<T>的区别(125)

List&#xff1c;T&#xff1e;对象&#xff1a;对象里面的元素属性包含List&#xff1c;T&#xff1e;(只有一个对象)&#xff1b; 对象List&#xff1c;T&#xff1e;&#xff1a;List&#xff1c;T&#xff1e;里面的数据是对象类型(可以有多组对象&#xff0c;但必须是同一…

精准运营,智能决策!解锁天翼物联水利水务感知云

面向智慧水利/水务数字化转型需求&#xff0c;天翼物联基于感知云平台创新能力&#xff0c;提供涵盖水利水务泛协议接入、感知云水利/水务平台、水利/水务感知数据治理、数据看板在内的水利水务感知云服务&#xff0c;构建水利水务感知神经系统新型数字化底座&#xff0c;实现智…

Python之动态规划

序言 最近在学习python语言&#xff0c;语言有通用性&#xff0c;此文记录复习动态规划并练习python语言。 动态规划&#xff08;Dynamic Programming&#xff09; 动态规划是运筹学的一个分支&#xff0c;是求解决策过程最优化的过程。20世纪50年代初&#xff0c;美国数学家…

vue使用命令npm install 报错 cb() never called!

一.错误说明,npm本身下载就慢&#xff0c;有可能是网络的问题。 二.解决方案,把npm设置成淘宝镜像后,再重新npm install npm config set registry https://registry.npm.taobao.org 三.还是不行&#xff0c;还会出现同样的问题&#xff0c;那接下来先清理一下npm缓存 npm cache…