当前位置: 首页 > news >正文

socket UDP 环路回显的服务端

基于socket通讯的方式,无论用http或者udp或者自定义的协议,程序结构都是类似的。这个以UDP协议为例简要说明。

#include <stdio.h> // 标准输入输出库
#include <sys/types.h> // 提供了一些数据类型,如ssize_t
#include <sys/socket.h> // 提供socket编程的接口
#include <netinet/in.h> // 提供IPv4和IPv6地址的结构体定义
#include <arpa/inet.h> // 提供网络地址转换的函数,如inet_pton和inet_ntop(注意:这里应该是<arpa/inet.h>的拼写错误,正确的是<arpa/inet.h>,但您已经写对了)
#include <unistd.h> // 提供对POSIX操作系统API的访问,如close函数
#include <stdlib.h> // 标准库,提供内存分配、程序退出等函数
#include <sys/stat.h> // 提供对文件状态的操作,本程序中未使用
#include <fcntl.h> // 提供对文件控制的操作,如文件描述符的设置,本程序中未使用
#include <string.h> // 提供字符串处理的函数,如bzero#define N 64 // 定义缓冲区的大小int main(int argc, char const *argv[]) // 程序的主入口
{int sockfd; // 声明socket文件描述符sockfd = socket(AF_INET, SOCK_DGRAM, 0); // 创建一个UDP socketif(sockfd < 0) // 检查socket是否创建成功{perror("sock err"); // 如果创建失败,打印错误信息return -1; // 并返回-1表示错误}// 绑定套接字(ip+port)struct sockaddr_in addr; // 声明一个IPv4地址的结构体addr.sin_family = AF_INET; // 设置地址族为IPv4addr.sin_port = htons(atoi(argv[2])); // 将命令行参数转换为整数,并转换为网络字节序后设置为端口号// 自动绑定所有的本机网卡的地址addr.sin_addr.s_addr = INADDR_ANY; // 设置IP地址为INADDR_ANY,表示绑定到所有可用的网络接口int addrlen = sizeof(addr); // 获取地址结构体的长度if(bind(sockfd, (struct sockaddr *)&addr, addrlen) < 0) // 绑定socket到指定的地址和端口{perror("bind err"); // 如果绑定失败,打印错误信息return -1; // 并返回-1表示错误}ssize_t len; // 声明一个变量来存储接收到的数据长度char buf[N] = {0}; // 声明并初始化一个缓冲区来存储接收到的数据struct sockaddr_in cliaddr; // 声明一个结构体来存储客户端的地址信息// cliaddr接收客户端的地址while (1) // 进入一个无限循环来等待客户端的数据{bzero(buf, N); // 清空缓冲区len = recvfrom(sockfd, buf, N, 0, (struct sockaddr *)&cliaddr, &addrlen); // 从socket接收数据if(len > 0) // 如果成功接收到数据{printf("recv data=%s\n", buf); // 打印接收到的数据sendto(sockfd, buf, len, 0, (struct sockaddr *)&cliaddr, addrlen); // 将接收到的数据发送回客户端(注意:这里应该使用len而不是N)}}// 关闭socket(注意:由于有无限循环,这行代码实际上永远不会被执行)close(sockfd); // 关闭socket以释放资源return 0; // 程序正常结束
}

程序功能

这个程序实现了一个简单的UDP服务器,它监听一个指定的端口,接收来自客户端的数据,并将接收到的数据原封不动地发送回客户端(回显服务器)。

程序结构

  1. 初始化:创建socket,设置地址和端口,绑定socket。
  2. 接收数据:进入一个无限循环,等待并接收来自客户端的数据。
  3. 处理数据:打印接收到的数据,并将数据发送回客户端。
  4. 关闭socket(实际上不会被执行):在循环结束后关闭socket。

