【Java网络编程04】网络原理进阶(二)

1. 前言

在网络原理进阶(一)部分我们详细介绍了UDP/TCP两大协议及其相关特性,本章我们会讨论网络层、数据链路层、物理层相关协议。但是需要注意的是,如果有小伙伴们未来是想成为Java后端开发工程师的,那么未来工作中大概率会涉及到网络通信,因此TCP相关特性是及其重要,必学不可的!!而网络层的IP协议确实很复杂、也很重要(站在网络协议设计者的角度),对于咱们职业来说,只需要适当了解即可。

2. 网络层

IP协议:网络层中最重要的协议就是IP协议了,其中IP协议主要完成的工作有两方面:1、地址管理(使用一套地址体系来描述网络设备所处的位置)2、路由选择(将数据报从一个地址转发到另一个地址)

2.1 IP数据报格式

【Java网络编程04】网络原理进阶(二)_第1张图片
下面对报头中各个字段进行简要介绍:

  • 4位版本号:指定遵循的IP协议版本,例如IPv4来说值就是4,IPv6就是6
  • 4位首部长度:与UDP协议一样,单位为4字节,因此首部最大长度是15 * 4即60字节
  • 8位服务类型:其中起作用的只有4位,这四位分别表示最小延时、最大吞吐量、最高可靠性、最小成本,这四者相互冲突,只能选择一个
  • 16位总长度:IP数据报整体占据多少个字节
  • 16位标识:当IP数据报被分片时,可以根据该字段确定哪些IP分片应该组包在一起
  • 3位标志:第一位保留,第二位为1表示禁止分片,第三位表示如果使用分片,那么如果为1表示这个最后一个分片,类似于“结束位”标记
  • 13位片偏移:是分片相对于原始IP报文开始处的偏移,可以根据该字段对于分片进行排序组包
  • 8位生存时间:指定数据报到达目的地的的最大报文跳数,一般是64,经过一个路由,跳数-1,如果一直减到0还没有到达,那么就丢弃了,这个字段主要用来防止出现路由循环
  • 8位协议:表示上层协议的类型(TCP或UDP)
  • 16位首部检验和:使用CRC等机制判断首部是否损坏
  • 32位源地址与目的地址:表示发送端与接收端
  • 选项字段:不定长,最多40字节

2.2 IP协议如何管理地址

IP地址:前面我们提到过,IP地址本质上是一个32位的二进制数,但是为了阅读起来方便,我们通常使用点分十进制的方式将IP地址分为4部分,其中每个部分1个字节,使用十进制进行表示,每个部分取值为0-255,例如IP地址为01111111 00000000 00000000 00000001,采用点分十进制表示后为127.0.0.1
IPv4地址数量:IP地址的出现是为了给每一个网络设备进行唯一的身份标识,32位能够表示的IP地址数目为2^32 - 1大约42亿9千万,尽管这个数目看起来很大,但是随着移动互联网时代的到来,每个用户甚至拥有4、5台网络设备,总的网络设备是很可能超过百亿的,因此解决IP地址不够用的问题迫在眉睫!!!

2.2.1 IP地址数量解决方案

如何解决IP地址不够用的问题成了上世纪90年代非常严重的问题!下面我们来简要介绍几种解决IP地址不够用的常见方案

2.2.1.1 动态分配IP地址

该方案的依据是全世界所以的网络设备不可能同时一起上网,因此对于正在上网的网络设备进行按需分配IP地址,就可以解决IP地址不够用的问题,但是缺点也非常的明显,这毕竟只是权宜之计,并不能真正解决IP地址不够用的问题!!!

2.2.1.2 NAT机制(网络地址映射)

IP地址分类:NAT机制要求把IP地址分为两大类:1、私网IP;2、公网IP,其中10.*192.168.*172.16-172.31.*这三类地址都是私网IP,剩下的都是公网IP了。NAT机制要求公网上设备对应的公网IP必须是唯一的,但是私网(局域网)上的IP地址只要保证当前局域网类不重复即可,不同局域网的IP可以重复。
由于上述规定,因此NAT机制就具有以下限制:

  1. 局域网设备访问局域网设备(同一局域网中),允许访问
  2. 局域网设备访问局域网设备(不同局域网中),不允许访问
  3. 局域网设备访问公网设备,可以访问,但是需要使用NAT机制对IP进行转换
  4. 公网设备访问公网设备,可以访问
  5. 公网设备访问局域网设备,不允许访问

【Java网络编程04】网络原理进阶(二)_第2张图片
这里我们简化一下模型,假设主机只经过一个路由器就将数据转入公网,最终到达服务器,中间路由器所做的工作我们并不关心,此时假设从主机(192.168.0.1)的数据想要经过路由器,进一步进行转发,此时NAT机制就会将IP报头中的源IP进行替换成路由器的IP,如下图所示:
【Java网络编程04】网络原理进阶(二)_第3张图片
此时数据报中的源IP就被替换为路由器的WAN口IP,并且更换后的数据报到达服务器后,服务器端看到的源IP就是5.6.7.8了,感知不到局域网的IP,达到多个局域网IP对应一个公网IP,起到节省IP地址的效果了。

