NB-IOT 相关技术

 

目录

第一章 NB-IOT 宝宝的成长故事

1.1 初次相见 NB 宝宝

1.2 NB-IoT 关键技术

1.3 NB-IoT 网络架构

第二章 NB 模组实战演练

2.1 NB 模组开机流程

2.2 NB 模组 UDP 数据发送测试

2.3 NB-IoT COAP 通信

2.3.1 名词解释

2.3.2 数据上报

2.3.3 信令下发

利用 NB-IoT 技术实现数据上传至阿里云

准备

硬件平台

软件平台

云平台:

NB 专用卡:

 具体操作 

附:UDP 服务端程序

UDP 协议

UDP 使用

UDP 报头

UDP 特性

对 UDP 一次发送多少 bytes 好?问题的思考

UDP 协议:低开销通信

内容补充


第一章 NB-IOT 宝宝的成长故事

1.1 初次相见 NB 宝宝

  • 大家都知道 WiFi(能上网),蓝牙(能传图连接鼠标耳机),ZigBee(工厂内听说过),但是对时下比较火的低功耗广域网络(LPWAN)总是模模糊糊,今天我们来讲讲 LPWAN 家族里的大娃:NB-IoT 宝宝的成长故事。
  • NB-IoT 即窄带物联网(Narrow Band-Internet of Things),具有低成本低功耗广覆盖海量连接等特点,定位于运营商级、基于授权频谱的低速率物联网市场,在位置跟踪、环境监测、智能泊车、远程抄表、农业和畜牧业等领域拥有广阔的应用前景。
  • NB-IoT 的诞生并非偶然,其寄托着电信行业对物联网市场的憧憬。近 10 年来,由于传统的 2G/3G/4G 网络并不能满足物联网设备低功耗、低成本的要求,大部分物联网设备在连接时主要使用 WiFi、蓝牙等免费技术,电信运营商很难从中获利。说白了也就是经济推动了技术的发展。

1.2 NB-IoT 关键技术

  • NB-IoT 系统的传输带宽和 LTE 系统的一个物理资源块的载波带宽相同,都是 180kHz,这使得 NB-IoT 系统能够与传统 LTE 系统很好地兼容。
  • NB-IoT 系统的系统带宽和 GSM 系统的载波带宽相同,都是 200kHz,这使得 NB-IoT 系统可以在 GSM 系统的频谱中实现无缝部署,对运营商重耕 2G 网络频谱提供了先天的便利性。
  • NB-IoT 将系统带宽收窄至 200kHz,将有效降低 NB-IoT 用户终端射频芯片的复杂度,进一步降低芯片成本及开发复杂度。

1.3 NB-IoT 网络架构

 

NB-IOT 相关技术_第1张图片

华为提供 NB-IoT 端到端解决方案的支持,提供多种开放能力供合作伙伴快速集成应用。提供海思的 NB-IoT 芯片,基站网络和 Ocean Connect 连接管理平台。开发者可以根据芯片 / 模组开发手册进行终端的开发,基于 IoT 平台进行 APP Server 开发。 ●    Device:NB-IoT 终端(如智能水表、智能气表等)通过空口连接到 eNodeB。 ●    eNodeB:主要承担空口接入处理和小区管理等相关功能,通过 S1-lite 接口与 IoT 核心网进行连接,将非接入层数据转发给高层网元处理。  ●    IoT Core:承担与终端非接入层交互的功能,将 IoT 业务相关数据转发到 IoT 平台进行处理。  ●    IoT Platform:IoT 联接管理平台汇聚从各种接入网得到的 IoT 数据,根据不同类型转发给相应的业务应用进行处理。  ●    APP Server:是 IoT 数据的最终汇聚点,根据客户的需求进行数据处理等操作。

第二章 NB 模组实战演练

2.1 NB 模组开机流程

步骤 执行
step1 模组上电,初始化 USIM 卡
step2 搜索小区信号
step3 附着到 NB 网络,进入 connect 状态
step4 激活 PDN, 获得 IP 地址,建立 PDN 承载
step5 建立用户数据链接,收发用户数据
step6 一段时间无数据交互后,依次进入 Drx(Idle)、PSM 状态
step7 等待上发用户数据,或 TAU(跟踪区域更新)再进入 connect 状态