UDP发送和接收函数的参数

  • recvfrom()函数:
    • sockfd:socket文件描述符。
    • buf:指向存储接收数据的缓冲区的指针。
    • len:缓冲区的大小。
    • flags:标志位,通常设置为0。
    • src_addr:指向存储发送方地址信息的结构体的指针。
    • addrlen:指向存储地址结构体长度的变量的指针。
  • sendto()函数:
    • sockfd:socket文件描述符。
    • buf:指向要发送的数据的缓冲区的指针。
    • len:要发送的数据的长度(注意:这里应该使用实际接收到的数据长度,而不是缓冲区的大小)。
    • flags:标志位,通常设置为0。
    • dest_addr:指向存储接收方地址信息的结构体的指针。
    • addrlen:地址结构体的长度。

其中:

sockaddr_in 结构体在 IPv4 网络编程中用于表示一个 Internet 地址。这个结构体定义在 <netinet/in.h> 头文件中(在 POSIX 兼容的系统中),并且它通常用于 bind()connect()sendto()recvfrom() 等网络相关的系统调用中,以指定或接收网络地址信息。

 sockaddr_in 结构体的定义:

struct sockaddr_in {sa_family_t    sin_family; // 地址族,对于 IPv4 来说是 AF_INETuint16_t       sin_port;   // 端口号,使用网络字节序(大端模式)struct in_addr sin_addr;   // IPv4 地址,也使用网络字节序// 在某些实现中,可能有一个用于填充的数组,以确保结构体大小与 sockaddr 一致// char        sin_zero[8]; // 这通常用于保持结构体大小的一致性,但现代代码通常不直接使用它
};
  • sin_family:这是一个 sa_family_t 类型的字段,用于指定地址族。对于 IPv4 地址,它应该被设置为 AF_INET

  • sin_port:这是一个 uint16_t 类型的字段,用于指定端口号。端口号应该以网络字节序(大端模式)存储,这通常意味着在将主机字节序(小端模式或大端模式,取决于具体的系统架构)的端口号传递给网络之前,需要使用 htons() 函数进行转换。

  • sin_addr:这是一个 struct in_addr 类型的字段,它包含了一个 IPv4 地址。IPv4 地址也应该以网络字节序存储。struct in_addr 通常定义为一个包含单个 uint32_t 类型字段 s_addr 的结构体,用于存储 32 位的 IPv4 地址。

  • sin_zero:在某些实现中,sockaddr_in 结构体可能包含一个名为 sin_zero 的字符数组字段,用于填充,以确保结构体的大小与更通用的 sockaddr 结构体一致。然而,在现代的网络编程实践中,这个字段通常不被直接使用,而且可能在一些实现中根本不存在。如果你的系统定义中包含了这个字段,你通常不需要关心它,只需要确保在初始化 sockaddr_in 结构体时将其清零(尽管这通常不是必需的,因为系统调用通常只关心 sin_familysin_port, 和 sin_addr 字段)。

在使用 sockaddr_in 结构体时,你需要确保正确地设置 sin_familysin_port, 和 sin_addr 字段,并且如果 sin_zero 字段存在,也最好将其清零(尽管这通常不是错误源)。然后,你可以将这个结构体的地址作为参数传递给网络相关的系统调用。

 

相关文章:

socket UDP 环路回显的服务端

基于socket通讯的方式&#xff0c;无论用http或者udp或者自定义的协议&#xff0c;程序结构都是类似的。这个以UDP协议为例简要说明。 #include <stdio.h> // 标准输入输出库 #include <sys/types.h> // 提供了一些数据类型&#xff0c;如ssize_t #include <sy…...

springboot/ssm车辆违章信息管理系统Java代码web项目汽车违章处罚源码

基于springboot(可改ssm)htmlvue项目 springboot/ssm车辆违章信息管理系统Java代码web项目汽车违章处罚源码 开发语言&#xff1a;Java 框架&#xff1a;springboot/可改ssm vue JDK版本&#xff1a;JDK1.8&#xff08;或11&#xff09; 服务器&#xff1a;tomcat 数据库&…...