注意:路由器的LAN口IP往往是一个局域网IP,WAN口可能是局域网IP,也可能是公网IP,路由器的核心就是能够将两个网络连接起来,并且不是所有的路由器都会替换源IP,当源IP被修改为公网IP后,路由器就不再进行替换

NAT工作原理
下面我们就来详细介绍NAT机制的工作原理

  1. 不同主机访问不同服务器

【Java网络编程04】网络原理进阶(二)_第4张图片

  1. 此时主机(192.168.0.1)访问服务器(1.2.3.4),此时源IP被替换为5.6.7.8,此时路由器内部维护一个数据结构保存对应映射信息
  2. 此时主机(192.168.0.2)访问服务器(9.10.11.12),此时源IP被替换为5.6.7.8,此时路由器内部维护的映射表新增记录

【Java网络编程04】网络原理进阶(二)_第5张图片

  1. 此时服务器1.2.3.4返回给目的IP地址5.6.7.8,然后根据映射表找到源IP地址为192.168.0.1然后成功返回给对应主机
  2. 此时服务器9.10.11.12返回给目的IP地址5.6.7.8,然后根据映射表找到源IP地址为192.168.0.2然后成功返回给对应主机
  3. 不同主机(不同端口)访问同一服务器

【Java网络编程04】网络原理进阶(二)_第6张图片

  1. 此时主机(192.168.0.1)上的应用程序端口是26000,此时访问服务器1.2.3.4,此时源IP地址被替换为5.6.7.8,并在映射表中新增记录表项
  2. 此时主机(192.168.0.2)上的应用程序端口是26001,此时访问服务器1.2.3.4,此时源IP地址被替换为5.6.7.8,并在映射表中新增记录表项

【Java网络编程04】网络原理进阶(二)_第7张图片

  1. 此时服务器返回目的IP为5.6.7.8,目的端口号为26000,此时路由器根据映射表找到端口号26000对应的源主机IP地址为192.168.0.1,然后成功返回给对应主机
  2. 此时服务器返回目的IP为5.6.7.8,目的端口号为26001,此时路由器根据映射表找到端口号26001对应的源主机IP地址为192.168.0.2,然后成功返回给对应主机
  3. 不同主机(同一端口)访问同一服务器

【Java网络编程04】网络原理进阶(二)_第8张图片

  1. 此时主机(192.168.0.1)上的应用程序端口是26000,此时访问服务器1.2.3.4,此时源IP地址被替换为5.6.7.8,并在映射表中新增记录表项
  2. 此时主机(192.168.0.2)上的应用程序端口是26000,此时访问服务器1.2.3.4,此时源IP地址被替换为5.6.7.8,并在映射表中新增记录表项

【Java网络编程04】网络原理进阶(二)_第9张图片

  1. 此时服务器返回目的IP为5.6.7.8,目的端口号为26001,此时路由器根据映射表找到替换端口号26001对应的源主机IP地址为192.168.0.1,然后成功返回给对应主机
  2. 此时服务器返回目的IP为5.6.7.8,目的端口号为26002,此时路由器根据映射表找到替换端口号26002对应的源主机IP地址为192.168.0.2,然后成功返回给对应主机

总结

  • 如果同一局域网内不同主机访问不同的服务器,那么返回数据时只需要根据服务器的IP地址就可以查表找到对应的主机
  • 如果同一局域网内不同主机访问同一个服务器,但是端口号不同,那么此时可以根据端口号的不同进行区分
  • 如果同一局域网内不同主机访问同一个服务器,但是端口号相同(极小概率),NAT机制可以替换源端口,仍然能够区分,此时路由器就不是单纯作用在网络层的设备了,还工作在传输层(因为可以修改传输层报文中的端口号)

NAT机制本质上并没有增加IP地址的数目,只是将IP地址进行了复用,当前互联网就是NAT+动态分配相结合的方案解决IP地址不够用的问题,但是始终是权宜之计,并没有从根本上解决问题!!!

2.2.1.3 IPv6

IPv6:IPv6的出现是在根本上解决了IPv4地址不够用的问题,IPv6使用16个字节表示一个IP地址,总的表示范围是2^128,这是一个天文数字,号称可以给世界上每一粒沙子都分配一个IP地址。
关于IPv6的有关内容,本章不做过多讨论,感兴趣的小伙伴可以自行查阅相关资料,这里提供一个超赞的科普视频
点击查看【bilibili】

你可能感兴趣的:(java,网络)