在模组进入 PSM 状态后 IP 地址会保留,若 PSM 状态时模组请求发送数据,模组会转化为 connect 状态,但模组不会重新获取 IP,还是以之前的 IP 发送数据。即:模组上电成功获取 IP 后,任何时刻查询其 IP 地址都是同样的 IP 值。

2.2 NB 模组 UDP 数据发送测试

  • 以下为 NB 模组(利尔达和移远都可以)测试步骤,方框内为发送相应指令后,NB 模组返回的数据;

第一步:开机 / 重启,模块已经正常启动!

REBOOTING   REBOOT_CAUSE_APPLICATION_AT   Neul    OK

第二步:AT+NBAND? 查看当前频段信息,确定是否和模块型号对应,默认移动 / 联通 8,电信模块需要将 NBAND 设置为 5,之后重启模块

第三步:AT+NBAND=5 电信模块,设置频段为 850MHZ

第四步:AT+NRB 重启模块

REBOOTING   REBOOT_CAUSE_APPLICATION_AT   Neul    OK

第五步:AT+NBAND? 再次查询模块频段信息,确认设置成功

+NBAND:5   OK

第六步:AT+NCONFIG? 查询配置信息,主要包括自动连接使能配置信息,默认使能

+NCONFIG:AUTOCONNECT,TRUE             //   自动连接网络 +NCONFIG:CR_0354_0338_SCRAMBLING,TRUE      开启了扰码功能 +NCONFIG:CR_0859_SI_AVOID,TRUE   +NCONFIG:COMBINE_ATTACH,FALSE   +NCONFIG:CELL_RESELECTION,FALSE   +NCONFIG:ENABLE_BIP,FALSE   OK

第七步:AT+CFUN? 模块是否处于全工作模式,打开射频电路,搜索信号,如果返回 0,请确定 AUTOCONNECT 值是否为 TRUE,以及是否安装 NBIOT 专用 SIM 卡

+CFUN:1   OK

第八步:AT+CIMI 查询 IMSI 信息,如果返回具体数值,说明已经正常识别 SIM 卡

460111176314533   OK

第九步:AT+CSQ 查询信号强度,返回的第一个数值代表信号强度,0-31 代表有信号,数值越大信号越强,99 代表没有 NBIOT 网络信号,第二个参数还没有实施,一直为 99

+CSQ:21,99   OK

第十步:AT+NUESTATS 查询模块状态

Signal power:-842   Total power:-718   TX power:-32768   TX time:0   RX time:2472   Cell ID:79044177   ECL:255   SNR:-16   EARFCN:2506   PCI:3   RSRQ:-148   OK

第十一步:AT+CGATT? 查询是否模块附着成功,返回 1 代表成功;网络分为测试网络和商用网,SIM 也分为测试卡和商用卡,确保一一对应才能附着成功,具体网络信息和 SIM 卡信息可跟运营商确认

+CGATT:1   OK

第十二步:AT+CEREG? 查询网络注册状态,第二个数值返回 1 代表:网络注册成功,返回 2 代表:正在注册网络,注册时间和信号强度有关

+CEREG:0,1   OK

第十三步:AT+CSCON? 查看模块工作的连接状态,第二个返回数值代表模块的工作状态,1 代表 CONNECT 连接状态,0 代表 IDLE 睡眠状态,如果没有数据交互,在 CONNECT 状态持续 20 秒,之后进入 IDLE 状态;如果仍然没有数据交互,10 秒之后从 IDLE 状态进入 PSM 深度睡眠状态,此时模块不在接收任何下行数据,如果需要下行传输数据必须在 CONNECT 和 IDLE 状态下进行

+CSCON:0,0   OK

第十四步:AT+NSOCR=DGRAM,17,5683,1 创建 UDP SOCKET 传输信道,DGRAM 和 17 固定,5683 代表本地端口号,1 代表使能接收下行数据;最多可创建 7 个 SOCKET 传输信道,返回数值代表信号 ID 号,在发送和接收数据时需要指定

0   OK

第十五步:AT+NSOST=0,...,####,3,303132 发送 UDP 数据,0 代表 UDP  SOCKET 信道 ID,... 代表远程服务器的 IP 地址(公网 IP 地址),#### 代表远程服务器端口号,3 代表发送的字符个数(发送了 3 个字符),303132 代表 “012”3 个 hex 表示的字符;返回值代表成功从 0 信道发送了 3 个字节的数据(我这里测试发送了 74 个字节)