5G模组AT命令脚本-关闭模组的IP过滤功能

关闭模组的IP过滤功能 关闭模组的IP过滤功能 5G 模组通常使用nat方式为 下挂设备或上位机提供上网服务&#xff0c;默认情况&#xff0c;不做NAt的包无法经由 模组转发&#xff0c;如果禁掉这个限制 &#xff0c;可使用本文中的配置命令本脚本用于关闭模组的IP过滤功能&#xf…...

STM32:实现ping命令(lwip)

目录 0.协议介绍ICMP数据包格式ping指令发送的ICMP回声请求消息ping指令接收的ICMP回声应答消息1.实现步骤2.源码分析2.1 初始化函数2.2 发送函数2.3 回调函数2.3.1 函数定义:2.3.2 解析数据包:2.3.3.处理ICMP数据包:2.3.4 资源释放:2.3.5 返回值:3.源码展示4.源码链接5.问…...

nvm安装指定版本显示不存在及nvm ls-remote 列表只出现 iojs 而没有 node.js 解决办法

在使用 nvm install 18.20.3 安装 node 时会发现一直显示不存在此版本 Version 18.20.3 not found - try nvm ls-remote to browse available versions.使用 nvm ls-remote 查看可安装列表时发现&#xff0c;列表中只有 iojs 解决方法&#xff1a; 可以使用以下命令查看可安装…...

Spring Boot 中 WebClient 的实践详解

在现代微服务架构中&#xff0c;服务之间的通信至关重要。Spring Boot 提供了 WebClient&#xff0c;作为 RestTemplate 的替代方案&#xff0c;用于执行非阻塞式的 HTTP 请求。本文将详细讲解 WebClient 的实践&#xff0c;包括配置、使用场景以及常见的优化策略&#xff0c;帮…...

在GITHUB上传本地文件指南(详细图文版)

这份笔记简述了如何在GITHUB上上传文件夹的详细策略。 既是对自己未来的一个参考&#xff0c;又希望能给各位读者带来帮助。 详细步骤 打开目标文件夹&#xff08;想要上传的文件夹&#xff09; 右击点击git bash打开 GitHub创立新的仓库后&#xff0c;点击右上方CODE绿色按…...

【大模型系列篇】LLaMA-Factory大模型微调实践 - 从零开始

前一次我们使用了NVIDIA TensorRT-LLM 大模型推理框架对智谱chatglm3-6b模型格式进行了转换和量化压缩&#xff0c;并成功部署了推理服务&#xff0c;有兴趣的同学可以翻阅《NVIDIA TensorRT-LLM 大模型推理框架实践》&#xff0c;今天我们来实践如何通过LLaMA-Factory对大模型…...

30天学会Go--第7天 GO语言 Redis 学习与实践

30天学会Go–第7天 GO语言 Redis 学习与实践 文章目录 30天学会Go--第7天 GO语言 Redis 学习与实践前言一、Redis 基础知识1.1 Redis 的核心特性1.2 Redis 常见使用场景 二、安装 Redis2.1 在 Linux 上安装2.2 在 Windows 上安装2.3 使用 Docker 安装 Redis 三、Redis 常用命令…...

java 使用JSqlParser和CCJSqlParser 解析sql

maven <dependency><groupId>com.github.jsqlparser</groupId><artifactId>jsqlparser</artifactId><version>4.9</version> </dependency>解析SQL String sql "select aa,bb from b"; Statement statementCCJSq…...

基于spring boot的高校专业实习管理系统的设计与实现

文末获取源码和万字论文&#xff0c;制作不易&#xff0c;感谢点赞支持。 设计题目&#xff1a;基于spring boot的高校专业实习管理系统的设计与实现 摘 要 随着国内市场经济这几十年来的蓬勃发展&#xff0c;突然遇到了从国外传入国内的互联网技术&#xff0c;互联网产业从开…...

