第14章 UDP编程(3)_利用UDP实现广播功能
3. 广播的介绍
(1)广播
①广播实现一对多的通信,如QQ群
②它通过向广播地址发送数据报文实现的
(2)SO_BROADCAST选项
①SO_BROADCAST选项控制着UDP套接字是否能发送广播数据报,选项的类型为int,非零意味着“是”。
②注意,该选项只有UDP套接字可以使用,TCP是不能使用广播的。
(3)其它选项:SO_SNDBUF和SO_RCVBUF选项
①每一个套接字有一个发送缓冲区和接收缓冲区,这两个缓冲区由底层协议使用。
②接收缓冲区存放由协议接收的数据直到被应用程序读走。发送缓冲区存放应用写出的数据直接被协议发送出去。
③SO_SNDBUF和SO_RCVBUF选项分别控制发送和接收缓冲区的大小,他们的类型均为int,以字节为单位。
(4)广播地址
①如果用{netID, subnetID, hostID}来表示IPv4地址,那么有四类的广播地址,用-1表示所有比特都为1的字段。
②子网广播地址:{netID, subnetID, -1}。这类地址编排指定子网上的所有接口。例如,如果我们对C类地址192.168采用8位子网ID,那么192.168.2.255将是192.168.2子网上所有接口的子网广播地址。路由器通常不转发这类广播。
③全部子网广播地址{netID,-1,-1}。这类广播地址编排指定网络上的所有子网。现在很少这样用。
④受限广播地址:{-1,-1,-1,-1}或{255,255,255,255}。路由器从不转发目的地址为255.255.255.255的IP数据报。
【编程实验】利用UDP发送广播(多对多或一对多)
//receiver.c
#include <netdb.h>
#include <sys/socket.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <signal.h>
#include <memory.h> int sockfd; void sig_handler(int signo)
{
if(signo == SIGINT){
printf("receiver will exit\n");
close(sockfd);
exit();
}
} int main(int argc, char* argv[])
{
if(argc < ){
fprintf(stderr, "usage: %s port\n", argv[]);
exit();
} if(signal(SIGINT, sig_handler) == SIG_ERR){
perror("signal sigint error");
exit();
} //创建套接字
sockfd = socket(AF_INET, SOCK_DGRAM, ); //UDP协议
if(sockfd < ){
perror("socket error");
exit();
} //绑定地址,以便在指定的端口上接收广播
struct sockaddr_in recvAddr;
memset(&recvAddr, , sizeof(recvAddr));
recvAddr.sin_family = AF_INET; //IPv4
recvAddr.sin_port = htons(atoi(argv[])); //port
recvAddr.sin_addr.s_addr = INADDR_ANY; //由系统指定IP if(bind(sockfd, (struct sockaddr*)&recvAddr, sizeof(recvAddr)) < ){
perror("bind error");
exit();
} //接收广播消息
char buff[];
struct sockaddr_in sendAddr;
socklen_t len = sizeof(sendAddr);
while(){
memset(buff, , sizeof(buff));
memset(&sendAddr, , sizeof(sendAddr));
if(recvfrom(sockfd, buff, sizeof(buff), , (struct sockaddr*)&sendAddr, &len) < ){
perror("recvfrom error");
exit();
}else{
char ip[];
inet_ntop(AF_INET, &sendAddr.sin_addr.s_addr, ip, sizeof(ip));
int port = ntohs(sendAddr.sin_port);
printf("%s(%d): %s\n", ip, port, buff);
} }
}
/*输出结果
[root@localhost 14.udp]# gcc -o bin/broadcast src/broadcast.c
[root@localhost 14.udp]# bin/receiver
usage: bin/receiver port
[root@localhost 14.udp]# bin/receiver 8888
192.168.32.100(40894): hello world!
192.168.32.100(33915): hello world!
192.168.32.100(48427): hello world!
^Creceiver will exit
*/
//broadcast.c
#include <netdb.h>
#include <sys/socket.h>
#include <stdio.h>
#include <stdlib.h>
#include <memory.h> int main(int argc, char* argv[])
{
if(argc < ){
fprintf(stderr, "usage: %s ip port\n", argv[]);
exit();
} //创建套接字
int sockfd = socket(AF_INET, SOCK_DGRAM, ); //UDP协议
if(sockfd < ){
perror("socket error");
exit();
} //设置为广播方式发送消息
int opt = ;
setsockopt(sockfd, SOL_SOCKET, SO_BROADCAST, &opt, sizeof(opt)); struct sockaddr_in recvAddr; //指定广播的接收者地址信息。
memset(&recvAddr, , sizeof(recvAddr));
recvAddr.sin_family = AF_INET;
recvAddr.sin_port = htons(atoi(argv[])); //注意,不指定IP(广播为255),只说明接收者的端口
inet_pton(AF_INET, argv[], &recvAddr.sin_addr.s_addr); printf("I will broadcast...\n");
char* info = "hello world!";
size_t size = strlen(info)* sizeof(char);
if(sendto(sockfd, info, size, , (struct sockaddr*)&recvAddr, sizeof(recvAddr)) < ){
perror("sendto error");
exit();
}else{
printf("broadcast success\n");
} close(sockfd); return ;
}
/*输出结果
* [root@localhost 14.udp]# bin/broadcast 192.168.32.100 8888
* I will broadcast...
* broadcast success
* [root@localhost 14.udp]# bin/broadcast 192.168.32.100 8888
* I will broadcast...
* broadcast success
* [root@localhost 14.udp]# bin/broadcast 192.168.32.100 8888
* I will broadcast...
* broadcast success
*/
第14章 UDP编程(3)_利用UDP实现广播功能的更多相关文章
- 第14章 UDP编程(1)_UDP客户端服务器模型
		