AT+NSOST=0,54.223.248.94,9502,74,FFAAD0D00000490F3836353335323033303030313031390000041F0000000000000000026B44F8FCF700F1000000020018020A6C002600004D380000000000000000000200000644628E   0,74   OK

1. 如果远程服务端接收模块发送的数据,必须在 30s = (CONNECT 状态 20s  +  IDLE 状态 10s) 之内发送下行数据,否则在没有数据交互的情况下模块会进入 PSM 深度睡眠状态,将   无法再接收到任何下行数据,但是此时模块仍然可以再次发送数据; 2. 模块可以在 CONNECT + IDLE + PSM 任何状态下发送数据,只能 CONNECT + IDLE 状态下   接接收数据; 3. 只需要执行一次 AT+NSOCR 命令创建 UDP SOCKET 信道,之后任何模式下直接执行 AT+NSOST 发送数据

第十六步:+NSONMI:0,67 信息代表模块接收到新的数据,需要读取,如果不及时读取,接收到下一条数据,将不会主动上报该信息;但可以连续读取;0 代表 UDP SOKECT 信道,67 代表有 67 个字节数据需要读取。

+NSONMI:0,67

第十七步:AT+NSORF=0,3 读取数据;0 代表 UDP  SOCKET 信道,3 代表需要读取数据字节长度;需要从返回值中提取出有效数据 303132,代表字符 “012”

0,54.223.248.94,9502,67,FFAAD1D10000430F3836353335323033303030313031390000015E8569078F03C000000002000801C1000000030012000000140000003C000003C20000000400080198,0   OK

1.+NSONMI 主动上报信息说明,如果模块接收到多包数据,但是没有使用 AT+NSORF 命令读取数据,那么只会在第一次接收到数据时上报 +NSONMI 信息,此后不在主动上报,直到执行 AT+NSORF 读取数据之后才会上报。

第十八步:AT+NSOCL=0 关闭 UDP SOCKET 传输信道

OK

2.3 NB-IoT COAP 通信

2.3.1 名词解释

  • 南向设备:开发者自行开发的终端硬件设备(包含多个传感器和 MCU)。
  • 北向应用:开发者自行开发的服务端应用(基于华为 OceanConnect 物联网平台提供的 RESTful 接口)。
  • NB-IoT:窄带物联网,华为等公司主推的物联网通讯用蜂巢网络。
  • NB 芯片 / 模组:类似于 3G/4G 通信模组,将设备端数据打包发送到指定平台的硬件模块。
  • SoftRadio:用于模拟 NB 模组、基站、核心网的 PC 端软件,可用于在缺乏 NB 模组和 NB 实网环境时的设备对接调试。
  • OceanConnect:华为物联网全联接平台,南向设备和北向应用通过该平台交换数据和信令。
  • 设备 Profile 文件:描述设备 “是什么”、“能干什么” 的 json 格式文件,上传到 OceanConnect 平台(上传时是 zip 包格式),设备绑定平台和提供服务的关键配置文件。
  • 编解码插件:用来对 NB 设备上报的数据进行解码,同时对下发给 NB 设备的信令进行编码的插件,对接前需上传到 OceanConnect 平台。

2.3.2 数据上报

概念:信令下发是另一个物联网的基本业务。应用服务器通过物联网平台,发送信令到南向设备,而设备也将做出一些对应的响应。

NB-IOT 相关技术_第2张图片

  流程: 1. 应用创建信令 (命令的相关项需要和设备 Profile 中的描述一致),发送到平台; 2. 如果平台判断设备在线,则立即下发信令;如果平台判断设备离线,则     信令将缓存于平台的数据库中; 3. 南向设备在某时刻上报数据,平台收到数据后,将检索对应设备在数据库中是否存在有效未下发的信令,如有,则下发该信令; 4. 信令通过编解码插件进行编码(json 到 16 进制码流),并被发送到设备端; 5. 设备收到信令,执行完毕,返回信令执行结果; 6. 平台收到上述执行结果,通过编解码插件的解析,获取信令执行的结果,修改对应的信令状态。

2.3.3 信令下发

概念:信令下发是另一个物联网的基本业务。应用服务器通过物联网平台,发送信令到南向设备,而设备也将做出一些对应的响应。

