之前写过一篇《通俗易懂TCP/IP(概述)》 , 广受欢迎和好评 , 有网友催更 , 便抽空续写IP章节 , 回应粉丝期待 。
TCP/IP网络模型TCP/IP网络模型分为4层 , 自下而上分布为链路层(又叫网络接口层)、网络层、传输层、应用层 。
文章插图
- 链路层:处理数据在媒介上的表示、传输以及与硬件交互的细节 。
- 网络层:IP层负责IP数据报的路由转发 , 所有的TCP、UDP、ICMP和IGMP数据都通过IP数据报传输 。网络层(IP)提供了一种尽力而为、无连接、不可靠的数据报交付服务 , IP负责将IP数据报(又叫分组)放入数据链路层传输 , 并处理分片和重组逻辑 。
- 传输层:为端主机上运行的应用程序提供端到端服务 , 包括TCP和UDP 。
- TCP提供了带流量控制、拥塞控制、有序、可靠的流交付 , TCP需要处理丢包检测重传、重排序等IP层不处理的问题 , TCP面向连接 , 不保留消息边界 。
- UDP提供的功能基本上没有超越IP , 不提供速率控制和差错控制 , 不保证可靠性 , UDP只是提供一套端口号 , 用于复用、多路分解(即把收到的数据报交给应用层对应程序处理)和校验数据完整性(只检错不纠错) , UDP面向非连接 , 保留消息边界 。
- 应用层:负责处理特定应用的细节 , 通常应用的实现都是基于TCP/IP或者UDP/IP 。应用层与应用细节相关 , 与网络数据传输无关 , 而之下的三层(链路层、网络层、传输层)则对应用一无所知 , 但需要处理通信的细节 。
文章插图
分层的目标是隔离 , 通过分层实现:下层对上层透明 , 而上层利用下层提供的能力 。
分层的另一个优点是协议复用 , 这种复用允许多种协议共存于同一基础设施之中 , 复用可以发生在不同层 , 并在每层都有不同类型的标识符区分 , 用于确定信息属于哪个协议 。
比如在链路层的数据帧(Frame)有一个协议标识符字段 , 用来标识链路层帧携带的协议是IP还是ARP;又比如在网络层的IP数据报头部有一个8位协议字段 , 标识该IP数据报来自于TCP、还是UDP、亦或是ICMP、IGMP...
封装【通俗易懂网络协议 pdu是什么】数据在发送端从上到下经过TCP/IP协议栈 , 遵循应用层->TCP/UDP->IP->链路层的顺序 。
当某层的一个协议数据单元(PDU)对象转换为由底层携带的数据格式表示 , 这个过程称为在相邻低层的封装 , 即上层被封装对象作为不透明数据充当底层的Payload部分 , 封装是层层包裹的过程 。
文章插图
每层都有自己的消息对象(PDU)的概念 。
- TCP层的PDU叫TCP段(segment)
- UDP层的PDU叫UDP数据报(Datagram)
- IP层的PDU叫IP数据报(Datagram)
- 链路层的PDU叫链路层帧(Frame)
具体到TCP传输数据而言 , 发送端的数据要经过三次封装 。
- 应用层数据经过TCP层的时候 , 会增加TCP头部 , 产生TCP Segment , TCP头部中的端口号是该层的分解标识符 。
- TCP Segment经过IP层的时候 , 会增加IP头部 , 产生IP Datagram , IP头部中的协议类型字段是该层的分解标识符 。
- IP分组经过链路层的时候 , 会增加以太网首部和尾部 , 产生以太网Frame , 帧头部中的以太网类型字段 , 可用于区分IPv4(0x8000)、IPv6(0x86DD)和ARP(0x0806) 。
接收端的数据还原也需要经历三次解封 。
- 经过链路层会剥离以太网首尾部 , 根据以太网类型字段 , 如果是IP Datagram则交给IP模块 。
- 经过IP层会清除IP头部 , 根据IP头部中的协议类型字段 , 交给TCP、UDP或者ICMP、IGMP模块 。
- 经过TCP/UDP层去掉TCP/UDP头部 , 根据端口号 , 最终将数据还原取出 , 并交付给应用程序 。
文章插图
封装发生在发送方 , 拆封(还原)发生在接收方 。
消息边界应用层将协议携带的数据写入消息 , 消息边界是两次写入操作之间的位置或字节偏移量 。
保留消息边界的协议(UDP)在接收方能获得发送方的消息边界 , 而不保留消息边界的协议(TCP)在接收方将不能获得发送方的消息边界 。
文章插图
比如发送端通过UDP协议先后发送2个大小分别为100、200字节的消息 , 接收端通过UDP协议接收数据 , 将分2次分别接收到100、200字节的消息 , 但不保证接收100、200消息的先后顺序 。
而TCP是数据流协议 , 如果发送端通过TCP协议先后发送2个大小为100和200字节的消息 , 接收端会收到300字节数据 , 但每次接收返回的不一定是100、200字节消息 , 接收端丢失了发送端的消息边界 。
网络地址IP地址用于IP层 , IPv4的IP地址是32位整数 , 最多可以表示40多亿个IP地址 , 按8位一字节 , 则分为4字节 , 每个字节是一个0~255的无符号整数 , 所以可以表示为“abc.def.ghi.jkl”的点分十进制格式 , 也可以表示为32位无符号整数 。
点分十进制和无符号32位无符号整数可以很容易换算 。
IPv4地址空间分成五大类 , A、B、C类用于Internet单播 , D类地址供组播使用 , E类地址保留 。
IPv4的32位又被划分为网络号和主机号 , 可以把网络号想象成到小区的邮政地址 , 而主机号想象成房间号 。
文章插图
链路层使用48bit的MAC地址 , ARP和RARP用于IP地址和MAC地址之间的相互换算 。
应用程序编程接口操作系统通过提供编程接口(API)来支持应用程序的网络开发 , 目前最流行的API是套接字(Socket) , 也叫Berkeley套接字 。
Socket抽象层位于应用层跟传输层之间 , 提供创建、绑定、监听、连接、发送、接收、关闭等常用方法 。
文章插图
Internet协议IP是TCP/IP协议族中的核心协议 , 为传输层提供IP数据报的交付能力 , 它负责将IP数据报从网络一端传递到另一端 , 实现数据转发 。
IP的另一个作用是:在发送端 , 接收来自传输层的协议数据单元(PDU) , 添加IP首部封装为IP数据报 , 交给协议族的下一层链路层 。
在接收端(包括中间路由器) , 接收来自链路层的PDU , 去掉IP首部 , 根据IP首部中的协议类型 , 将数据分发给TCP、UDP或者其他 。
IP只是完成分组交换(转发) , 如果你希望得到可靠性保证 , IP会说:对不起 , 做不了 。
发送一个IP数据报犹如寄一个快递 , 只需把目的地收件人写在快递上 , 快递公司会路由分发 , 但中间有可能丢件 , 丢了不管 , 而且到了 , 也不会有确认 , 一切随缘 。
基于TCP/IP协议族构建的网络 , 可以区分为端系统(两边的主机)和中间系统(中间路由器) , 端主机实现网络所有层 , 而路由器实现传输层之下的所有层 , IP使用逐跳协议 , IP之上的各层使用端到端协议 。
路由器路由器工作于网络层 , 是IP层的核心设备 。
路由器有两个或两个以上的网络接口 , 用于连接两个或多个网络 , 负责将IP数据报(分组)从一个网络接口转发到另一个网络接口 。
带有多网络接口(网卡)的主机也能承担转发分组的功能 , 这种主机称为作为路由器使用的主机 。
文章插图
如果把一个村庄比喻成一个小的局域网 , 那路由器就相当于连接村庄的桥梁 , 路由器属于中间系统 , 所以连接不同网络的路由器需要实现不同的链路层协议 , 完成不同链路层的翻译转换功能 。
另一方面 , 路由器实现链路层+网络层这2层就够了 , 而不必实现传输层和应用层 , 这是由它的功能(实现分组交换)决定的 。
每个IP分组都是一个IP数据报 , 包含发送方和接收方的第三层地址(IP地址) , 即32位的IPv4或128位的IPv6 , IP数据报首部中的目的地址决定将该数据报发往何处 , 而做出决定和发送数据报到下一跳的过程叫转发 , 转发依赖于路由表 , 是存储于内存中的一个数据结构 。
IP协议格式在贴出IP协议格式之前 , 我们可以设想一下 , IP协议需要包括哪些信息 , 这比直接上图+死记硬背要好 。
根据之前封装的描述 , 显然 , IP数据报应该是包括IP首部+数据负载 , 而这个不透明的负载(Payload)来自于TCP、UDP或者其他 。
所以我们讲IP数据报格式 , 其实就是IP首部的组成和结构 , 因为数据负载来自于上层 , 而封装的本质要求上层的数据对下层隐藏、无须解释 , 既然IP的Payload对于IP层透明 , 那自然没什么可讲的 。
IP首部由各种不同用途和含义的字段组成 。
因为IP分32位的IPv4和128位的IPv6 , 所以IP首部需要包括版本号字段用来区分这两种情况 。
因为IP负责分组转发 , 所以IP首部应该包括目的IP地址 , 用于路由转发逻辑的处理 , 另外接收端可能需要找到该分组的来源 , 所以也应该包含来源IP地址 。
TCP、UDP、ICMP、IGMP都通过IP数据报传输 , 所以在IP首部 , 需要包含一个协议字段 , 用于区分该IP数据报承载的是哪种类型的协议 。
IP不纠错 , 但是需要检查错误 , 数据在传输过程中 , 有可能出错 , 导致接收到的数据跟发送的不一样 , 所以接收端需要有方法知道传输过程中 , 数据是否跟发送端一致 , 所以头部校验和字段也是必要的 。
因为IP要处理分片和重组 , 所以IP首部需要包含相关信息 , 以支持该功能 。
IP分IPv4和IPv6两种 , 协议格式不同 , 本文讲述以IPv4为主 , 先给一个IPv4的数据报图 , 不带选项的IP数据报头部为20字节 。
文章插图
版本 , IP协议的第一个字段都是版本字段 , 这也是IPv4和IPv6唯一相同的字段 , IP数据报的版本字段为4对应IPv4 , 为6对应IPv6 , 主机或者路由器可以根据版本字段 , 分别处理IPv4或IPv6(称为双栈) 。
IHL , Internet头部长度 , 该字段为4位 , 表示头部(包括选项)32位字的数量 , 也就是说 , 真正的用字节表示的头部长度应该是IHL的值 , 再乘以4(32位=4字节) , 因为4位能表示的最大2进制为1111 , 对应十进制15 , 所以IPv4的首部最多60(15*4)字节 。
DS , 服务类型字段占6bit , 显示控制通知(ECN)占2bit , 一共8bit , 该8bit用来替换了最初版本的服务类型(ToS)字段 , 原因是ToS其实没怎么被用 。
总长度字段 , 是IP数据报的总长度 , 包括首部和数据 。
接下来的32位字(4字节) , 标识(16bit)+标志(3bit)+分片偏移(13bit)用于分片和重组逻辑 。
TTL , 生存期字段用于设置数据报可经过路由器数量的上限 。超此上限的IP数据报将被丢弃 。
协议字段 , 8bit , 提供多路分解功能 , 满足IP协议可用于携带多种(TCP、UDP、ICMP、IGMP等)协议类型的有效载荷的要求 , TCP对应值17 , UDP对应值为6 。
头部校验和字段 , 仅计算IPv4头部 , 不包括数据 , 数据(Payload)的校验由传输层协议去保证 , 校验和的含义很简单明了 , 在发送端根据IP头部的各位计算出一个数值 , 接收端根据接收到的IP头部的各位重算一个数值 , 如果该值等于校验和字段 , 那就哦了 , 否则 , 传输过程中出错了 , 这个IP数据报不靠谱 , 扔了吧 。
分片和重组链路层对可传输的帧有一个最大长度的限制 , 以太网对数据帧的长度上限是1500字节 , 链路层可传输帧的长度限制叫做最大传输单元(MTU) 。
如果IP层有一个数据报要传 , 且数据长度比链路层的MTU还大 , 那么IP层就需要对该数据报分片(fragmentation) , 把超限的数据报切分为若干片 , 使得每片都小于MTU限制 。
IP层接收到一份要发送的数据报时 , 通过选路逻辑来决定向哪个接口(网卡)发送数据 , 发送数据之前 , 需要查询该接口获得其MTU , 然后将数据报长度与MTU进行比较 , 如果需要 , 则进行分片 , 分片可以发生在原始发送端主机 , 也可以发生在中间路由器上 。
IP数据报分片后 , 到达目的地后才进行重新组装 , 恢复分片前的IP数据报信息 , 重组由目的主机的IP层完成 。因此 , 分片和重组对传输层(TCP、UDP)透明 , IP首部中的标识、标志、分片偏移字段为分片和重组提供了足够的信息 。
IP数据报首部中的标识(16bit)保存分片的唯一值 , 这意味着属于同一IP数据报的多个分片拥有相同的标识值 。
标志(3bit)字段中的一位用来表示“是否有更多的片” , 除最后一片外 , 其他组成数据报的分片该位设1 , 最后一片置0表示没有更多的片 , 也就是最后一片;片偏移字段用来标识该片在原始IP数据报中的位置 。
当IP数据报切分为多个分片(IP数据报)后 , 每个分片的总长度字段(16bit)要更改为该片的长度值 。
对链路层而言 , 不管是完整的IP数据报 , 还是IP数据报的一个分片 , 都以IP分组同等视之 , 分组是IP层把数据报传递给链路层的一个概念 , 既可能是一个独立IP数据报也可能是一个IP数据报的分片 。每个分组(分片)都有自己的IP首部 , 并在选路时与其他分组(分片)独立路由 , 所以这些分片到达目的端可能失序 , 但IP首部有足够信息重新组装这些片 。
任何一个分片的丢失 , 都要导致重传整个数据报 , 这是因为重传机制在传输层 , 而分片对传输层透明 。
文章插图
上图是UDP数据报在IP层的分片示例 , 可见UDP首部只存在第一个分组(分片)之中 , 这很容易理解 , 因为经传输层封装后的数据报对于IP层而言是透明的 , IP不区分UDP首部和UDP数据 , 它们都是不透明的Payload 。
接收端在收到IP分片后 , 相同标识值的分片属于同一个被切分的数据报 , 然后对分片偏移排序 , 更多片标志位为0的分组是最后一片 , 排序后的分组 , 如果分配偏移连续 , 且最后一个分组也到达 , 则表示整个数据报都到达了 , 则恢复数据报 , 否则继续等待 。
IP转发IP转发的概念很简单 , 就是路由器为IP数据报挑选一个接口发送出去 。
从发送端到目的端 , 之间经历的所有路由器构成网络路由的完整路径 , 这跟从家到公司经过的所有路口构成的路径类似 。
当网络接口(网卡)收到数据报时 , IP模块检查数据报目的地址是否为自己的IP地址 , 如果是 , 数据报交付给由协议字段指定的协议模块(TCP、UDP等) , 如果不是 , 则判断IP层是否配置为路由器 , 如果是 , 则转发 , 如果不是 , 丢弃 , 因为主机不转发那些不是由它生成的数据报 。
IP层包含一些位于内存中的信息 , 称为路由表 , 每次转发数据报时 , 都要查询路由表 , 执行最长前缀匹配法 , 决定挑选哪个路由表项做数据转发 。IP转发逐跳进行 , 每次转发假设离目的地更近一步 , 路由器和主机不包含到目的地的完整路径信息 。
路由表是路由条目的列表 , 每个路由条目包括以下几项关键信息 。
- 目的地:一个32位字段 , 用于与掩码操作结果相匹配 。
- 掩码:一个32位字段 , 用于与IP数据报中的目的IP地址做按位与操作 。
- 下一跳:下一个IP实体(路由器或者主机)的32位IP地址 , 数据报将被转发到该地址 。
- 接口:用于将数据报发送给下一跳的网络接口(网卡) 。
- 首先取出数据报中的目的IP地址 , 然后与路由条目的掩码字段进行按位与 , 按位与的结果如果等于路由条目的目的地 , 则该条目与目的地IP匹配 , 该条目进入候选集合 。
- 从候选集合中选择最匹配的条目 , 即掩码最多位为1的条目 , 取出下一跳字段作为转发数据报的下一跳IP地址 。
- 通过最匹配条目的网络接口 , 发送到下一跳 。
- 如果没有匹配条目 , 则数据报无法交付 , 通过ICMP发送“主机不可达”通知发送主机 。
欢迎关注:"码砖杂役"公众号和头条号 , 本号专注于科技互联网知识传播和分享 。
- 邮政编码是一个国家或地区为实现邮件分拣自动化和邮政网络数位化 河南省项城市的邮政编码
- 在双代号网络计划中,当计划工期等于计算工期时
- 网络安全成为国家安全重要组成部分 网络概念股有哪些
- 网络电视是直播吗
- 网络数据与大数据 什么叫网络大数据
- 解聘劳动合同协议书 解聘劳动合同协议书企业要加什么字
- 常用的网络硬件设备有哪些?其功能是什么 常用的网络硬件设备有哪些
- 复印的协议可以被劳动监察认可吗
- 解除劳务合同协议书 协议解除劳动合同有经济补偿金吗
- 为什么登录快手无法连接网络