网络通信2—UDP 模型程序编写步骤(参照 Ubuntu 16.04 版本)

2023-05-16

UDP 模型程序编写步骤
一、UDP基础模型
  • 服务器流程
  1. step 1:创建 socket() 套接字接口并判断
sockfd = socket(AF_INET, SOCK_DGRAM, 0);
if (sockfd == -1)
{perror("socket failed");return -1;}
  1. step 2:设置服务器 IP 和 Port
memset(&seraddr, 0, sizeof(seraddr));
seraddr.sin_family = AF_INET;
seraddr.sin_port = htons(8888);
seraddr.sin_addr.s_addr = inet_addr("127.0.0.1");
  1. step 3:绑定 IP 和 Port 并判断
ret = bind(sockfd, (struct sockaddr *)&seraddr, sizeof(seraddr));
if (sockfd == -1)
{perror("bind failed");return -1;}
  1. step 4:接收数据并判断
ret = recvfrom(sockfd, buf, sizeof(buf), (struct sockaddr *)&cliaddr, &addrlen);
if (ret == -1)
{perror("recvfrom failed");return -1;}
printf("recv from %s: %d, content: %s\n", inet_ntoa(cliaddr.sin_addr), ntohs(cliaddr.sin_port), buf);
  1. step 5:发送数据并判断
ret = sendto(sockfd, buf, sizeof(buf), (struct sockaddr *)&cliaddr, sizeof(cliaddr));
if (ret == -1)
{perror("sendto failed");return -1;}
  1. step 6:关闭服务器
close(sockfd);
  1. step 7:检查头文件和变量是否添加和定义
  • 客户端流程
  1. step 1:创建 socket() 套接字接口并判断
sockfd = socket(AF_INET, SOCK_DGRAM, 0);
if (sockfd == -1)
{perror("socket failed");return -1;}
  1. step 2:设置服务器 IP 和 Port
memset(&seraddr, 0, sizeof(seraddr));
seraddr.sin_family = AF_INET;
seraddr.sin_port = htons(8888);
seraddr.sin_addr.s_addr = inet_addr("127.0.0.1");
  1. step 3:发送数据并判断
ret = sendto(sockfd, buf, sizeof(buf), 0, (struct sockaddr *)&seraddr, sizeof(seraddr));
if (ret == -1)
{perror("sendto failed");return -1;}
  1. step 4:接收数据并判断输出
ret = recvfrom(sockfd, buf, sizeof(buf), 0, (struct sockaddr *)&seraddr, &addrlen);
if (ret == -1)
{perror("recvfrom failed");return -1;}
printf("recv from %s: %d\ncontent: %s\n", inet_ntoa(seraddr.sin_addr), ntohs(seraddr.sin_port), buf);
  1. step 5:关闭连接
close(sockfd);
  1. step 6:检查头文件和变量是否添加和定义
二、UDP 循环服务器模型
  • 服务器流程
  1. step 1:创建 socket() 套接字接口并判断
sockfd = socket(AF_INET, SOCK_DGRAM, 0);
if (sockfd == -1)
{perror("socket failed");return -1;}
  1. step 2:设置服务器 IP 和 Port
memset(&seraddr, 0, sizeof(seraddr));
seraddr.sin_family = AF_INET;
seraddr.sin_port = htons(8888);
seraddr.sin_addr.s_addr = inet_addr("127.0.0.1");
  1. step 3:绑定 IP 和 Port 并判断
ret = bind(sockfd, (struct sockaddr *)&seraddr, sizeof(seraddr));
if (sockfd == -1)
{perror("bind failed");return -1;}
  1. step 4:设置循环接收数据
while (1)
{...}
  1. step 5:接收数据并判断
ret = recvfrom(sockfd, buf, sizeof(buf), (struct sockaddr *)&cliaddr, &addrlen);
if (ret == -1)
{perror("recvfrom failed");return -1;}
  1. step 6:设置跳出循环条件