NB-IOT 相关技术_第3张图片

   流程: 1. 应用创建信令 (命令的相关项需要和设备 Profile 中的描述一致),发送到平台; 2. 如果平台判断设备在线,则立即下发信令;如果平台判断设备离线,则信令将缓存于平台的数据库中; 3. 南向设备在某时刻上报数据,平台收到数据后,将检索对应设备在数据库中是否存在有效未下发的信令,如有,则下发该信令; 4. 信令通过编解码插件进行编码(json 到 16 进制码流),并被发送到设备端; 5. 设备收到信令,执行完毕,返回信令执行结果; 6. 平台收到上述执行结果,通过编解码插件的解析,获取信令执行的结果,修改对应的信令状态。

 

利用 NB-IoT 技术实现数据上传至阿里云

 

本文主要实现利用 NB-IoT 技术实现基于 UDP 协议的数据传输。

准备

硬件平台

:BC95-B5 ,在淘宝上购买即可,可以直接购买模块,然后自己利用 USB 转串口接到 PC 上。也可以购买有 MCU 地板的,本人购买的是基于 MSP430 地板的开发板,不需要自己接 USB 转串口工具,当然价格会贵一些。

软件平台

:由于本文只是实现简单的数据收发,不需要跑 MCU 程序,所以主要用的工具是 NB-IoT QNavigator 工具,读者可去网上自行下载。之前我使用串口直接发 AT 指令,比较麻烦,因为在正式使用 nb 模块发数据之前,需要一些指令进行配置。使用 NB-IoT QNavigator ,该软件内置了很多指令,比如创建套接字这些指令,都是自动配置好的,相当方便。

云平台:

阿里云。去阿里云官网购买一个最便宜的 ECS,预装 ubuntu14,当然也可以选择其他系统。使用云服务器的一个好处就是只要购买看 ECS,以后可以随便更换系统,几分钟就可以搞定。主要在购买的时候,选择专有网络,不要选择经典网络,这是方便后面安全组的设置。

NB 专用卡:

可以通过电信运营商购买,移动也有。

 具体操作 

在上面的条件都满足下来后,可以进行下面的操作:

SP1:在阿里云上运行一个 UDP 服务器程序(参见博客后面),主要实现接受数据并将数据返回的功能,需要设置服务端的 UDP 端口号,我这里设置为 3001,然后使用 gcc 指令编译程序。在运行程序之前,需要先在阿里云的 ECS 的安全组中将 3001 端口放行 (参见图 1),如何添加安全组规则可以参考阿里云的安全组相关文档。设置好安全组之后,运行 UDP 服务器程序。这里可以先使用 tcp/udp socket 调试工具,建立一个 UDP 客户端(参见图 2),选择 ECS 的 IP 地址和你所设置的端口号,进行数据测试,如果通信成功,说明服务器运行正常,可进行下一步操作。

 

NB-IOT 相关技术_第4张图片

 

图 1  安全组设置

 

NB-IOT 相关技术_第5张图片

 

图 2  udp 调试

SP2:将开发板通过 USB 线插入 PC,打开 NB-IoT QNavigator ,点击 Connect to module. 就会自动连接。这一步会出现很多问题,这些问题多数与你的模块所在地有没有信号覆盖有关,如果你所在地没有基站,你的模块就无法附着,也就无法通信。初始化完成之后,可以看到模块的相关信息和卡的相关信息。如图 3。如果一直无法注册到网络,试一试换一个位置,或者将开发板举高一点,因为这一步需要有 NB 信覆盖。

 

NB-IOT 相关技术_第6张图片

 

SP3:点击 NB-IoT QNavigator 左侧的 UDP,将阿里云服务器的 IP 地址和 dup 服务器的端口号填入,点击连接。如图 4.

 

NB-IOT 相关技术_第7张图片

 

连接成功后,发送数据 123456789,在接收端会收到 313233343536373839. 数据通过 NB 模块将发送到阿里云服务器,然后服务器将数据发回来。

图 5 为实物图

 

NB-IOT 相关技术_第8张图片

 

至此,利用 NBIoT 技术完成了数据传输。

后续可以利用 MCU 底板设计采集数据的程序,设计云服务的数据库,提供移动开发分 API 接口,以及数据展现等功能。以后采用基于 UDP 协议的 CoAP 协议进行数据传输。

问题 1:以后使用电信的 NB 卡,都需要走电信的统一平台,也就是数据不能之间发送到自己的服务器。

问题 2:NB 的信号目前不稳定,对 NB 来说,如果 20 秒之内没有连接成功,就进入睡眠状态,后续就无法连接。据说可以更改这个时间,具体需要去查阅资料。

                                                               《完》