1. UDP编程模型 (1)UDP客户端服务器模型 ①客户端可以不调用bind()而直接与服务器通讯. ②UDP是无连接的,因此服务端不需要调用accept和listen,客户端也无需调用connec ...
 - Twisted UDP编程技术
		
实战演练1:普通UDP UDP是一种无连接对等通信协议,没有服务器和客户端概念,通信的任何一方均可通过通信原语直接和其他方通信 1.相对于TCP,UDP编程只需定义DatagramProtocol子类 ...
 - Socket编程实践(12) --UDP编程基础
		
UDP特点 无连接,面向数据报(基于消息,不会粘包)的传输数据服务; 不可靠(可能会丢包, 乱序, 反复), 但因此普通情况下UDP更加高效; UDP客户/服务器模型 UDP-API使用 #inclu ...
 - udp编程中,一次能发送多少个bytes为好?
		
在进行UDP编程的时候,我们最容易想到的问题就是,一次发送多少bytes好? 当然,这个没有唯一答案,相对于不同的系统,不同的要求,其得到的答案是不一样的,我这里仅对 像ICQ一类的发送聊天消息 ...
 - 《Android开发艺术探索》读书笔记 (13) 第13章 综合技术、第14章 JNI和NDK编程、第15章 Android性能优化
		
第13章 综合技术 13.1 使用CrashHandler来获取应用的Crash信息 (1)应用发生Crash在所难免,但是如何采集crash信息以供后续开发处理这类问题呢?利用Thread类的set ...
 - 【机器学习实战】第14章 利用SVD简化数据
		
第14章 利用SVD简化数据 SVD 概述 奇异值分解(SVD, Singular Value Decomposition): 提取信息的一种方法,可以把 SVD 看成是从噪声数据中抽取相关特征.从生 ...
 - 老李推荐:第14章1节《MonkeyRunner源码剖析》 HierarchyViewer实现原理-面向控件编程VS面向坐标编程
		
老李推荐:第14章1节<MonkeyRunner源码剖析> HierarchyViewer实现原理-面向控件编程VS面向坐标编程 poptest是国内唯一一家培养测试开发工程师的培训机 ...
 - 《mysql必知必会》学习_第14章_20180806_欢
		
第14章:使用子查询. 子查询是镶嵌在其他查询里面,相当其他的select查询的条件来. P91 select order_num from where prod_id='tnt2'; #检索条件 ...
 - Windows核心编程:第14章 探索虚拟内存
		
Github https://github.com/gongluck/Windows-Core-Program.git //第14章 探索虚拟内存.cpp: 定义应用程序的入口点. // #inclu ...
 
随机推荐
- 逆向路由器固件之敏感信息泄露 Part2
			
之前的文章中详细介绍了各种解包路由器固件的工具.解包之后就获得了固件中的文件.下一步就是分析文件寻找漏洞了.这次分析的目标是Trendnet路由器,分析的漏洞是一个远程获取路由器权限的漏洞. 初步分析 ...
 - git stash,git cherry-pick
			
git stash: 备份当前的工作区的内容,从最近的一次提交中读取相关内容,让工作区保证和上次提交的内容一致.同时,将当前的工作区内容保存到Git栈中.git stash pop: 从Git栈中读取 ...
 - SWIFT中数字格式
			
SWIFT中格式化数字比较常用的应该就是以下几种格式了. var formatter = NSNumberFormatter() //formatter.numberStyle = NSNumberF ...
 - MyEclipse10 添加反编译JadClipse插件
			
工具/原料 MyEclipse10.0.7+net.sf.jadclipse_3.3.0.jar+jad.exe net.sf.jadclipse_3.3.0.jar+jad.exe下载地址:ht ...
 - 如何使用firebug
			
什么是Firebug 从事了数年的Web开发工作,越来越觉得现在对WEB开发有了更高的要求.要写出漂亮的HTML代码:要编写精致的CSS样式表展示每个页面模块:要调试javascript给页面增加一些 ...
 - Codeforces Beta Round #81 A Transmigration
			
在魔界战记中有一个设定叫做转生,当一个人物转生时,会保留之前的技能,但是技能等级需要乘以一个系数 k ,如果技能等级小于100,将会在转生之后失去该技能. 转生之后,会学到一些新技能.这些新技能附加的 ...
 - 2012年东京区域赛 UVAlive6182~6191
			
暑假训练场 A(UVAL6182). 凯神看了敲掉的题目,还没有看过 #include <iostream> #include <memory.h> using namespa ...
 - window.open()与window.showModalDialog
			
弹出窗口两种方式: 1.window.showModalDialog: var feature = "dialogWidth:615px;dialogHeight:505px ...
 - MVC5 + EF6 + Bootstrap3系列教程
			
本系列教程以ASP.NET MVC5为核心框架,使用Entity Framewok6访问数据,并使用Bootstrap3作为前端UI框架.帮助大家开发出一套高效.美观.稳定.实用的软件系统. MVC5 ...
 - ThinkPHP 5 中的 composer.json
			
本篇并不是揭 ThinkPHP 5 的问题. 只是通过 composer.json 来学习 compoer.json 元旦那天, ThinkPHP 5.1 正式发布,值得庆祝. 之后的第二天有人反馈 ...