if (!strncmp("quit", buf, 4)
{printf("client IP: %s Port: %d is disconnected\n", inet_ntoa(cliaddr.sin_addr), ntohs(cliaddr.sin_port);continue;}
printf("recv from %s: %d, content: %s\n", inet_ntoa(cliaddr.sin_addr), ntohs(cliaddr.sin_port), buf);
  1. step 7:发送数据并判断
ret = sendto(sockfd, buf, sizeof(buf), (struct sockaddr *)&cliaddr, sizeof(cliaddr));
if (ret == -1)
{perror("sendto failed");return -1;}
printf("send successfully!\n");
  1. step 8:关闭服务器
close(sockfd);
  1. step 9:检查头文件和变量是否添加和定义
  • 客户端流程
  1. step 1:创建 socket() 套接字接口并判断
sockfd = socket(AF_INET, SOCK_DGRAM, 0);
if (sockfd == -1)
{perror("socket failed");return -1;}
  1. step 2:设置服务器 IP 和 Port
memset(&seraddr, 0, sizeof(seraddr));
seraddr.sin_family = AF_INET;
seraddr.sin_port = htons(8888);
seraddr.sin_addr.s_addr = inet_addr("127.0.0.1");
  1. step 3:设置循环发送并获取数据
while (1)
{fgets(buf, sizeof(buf), stdin);
buf[strlen(buf)-1] = '\0';
...}
  1. step 4:发送数据并判断
ret = sendto(sockfd, buf, sizeof(buf), 0, (struct sockaddr *)&seraddr, sizeof(seraddr));
if (ret == -1)
{perror("sendto failed");return -1;}
  1. step 5:设置退出循环条件
if (!strncmp("quit", buf, 4))
break;
  1. step 6:接收数据并判断输出
ret = recvfrom(sockfd, buf, sizeof(buf), 0, (struct sockaddr *)&seraddr, &addrlen);
if (ret == -1)
{perror("recvfrom failed");return -1;}
printf("recv from %s: %d\ncontent: %s\n", inet_ntoa(seraddr.sin_addr), ntohs(seraddr.sin_port), buf);
  1. step 7:关闭连接
close(sockfd);
  1. step 8:检查头文件和变量是否添加和定义
三、UDP 并发服务器模型
  • 服务器流程
  1. step 1:创建 socket() 套接字接口并判断
sockfd = socket(AF_INET, SOCK_DGRAM, 0);
if (sockfd == -1)
{perror("socket failed");return -1;}
  1. step 2:设置服务器 IP 和 Port
memset(&seraddr, 0, sizeof(seraddr));
seraddr.sin_family = AF_INET;
seraddr.sin_port = htons(8888);
seraddr.sin_addr.s_addr = inet_addr("127.0.0.1");
  1. step 3:绑定 IP 和 Port 并判断
ret = bind(sockfd, (struct sockaddr *)&seraddr, sizeof(seraddr));
if (sockfd == -1)
{perror("bind failed");return -1;}
  1. step 4:设置信号处理函数,防止僵尸进程
signal(SIGCHLD, SIG_IGN);
  1. step 5:设置循环接收数据
while (1)
{...}
  1. step 6:接收数据并判断
ret = recvfrom(sockfd, buf, sizeof(buf), (struct sockaddr *)&cliaddr, &addrlen);
if (ret == -1)
{perror("recvfrom failed");return -1;}
  1. step 7:设置跳出循环条件
if (!strncmp("quit", buf, 4)
{printf("client IP: %s Port: %d is disconnected\n", inet_ntoa(cliaddr.sin_addr), ntohs(cliaddr.sin_port);continue;}
printf("recv from %s: %d, content: %s\n", inet_ntoa(cliaddr.sin_addr), ntohs(cliaddr.sin_port), buf);
  1. step 8:创建子进程并判断
pid = fork();
if (pid < 0)
{perror("fork failed");return -1}
  1. step 9:父进程继续
else if (pid > 0)
continue;
  1. step 10:子进程重新建立 socket 套接字并判断
else
{close(sockfd);
fd = socket(AF_INET, SOCK_DGRAM, 0);
if (fd == -1)
{perror("socket failed");return -1;}
  1. step 11:建立与客户端连接并判断
ret = connect(fd, (struct sockaddr *)&cliaddr, sizeof(cliaddr));
if (ret == -1)
{perror("connect failed");return -1;}
  1. step 12:设置子进程循环内发送数据并判断
while (1)
{ret = send(fd, buf, sizeof(buf), 0);
if (ret == -1)
{perror("send failed");return -1;}
printf("send successfully!\n");
  1. step 13:接收数据并判断
ret = recvfrom(sockfd, buf, sizeof(buf), (struct sockaddr *)&cliaddr, &addrlen);
if (ret == -1)
{perror("recvfrom failed");return -1;}
  1. step 14:设置跳出循环条件
if (!strncmp("quit", buf, 4)
{printf("client IP: %s Port: %d is disconnected\n", inet_ntoa(cliaddr.sin_addr), ntohs(cliaddr.sin_port);break;}
printf("recv from %s: %d, content: %s\n", inet_ntoa(cliaddr.sin_addr), ntohs(cliaddr.sin_port), buf);
  1. step 15:关闭客户端连接并退出子进程
close(fd);
exit(0);
  1. step 16:关闭服务器
close(sockfd);
  1. step 17:检查头文件和变量是否添加和定义
  • 客户端流程(同循环客户端流程)
  1. step 1:创建 socket() 套接字接口并判断
sockfd = socket(AF_INET, SOCK_DGRAM, 0);
if (sockfd == -1)
{perror("socket failed");return -1;}
  1. step 2:设置服务器 IP 和 Port
memset(&seraddr, 0, sizeof(seraddr));
seraddr.sin_family = AF_INET;
seraddr.sin_port = htons(8888);
seraddr.sin_addr.s_addr = inet_addr("127.0.0.1");
  1. step 3:设置循环发送并获取数据
while (1)
{fgets(buf, sizeof(buf), stdin);
buf[strlen(buf)-1] = '\0';
...}
  1. step 4:发送数据并判断
ret = sendto(sockfd, buf, sizeof(buf), 0, (struct sockaddr *)&seraddr, sizeof(seraddr));
if (ret == -1)
{perror("sendto failed");return -1;}
  1. step 5:设置退出循环条件
if (!strncmp("quit", buf, 4))
break;
  1. step 6:接收数据并判断输出
ret = recvfrom(sockfd, buf, sizeof(buf), 0, (struct sockaddr *)&seraddr, &addrlen);
if (ret == -1)
{perror("recvfrom failed");return -1;}
printf("recv from %s: %d\ncontent: %s\n", inet_ntoa(seraddr.sin_addr), ntohs(seraddr.sin_port), buf);
  1. step 7:关闭连接
close(sockfd);
  1. step 8:检查头文件和变量是否添加和定义
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

网络通信2—UDP 模型程序编写步骤(参照 Ubuntu 16.04 版本) 的相关文章

  • Leetcode每日一题——“合并两个有序数组”

    各位CSDN的uu们你们好呀 xff0c 又到小雅兰的愉快题解时候啦 xff0c 今天 xff0c 我们的题目内容是合并两个有序数组 xff0c 下面 xff0c 让我们进入合并两个有序数组的世界吧 示例 1 xff1a 输入 xff1a
  • Leetcode每日一题——“链表的中间结点”

    各位CSDN的uu们你们好呀 xff0c 今天 xff0c 小雅兰愉快的刷题内容是链表的中间结点 嘿嘿 xff0c 小雅兰的单链表还在偷懒ing xff0c 一直没有更新 xff0c 最近应该会更新出来 下面 xff0c 就让我们进入链表的
  • VRPN-体验

    VRPN简介 VRPN提供封装在库里的一套类 xff0c 在VR系统中 xff0c 用来为应用程序和物理外设提供网络传输接口 详细点击这里 VRPN源码获取 git clone https github com vrpn vrpn git
  • 单链表——“数据结构与算法”

    各位CSDN的uu们你们好呀 xff0c 今天 xff0c 小雅兰的内容终于是我们心心念念的单链表啦 xff0c 这一块呢 xff0c 是一个很重要的部分 xff0c 也是一个对目前的我来说 xff0c 比较困难的部分 xff0c 下面 x
  • springboot服务端接口外网远程调试,并实现HTTP服务监听【内网穿透】

    文章目录 前言1 本地环境搭建1 1 环境参数1 2 搭建springboot服务项目 2 内网穿透2 1 安装配置cpolar内网穿透2 1 1 windows系统2 1 2 linux系统 2 2 创建隧道映射本地端口2 3 测试公网地
  • MCSM面板一键搭建我的世界服务器-外网远程联机【内网穿透】

    文章目录 前言1 Mcsmanager安装2 创建Minecraft服务器3 本地测试联机4 内网穿透4 1 安装cpolar内网穿透4 2 创建隧道映射内网端口 5 远程联机测试6 配置固定远程联机端口地址6 1 保留一个固定TCP地址6
  • 初识MySQL数据库——“MySQL数据库”

    各位CSDN的uu们你们好呀 xff0c 小雅兰好久没有更文啦 xff0c 确实是心有余而力不足 xff0c 最近学习的内容太难了 xff0c 这篇博客又是小雅兰的新专栏啦 xff0c 主要介绍的是一些MySQL数据库的知识点 xff0c
  • Windows10本地搭建网站教程【内网穿透】

    文章目录 概述1 搭建一个静态Web站点2 本地浏览测试站点是否正常3 本地站点发布公网可访问3 1 安装cpolar内网穿透3 2 创建隧道映射公网地址3 3 获取公网URL地址 4 公网远程访问内网web站点5 配置固定二级子域名5 1
  • MySQL环境搭建——“MySQL数据库”

    各位CSDN的uu们你们好呀 xff0c 小雅兰又来啦 xff0c 好久没有更文啦 xff0c 今天继续 xff01 xff01 xff01 今天小雅兰的内容是MySQL环境搭建 xff0c 下面 xff0c 让我们进入MySQL数据库的世
  • 在树莓派上搭建WordPress博客网站【内网穿透】

    文章目录 概述安装 PHP安装MySQL数据库安装 Wordpress设置您的 WordPress 数据库设置 MySQL MariaDB创建 WordPress 数据库 WordPress configuration将WordPress站
  • 双链表——“数据结构与算法”

    各位CSDN的uu们你们好呀 xff0c 今天 xff0c 小雅兰又回来了 xff0c 到了好久没有更新的数据结构与算法专栏 xff0c 最近确实发现自己有很多不足 xff0c 需要学习的内容也有很多 xff0c 所以之后更新文章可能不会像
  • Windows在外远程桌面控制macOS【macOS自带VNC远程】

    文章目录 前言1 测试局域网内远程控制1 1 macOS打开屏幕共享1 2 测试局域网内VNC远程控制 2 测试公网远程控制2 1 macOS安装配置cpolar内网穿透2 2 创建tcp隧道 xff0c 指向5900端口 3 测试公网远程
  • 初学正点原子Ministm32板串口实验

    本章将实现如下功能 xff1a STM32 通过串口和上位机的对话 xff0c STM32 在收到上位机发过来的字符串后 xff0c 原原本本的返回给上位机 本章分为如下几个小节 xff1a 1 STM32串口简介 2 硬件设计 3 软件设
  • Qt网络通信实战(聊天室小项目TCP实现)

    一 UDP与TCP的区别 用一个表格来显示这两者的区别 比较项TCPUDP是否连接面向连接无连接传输是否可靠可靠不可靠流量控制提供不提供工作方式全双工可以是全双工应用场合大量数据少量数据速度慢 快 我们这里采用TCP 当有新的连接出现时就会
  • 常用坐标系及坐标系之间的变换

    坐标系统 xff1a 有哪些坐标系 xff0c 他们之间的变换矩阵是怎样的 xff1f xff08 主要是3个坐标系 3 个角 xff09 地理坐标系 xff08 n系 xff09 坐标系原点On取为飞行器质心 Xn轴向指向北 xff0c
  • ulimit命令用法详解

    ulimit用来限制每个用户可使用的资源 xff0c 如CPU 内存 句柄等 一 用法 ulimit SHacdefilmnpqrstuvx 限制 参数详解 S xff1a 表示软限制 超出设定的值会告警 H xff1a 表示硬限制 xff
  • java的数组反转

    Java中数组反转一般有两个思路 xff0c 第一个是新建一个临时数组 xff0c 把原来的数组内各值倒着给放进去 public class ArrayReverse public static void main String args
  • Ardupilot移植经验分享(1)

    目录 前言背景为什么写这篇文章移植Ardupilot的方法有两种底层适配提取应用层代码两种方法对比 准备阅读源码阅读官方开发者wiki选择编译平台下载编译源代码切换版本的正确方式编译老版本手动下载编译器修改PATH配置配置ubuntu以支持
  • 国产UOS系统之——安装wxPython

    安装依赖库 xff1a sudo apt get install libgtk 3 dev sudo apt get install libcanberra gtk module sudo apt get install pkg confi
  • OpenHarmonyllvm交叉编译工具链编译介绍

    一 工具链基础介绍 1 1 工具链下载 repo init u https gitee com OpenHarmony manifest git b master m llvm toolchain xml repo sync c repo

随机推荐

  • 一键配置Ubuntu的OpenHarmony基础编译环境

    一键配置Ubuntu的OpenHarmony基础编译环境 一 配置前说明 该更新源仅适用于Ubuntu以下系列 Ubuntu18 04 Ubuntu20 04 Ubuntu22 04 强烈推荐Ubuntu20 04 xff0c 本人使用的一
  • 卸载Proteus后再次安装出错解决办法

    相信有人和我一样 xff0c 在卸载Proteus后再次安装时会跳过下图这一步 然后安装完了注册时会弹出修改注册 LICENCE失败 xff0c 从而导致破解不成功 xff0c 怎么办呢 xff1f 本人解决方法 xff1a 1 首先正常安
  • STM32cubeMx来对单片机串口1进行初始化

    步骤如下 xff1a 打开STM32CubeMX软件并新建一个工程在Pinout amp Configuration选项卡中选择正确的芯片型号 xff0c 然后在Pinout视图中找到串口1相关的引脚 默认情况下 xff0c 串口1使用PA
  • Keil 头文件源程序代码——Math.h

    MATH H Prototypes for mathematic functions Copyright c 1988 2002 Keil Elektronik GmbH and Keil Software Inc All rights r
  • Keil头文件代码—Absacc

    ABSACC H Direct access to 8051 extended 8051 and NXP 8051MX memory areas Copyright c 1988 2010 Keil Elektronik GmbH and
  • reg52.h中直接定义了P3^4等引脚,但是P1^5引脚没有明确表示出来?

    实际上reg52 h中已经定义了 34 sfr P0 61 0x80 sfr P1 61 0x90 sfr P2 61 0xA0 sfr P3 61 0xB0 34 等引脚的地址 xff0c 如果取P1 5的引脚 xff0c 只需要表示成
  • 关于scanf很多人不知道的小秘密

    今天忽然想到一个问题 xff0c 假如我利用scanf想给变量a输入一个 d的整数 xff0c 结果不小心输入了一个字符串yf或者是123ff后会怎么样呢 xff1f 哈哈 xff0c 自己测试了一下 xff0c 结果发现 xff0c 当你
  • 关于sizeof(*p+1)的那些事

    今天老铁在写程序时发现一个意外 xff0c 在char a 61 1 3 5 7 9 p 61 a 程序求sizeof p 43 1 时遇到一些意外 xff0c 本来以为会是1 xff0c 结果却出意料的是4 xff0c 这就有些尴尬了 x
  • 求解完数

    完数的定义 xff1a 一个数如果恰好等于它的因子之和 xff0c 这个数就称为 完数 例如 xff1a 6 61 1 xff0b 2 xff0b 3 如果需要求解1000或者10000以内的所有完数 xff0c 怎么做呢 xff1f 分析
  • 查找100-200以内素数

    只能被1和其本身整除的数称为素数 xff0c 1不是素数 xff0c 因为简单 xff0c 所以不做解释 xff0c 直接上程序 源代码如下 xff1a Search all prime numbers from 101 to 200 in
  • 实现4个按键控制8个LED灯1个数码管程序

    按要求C语言编程 xff0c 实现4个按键控制8个LED灯1个数码管程序 具体要求如下 xff1a 1 按键一 xff0c 清零作用 无论数码管以前显示何内容 xff0c 都归零 xff0c 显示0 xff1b 2 按键二 xff0c 加一
  • Linux 关机/重启指令

    Linux系统下关机指令只有root用户终端才能下达 xff08 Linux里切换用户可以用 su root 输入密码便进入 root 用户 xff09 xff0c 同时其他终端也会接收到 如root用户发出关机指令 其他终端也会收到相应的
  • C 语言中的goto、 break 和 continue 语句使用

    一 goto 语句 goto 语句为无条件跳转 xff0c goto 语句后面带一个标识符 xff0c 该标识符是同一个函数 内某条语句的标号 标号可以出现在任何可执行语句的前面 xff0c 并且以一个冒号 xff1a 作为后缀 gt Fi
  • 云台控制协议VISCA、PELCO-D、PELCO-P

    原 云台控制协议VISCA PELCO D PELCO P 2013年12月02日 18 42 21 autowanglei 阅读数 xff1a 10146 更多 lt div class 61 34 tags box space 34 g
  • 目录和文件权限与 umask 关系

    一 权限 文件权限 xff1a r xff1a 读取文件内容的权限 w xff1a 新增 修改和删除文件内容的权限 x xff1a 执行文件的权限 例如 xff1a 一个文件a sh xff0c 它的权限是rw xff0c 使用 a sh
  • open 函数的 flag 参数和错误代码

    一 flag 参数 定义头文件 xff1a lt bits fcntl linux h gt 必选参数说明 xff1a define O ACCMODE 0003 xff1a 读写文件操作时取出 flag 的低两位 define O RDO
  • 系统全局变量 errno 是如何获得 errno.h 中的值的呢?

    很多时候我们在使用 errno 的时候都知道它代表的是 errno h 中的错误值 xff0c 可是为什么它就是代表那些值的呢 xff1f 系统在哪里给它赋值了呢 xff1f 故事就要从源头开始 1 errno 全局变量是在哪里定义的 xf
  • const pointer

    int a b const int p 61 a 与int const p 61 a 是一样的 表示p可以指向a xff0c 也可以改变指向b xff0c 但是不能通过指针p来修改a的值 p 61 b p 61 4 int const q
  • I_O —基础概念(参照 Ubuntu 16.04 版本)

    一 文件的概念 定义 xff1a 所谓文件是指一组相关数据的有序集合 xff0c 这个数据集有一个名称 xff0c 叫文件名 如源程序文件 xff0c 目标文件 xff0c 可执行文件 xff0c 头文件等文件通常是在驻留在外部介质上的 x
  • 网络通信2—UDP 模型程序编写步骤(参照 Ubuntu 16.04 版本)

    UDP 模型程序编写步骤 一 UDP基础模型 服务器流程 step 1 xff1a 创建 socket 套接字接口并判断 sockfd 61 socket AF INET SOCK DGRAM 0 if sockfd 61 61 1 per