附:UDP 服务端程序

 

 #include
 #include
 #include
 #include
 #include
 #include
 #include
 #include

 #define SERV_PORT 3001
 
 int main()
 {
 int sock_fd; 
 int recv_num;
 int send_num;
 int client_len;
 char recv_buf[20];
 struct sockaddr_in addr_serv;
 struct sockaddr_in addr_client;
 sock_fd = socket(AF_INET,SOCK_DGRAM,0);
 if(sock_fd < 0){
 perror("socket");
 exit(1);
 } else{

printf("sock sucessful\n");
 } 
 memset(&addr_serv,0,sizeof(struct sockaddr_in));
 addr_serv.sin_family = AF_INET;
 addr_serv.sin_port = htons(SERV_PORT);
 addr_serv.sin_addr.s_addr = htonl(INADDR_ANY);
 client_len = sizeof(struct sockaddr_in);
 
 if(bind(sock_fd,(struct sockaddr *)&addr_serv,sizeof(struct sockaddr_in))<0 ){
 perror("bind");
 exit(1);
} else{
 
 printf("bind sucess\n");
 }
 while(1){
 printf("begin recv:\n");
 recv_num = recvfrom(sock_fd,recv_buf,sizeof(recv_buf),0,(struct sockaddr *)&addr_client,&client_len);
 if(recv_num < 0){
 printf("bad\n");
 perror("again recvfrom");
 exit(1);
 } else{
 recv_buf[recv_num]='\0';
 printf("recv sucess:%s\n",recv_buf);
 }
 printf("begin send:\n");
 send_num = sendto(sock_fd,recv_buf,recv_num,0,(struct sockaddr *)&addr_client,client_len);
 if(send_num < 0){
 perror("sendto");
 exit(1);
 } else{
 printf("send sucessful\n");
 }
 }
 close(sock_fd);
return 0;
 }

 

 

UDP 协议

UDP(User Datagram Protocol),用户数据报协议,是 OSI(Open System Interconnection,开放式系统互联) 参考模型中一种无连接的传输层协议,提供面向事务的简单不可靠信息传送服务,IETF RFC 768 是 UDP 的正式规范。UDP 提供了无连接通信,且不对传送数据包进行可靠性保证,适合于一次传输少量数据,UDP 传输的可靠性由应用层负责。常用的 UDP 端口号有:

应用协议 端口号
DNS 53
TFTP 69
SNMP 161

UDP 报文没有可靠性保证、顺序保证和流量控制字段等,可靠性较差。但是正因为 UDP 协议的控制选项较少,在数据传输过程中延迟小、数据传输效率高,适合对可靠性要求不高的应用程序,或者可以保障可靠性的应用程序,如 DNS、TFTP、SNMP 等。
UDP 在 IP 报文中的位置如下图所示:

 

NB-IOT 相关技术_第9张图片


可以看到,UDP 其实就是在 IP 报文中添加了端口信息,使数据到达主机后送达至相应端口的应用程序。下面是通过 wireshark 抓的一个 UDP 数据包:

NB-IOT 相关技术_第10张图片

UDP 使用

在选择使用协议的时候,选择 UDP 必须要谨慎。在网络质量令人十分不满意的环境下,UDP 协议数据包丢失会比较严重。但是由于 UDP 的特性: 它不属于连接型协议,因而具有资源消耗小,处理速度快的优点,所以通常音频、视频和普通数据在传送时使用 UDP 较多,因为它们即使偶尔丢失一两个数据包,也不会对接收结果产生太大影响。比如我们聊天用的 QQ 就是使用的 UDP 协议。

既然 UDP 是一种不可靠的网络协议,那么还有什么使用价值或必要呢? 其实不然,在有些情况下 UDP 协议可能会变得非常有用。因为 UDP 具有 TCP 所望尘莫及的速度优势。虽然 TCP 协议中植入了各种安全保障功能,但是在实际执行的过程中会占用大量的系统开销,无疑使速度受到严重的影响。反观 UDP 由于排除了信息可靠传递机制,将安全和排序等功能移交给上层应用来完成,极大降低了执行时间,使速度得到了保证。

UDP 报头

UDP 报头由 4 个域组成,其中每个域各占用 2 个字节,如下图所示:

 

 