OpenCV相机标定与3D重建(11)机器人世界手眼标定函数calibrateRobotWorldHandEye()的使用

操作系统&#xff1a;ubuntu22.04 OpenCV版本&#xff1a;OpenCV4.9 IDE:Visual Studio Code 编程语言&#xff1a;C11 算法描述 计算机器人世界/手眼标定&#xff1a; w T b _{}^{w}\textrm{T}_b w​Tb​ 和 c T g _{}^{c}\textrm{T}_g c​Tg​。 cv::calibrateRobotWorldHa…...

计算机网络ENSP课设--三层架构企业网络

本课程设计搭建一个小型互联网&#xff0c;并模拟Internet的典型Web服务过程。通过此次课程设计&#xff0c;可以进一步理解Internet的工作原理和协议过程&#xff0c;并提高综合知识的运用能力和分析能力。具体目标包括&#xff1a; &#xff08;1&#xff09;掌握网络拓扑的…...

【openwrt】openwrt-21.02 基于IP地址使用ipset实现策略路由操作说明

openwrt版本信息 DISTRIB_ID=OpenWrt DISTRIB_RELEASE=21.02-SNAPSHOT DISTRIB_REVISION=r0-6bf6af1d5 DISTRIB_TARGET=mediatek/mt7981 DISTRIB_ARCH=aarch64_cortex-a53 DISTRIB_DESCRIPTION=OpenWrt 21.02-SNAPSHOT r0-6bf6af1d5 DISTRIB_TAINTS=no-all busybox override …...

Git:常用命令

一、查看当前分支 git branch 二、查看所有分支 git branch -a 三、切换到远程分支 git checkout origin/分支名 示例&#xff1a;git checkout origin/dev 四、拉取远程分支代码 git pull origin 分支名 示例&#xff1a;git pull origin dev 五、常用指令 查看暂存区…...

【2025最新版】搭建个人博客教程

【2025最新版】搭建个人博客教程 –小记&#xff1a; 在搭建我的这个博客之前我在CSDN也发布过一些文章&#xff0c;目前应该也是几千粉丝了&#xff0c;但是看到别人都是用自己博客写的就感觉自己很LOW&#xff0c;所以就想自己来搭建一个属于自己的个人博客。当然搭建博客的…...

微信小程序实现联动删除输入验证码框

以下是json代码 {"component": true,"usingComponents": {} }以下是wxml代码 <van-popup show"{{ show }}" bind:close"onClose" custom-class"extract"><image src"../../images/extract/icon1.png"…...

数据库中decimal、float 和 double区别

在计算机科学中&#xff0c;decimal、float 和 double 是用于表示和处理数值的不同数据类型。 - decimal 是一种精确的十进制浮点数表示&#xff0c;通常用于需要高精度计算的场景&#xff0c;比如财务应用。它能够精确表示小数&#xff0c;并且不会出现浮点数运算误差。 - flo…...

网络编程01

1. 概念 通过网络&#xff0c;让两个主机之间能够进行通信&#xff0c;基于这样的通信完成一定的功能 只要满足进程不同即可&#xff0c;即使是同一个主机&#xff0c;只要是不同的进程&#xff0c;基于网络完成编程 进行网络编程时&#xff0c;需要操作系统提供一组API&…...

el-dialog修改其样式不生效加deep也没用

场景 el-dialog标签直接写在了template下。 解决方法 在template中先写一层div&#xff0c;包裹住el-dialog。...

3.3.1_1 检错编码(奇偶校验码)

从这节课开始&#xff0c;我们会探讨数据链路层的差错控制功能&#xff0c;差错控制功能的主要目标是要发现并且解决一个帧内部的位错误&#xff0c;我们需要使用特殊的编码技术去发现帧内部的位错误&#xff0c;当我们发现位错误之后&#xff0c;通常来说有两种解决方案。第一…...