NB-IOT 相关技术_第11张图片

  • UDP 协议使用端口号为不同的应用保留其各自的数据传输通道。UDP 和 TCP 协议正是采用这一机制实现对同一时刻内多项应用同时发送和接收数据的支持。数据发送一方 (可以是客户端或服务器端) 将 UDP 数据包通过源端口发送出去,而数据接收一方则通过目标端口接收数据。有的网络应用只能使用预先为其预留或注册的静态端口; 而另外一些网络应用则可以使用未被注册的动态端口。* 因为 UDP 报头使用两个字节存放端口号,所以端口号的有效范围是从 0 到 65535。* 一般来说,大于 49151 的端口号都代表动态端口。

  • 数据报的长度是指包括报头和数据部分在内的总字节数。因为报头的长度是固定的,所以该域主要被用来计算可变长度的数据部分 (又称为数据负载)。数据报的最大长度根据操作环境的不同而各异。从理论上说,包含报头在内的数据报的最大长度为 65535 字节。不过,一些实际应用往往会限制数据报的大小,有时会降低到 8192 字节。(对于一次发送多少字节比较好,后面会讲到)

  • UDP 协议使用报头中的校验值来保证数据的安全。校验值首先在数据发送方通过特殊的算法计算得出,在传递到接收方之后,还需要再重新计算。如果某个数据报在传输过程中被第三方篡改或者由于线路噪音等原因受到损坏,发送和接收方的校验计算值将不会相符,由此 UDP 协议可以检测是否出错。这与 TCP 协议是不同的,后者要求必须具有校验值。

  • 许多链路层协议都提供错误检查,包括流行的以太网协议,也许你想知道为什么 UDP 也要提供检查和校验。其原因是链路层以下的协议在源端和终端之间的某些通道可能不提供错误检测。虽然 UDP 提供有错误检测,但检测到错误时,UDP 不做错误校正,只是简单地把损坏的消息段扔掉,或者给应用程序提供警告信息。

UDP 特性

UDP 是一个无连接协议,传输数据之前源端和终端不建立连接,当 UDP 它想传送时就简单地去抓取来自应用程序的数据,并尽可能快地把它扔到网络上。在发送端,UDP 传送数据的速度仅仅是受应用程序生成数据的速度、计算机的能力和传输带宽的限制; 在接收端,UDP 把每个消息段放在队列中,应用程序每次从队列中读一个消息段。

由于传输数据不建立连接,因此也就不需要维护连接状态,包括收发状态等,因此一台服务机可同时向多个客户机传输相同的消息。

UDP 信息包的标题很短,只有 8 个字节,相对于 TCP 的 20 个字节信息包的额外开销很小。

吞吐量不受拥挤控制算法的调节,只受应用软件生成数据的速率、传输带宽、源端和终端主机性能的限制。

UDP 使用尽最大努力交付,即不保证可靠交付,因此主机不需要维持复杂的链接状态表 (这里面有许多参数)。

UDP 是面向报文的。发送方的 UDP 对应用程序交下来的报文,在添加首部后就向下交付给 IP 层。既不拆分,也不合并,而是保留这些报文的边界,因此,应用程序需要选择合适的报文大小。

对 UDP 一次发送多少 bytes 好?问题的思考

在进行 UDP 编程的时候, 我们最容易想到的问题就是, 一次发送多少 bytes 好? 当然,这个没有唯一答案。相对于不同的系统,不同的要求,其得到的答案是不一样的。我这里仅对像 ICQ 一类的发送聊天消息的情况作分析,对于其他情况,或许也能得到一点帮助。

首先,我们知道 TCP/IP 通常被认为是一个四层协议系统,包括链路层、网络层、传输层、应用层。UDP 属于传输层, 下面我们由下至上一步一步来看: 以太网 (Ethernet) 数据帧的长度必须在 46-1500 字节之间, 这是由以太网的物理特性决定的。 这个 1500 字节被称为链路层的 MTU(最大传输单元)。 但这并不是指链路层的长度被限制在 1500 字节,其实这个 MTU 指的是链路层的数据区并不包括链路层的首部和尾部的 18 个字节。所以事实上这个 1500 字节就是网络层 IP 数据报的长度限制。因为 IP 数据报的首部为 20 字节,所以 IP 数据报的数据区长度最大为 1480 字节。而这个 1480 字节就是用来放 TCP 传来的 TCP 报文段或 UDP 传来的 UDP 数据报的。又因为 UDP 数据报的首部 8 字节,所以 UDP 数据报的数据区最大长度为 1472 字节。这个 1472 字节就是我们可以使用的字节数。

当我们发送的 UDP 数据大于 1472 的时候会怎样呢? 这也就是说 IP 数据报大于 1500 字节,大于 MTU。这个时候发送方 IP 层就需要分片 (fragmentation)。把数据报分成若干片,使每一片都小于 MTU。而接收方 IP 层则需要进行数据报的重组。这样就会多做许多事情,而更严重的是,由于 UDP 的特性,当某一片数据传送中丢失时,无法重组数据报,将导致丢弃整个 UDP 数据报。因此,在普通的局域网环境下,建议将 UDP 的数据控制在 1472 字节以下为好。

进行 Internet 编程时则不同, 因为 Internet 上的路由器可能会将 MTU 设为不同的值. 如果我们假定 MTU 为 1500 来发送数据的, 而途经的某个网络的 MTU 值小于 1500 字节, 那么系统将会使用一系列的机制来调整 MTU 值, 使数据报能够顺利到达目的地, 这样就会做许多不必要的操作. 鉴于 Internet 上的标准 MTU 值为 576 字节, 所以我建议在进行 Internet 的 UDP 编程时. 最好将 UDP 的数据长度控件在 548 字节 (576-8-20) 以内.

UDP 协议:低开销通信

UDP 是一种简单协议,提供了基本的传输层功能。与 TCP 相比,UDP 的开销极低,因为 UDP 是无连接的,并且不提供复杂的重新传输、排序和流量控制机制。

UDP 数据报重组

与 TCP 的通信机制不同,由于 UDP 是无连接协议,因此通信发生之前不会建立会话。UDP 是基于事务的,换言之,应用程序要发送数据时,它仅是发送数据而已。很多使用 UDP 的应用程序发送的数据量很小,用一个数据段就够了。但是也有一些应用程序需要发送大量数据,因此需要用多个数据段。UDP PDU(协议数据单元) 的实际意义是数据报,尽管数据段和数据报可以互换使用来描述某个传输层 PDU。

	将多个数据报发送到目的主机时,它们可能使用了不同的路径,到达顺序也可能跟发送时的顺序不同。与TCP不同,UDP不跟踪序列号。UDP不会对数据报重组,因此也不会将数据恢复到传输时的顺序。
	因此,UDP仅仅是将接收到的数据按照先来后到的顺序转发到应用程序。如果数据的顺序对应用程序很重要,那么应用程序只能自己标志数据的正确顺序,并决定如何处理这些数据。

UDP 服务器进程与请求

与基于 TCP 的应用程序相同的是,基于 UDP 的服务器应用程序也被分配了公认端口或已注册的端口。当上述应用程序或进程运行时,它们就会接受与所分配端口相匹配的数据。当 UDP 收到用于某个端口的数据报时,它就会按照应用程序的端口号将数据发送到相应的应用程序。

UDP 客户端进程

对于 TCP 而言,客户端 / 服务器模式的通信初始化采用由客户端应用程序向服务器进程请求数据的形式。而 UDP 客户端进程则是从动态可用端口中随机挑选一个端口号,用来作为会话的源端口。而目的端口通常都是分配到服务器进程的公认端口或已注册的端口。

采用随机的源端口号的另一个优点是提高安全性。如果目的端口的选择方式容易预测,那么网络入侵者很容易就可以通过尝试最可能开放的端口号访问客户端。

由于 UDP 不建立会话,因此一旦数据和端口号准备就绪,UDP 就可以生成数据报并递交给网络层,并在网络上寻址和发送。

需要谨记的是,客户端选定了源端口和目的端口后,通信事务中的所有数据报文头都采用相同的端口对。对于从服务器到达客户端的数据来说,数据报头所含的源端口和目的端口作了互换。

内容补充

TCP 在目的主机没有确定可以接收数据时不会向网络发送数据。TCP 管理数据流,并会重新发送目的主机没有确认收到的数据。TCP 使用握手、计时器和确认机制,以及动态窗口来实现可靠传输。但是,可靠性带来的结果就是增加了网络开销。有两点原因,其一是 TCP 采用了更大的数据段报头信息;其二是管理源端和目的端之间的数据传输也导致了更大的网络流量。

参考链接:https://blog.csdn.net/s_lisheng/article/details/73538229

https://blog.csdn.net/pengpengjy/article/details/78813619

https://www.cnblogs.com/hbtmwangjin/articles/8931282.html

你可能感兴趣的:(物联网)