sqlserver 根据指定字符 解析拼接字符串

DECLARE LotNo NVARCHAR(50)A,B,C DECLARE xml XML ( SELECT <x> REPLACE(LotNo, ,, </x><x>) </x> ) DECLARE ErrorCode NVARCHAR(50) -- 提取 XML 中的值 SELECT value x.value(., VARCHAR(MAX))…...

leetcodeSQL解题:3564. 季节性销售分析

leetcodeSQL解题&#xff1a;3564. 季节性销售分析 题目&#xff1a; 表&#xff1a;sales ---------------------- | Column Name | Type | ---------------------- | sale_id | int | | product_id | int | | sale_date | date | | quantity | int | | price | decimal | -…...

零基础在实践中学习网络安全-皮卡丘靶场(第九期-Unsafe Fileupload模块)(yakit方式)

本期内容并不是很难&#xff0c;相信大家会学的很愉快&#xff0c;当然对于有后端基础的朋友来说&#xff0c;本期内容更加容易了解&#xff0c;当然没有基础的也别担心&#xff0c;本期内容会详细解释有关内容 本期用到的软件&#xff1a;yakit&#xff08;因为经过之前好多期…...

如何在网页里填写 PDF 表格?

有时候&#xff0c;你可能希望用户能在你的网站上填写 PDF 表单。然而&#xff0c;这件事并不简单&#xff0c;因为 PDF 并不是一种原生的网页格式。虽然浏览器可以显示 PDF 文件&#xff0c;但原生并不支持编辑或填写它们。更糟的是&#xff0c;如果你想收集表单数据&#xff…...

搭建DNS域名解析服务器(正向解析资源文件)

正向解析资源文件 1&#xff09;准备工作 服务端及客户端都关闭安全软件 [rootlocalhost ~]# systemctl stop firewalld [rootlocalhost ~]# setenforce 0 2&#xff09;服务端安装软件&#xff1a;bind 1.配置yum源 [rootlocalhost ~]# cat /etc/yum.repos.d/base.repo [Base…...

C# 表达式和运算符(求值顺序)

求值顺序 表达式可以由许多嵌套的子表达式构成。子表达式的求值顺序可以使表达式的最终值发生 变化。 例如&#xff0c;已知表达式3*52&#xff0c;依照子表达式的求值顺序&#xff0c;有两种可能的结果&#xff0c;如图9-3所示。 如果乘法先执行&#xff0c;结果是17。如果5…...

Spring AI Chat Memory 实战指南:Local 与 JDBC 存储集成

一个面向 Java 开发者的 Sring-Ai 示例工程项目&#xff0c;该项目是一个 Spring AI 快速入门的样例工程项目&#xff0c;旨在通过一些小的案例展示 Spring AI 框架的核心功能和使用方法。 项目采用模块化设计&#xff0c;每个模块都专注于特定的功能领域&#xff0c;便于学习和…...

Ubuntu系统复制(U盘-电脑硬盘)

所需环境 电脑自带硬盘&#xff1a;1块 (1T) U盘1&#xff1a;Ubuntu系统引导盘&#xff08;用于“U盘2”复制到“电脑自带硬盘”&#xff09; U盘2&#xff1a;Ubuntu系统盘&#xff08;1T&#xff0c;用于被复制&#xff09; &#xff01;&#xff01;&#xff01;建议“电脑…...

在 Visual Studio Code 中使用驭码 CodeRider 提升开发效率:以冒泡排序为例

目录 前言1 插件安装与配置1.1 安装驭码 CodeRider1.2 初始配置建议 2 示例代码&#xff1a;冒泡排序3 驭码 CodeRider 功能详解3.1 功能概览3.2 代码解释功能3.3 自动注释生成3.4 逻辑修改功能3.5 单元测试自动生成3.6 代码优化建议 4 驭码的实际应用建议5 常见问题与解决建议…...