目录
1.IP地址
(1)局域网和公网
我们之前一直把IP地址简单描述为起始地址和截止地址,就像重庆到北京,全程保持不变。但实际上网络的结构更复杂,分为局域网的IP和公网IP。
①局域网
局域网IP仅适用于局域网内部的唯一性。
家里的路由器连接到交换机,交换机又连接每个联网设备(家用交换机没有IP,它只负责扩散和划分碰撞域)。因此,在路由器之下的所有设备都在路由器划分的局域网下。下面是常用的局域网地址块,/8表示前8位定位网络(网络号),后24位定位主机(主机号),子网掩码就是将网络号占用的位数都设置为1,后续拿到IP后,用IP + 子网掩码借助&操作就能清楚地知道网络号和主机号。
专用IP地址块 | 子网掩码/前缀 | 地址范围 | 使用范围 |
---|---|---|---|
10.0.0.0/8 | 255.0.0.0 | 10.0.0.0 ~ 10.255.255.255 | 适合大型网络,如大型企业、跨国机构、大型园区等(单网络可容纳超1600万台设备) |
172.16.0.0/12 | 255.240.0.0 | 172.16.0.0 ~ 172.31.255.255 | 适合中型网络,如中型企业、高校、中型园区等(单网络可容纳约6.5万台设备) |
192.168.0.0/16 | 255.255.0.0 | 192.168.0.0 ~ 192.168.255.255 | 适合小型网络,如家庭网络、小公司、办公室等(单子网最多容纳254台设备) |
后续都用其中一个地址块举例,其余地址块都同理。
注意,192.168.0.0 ~ 192.168.255.255并不包含192.168.0.0和192.168.255.255本身,主机号全0表示这个网络本身,全1表示广播,该网络下的所有主机都是目标。所以真正可用的、能正常用于定位主机的是192.168.0.1 ~ 192.168.255.254。另外两个地址块同理。
a.网关地址
路由器之下划分一个子网,其中路由器自己也有一个子网地址(网关地址),这个地址一般是198.168.0.1或192.168.1.1等,当然也可自己设置网关地址。那么子网下的设备怎么知道路由器的子网IP呢?除了手动设定网关地址,一般都是DHCP协议自动获取。
当有一个新设备连接到交换机后,它什么都不知道,只知道自己的mac地址。它不知道自己的网络号、主机号,也不知道路由器在哪。这个时候它会发送符合DHCP的数据,其中IP为255.255.255.255(未知网络号时也可广播),目的mac为全F,这样发出去的mac帧每个设备都能收到消息,其中DHCP服务器(一般也集成在路由器里)收到消息后会进行回应(新设备知道自己的mac,因此能单播回应)。其中就包含分配的网络号、主机号、网关地址等消息。
因此,联网的设备都知道自己的子网地址、子网掩码、网络号、主机号、网关地址等信息。
b.局域网通信
在局域网内有两个主机A、B,如果A想要给局域网内的设备发消息,它可以采用广播(类似DHCP)、查找服务器的方式获取B的子网IP地址。之后A会ARP请求B的mac地址,B回应后A发送数据,由交换机转发。全程IP地址都是子网IP,不管源IP还是目的IP。
同理,当A想要给不在局域网内的B发消息时,A会先发送给路由器,A知道路由器的LAN口IP(网关地址),ARP请求的目的IP就是路由器的网关地址。之后就将数据交给路由器转发,但在交给路由器的途中也完完全全是一个局域网通信。
②运营商子网
路由器有两个关键地址,一个是LAN口地址(网关地址),一个就是WAN口地址。其中在局域网通信中,路由器本身与其子网下的设备之间通信都是采用LAN口地址,而WAN口地址是面向局域网之外的。
在一般情况下,这个WAN口IP并不会直通公网IP(有的可以直通),而是会进入运营商子网。也就是说WAN口的IP地址可能是一个如100.64.20.1这样的运营商子网地址。
100.64.0.0 ~ 100.127.255.255是运营商级NAT(CG-NAT)专用的私网网段。有的也会使用10.0.0.0/8来划分。
不同家庭的WAN口IP都是运营商子网里的一个IP,我们的路由器就相当于运营商路由器划分的子网下的主机,运营商路由器也有自己的LAN口IP和WAN口IP,这是一个层级结构。 也就是说我们出了家庭内部的子网后并不一定走到了公网,大概率是进入了另一个更大的子网,并且极端情况下子网能够这样搭建好几层。
而运营商的WAN口IP才是一个真正的公网IP,这种设计方式极大的节约了公网IP地址。 一个运营商路由器WAN口只占一个公网IP,但其LAN口连接非常多个家庭的路由器的WAN口IP,每个家庭里面路由器又能单独划分子网,整个层级结构划分清晰。
一般来说运营商的子网不止一层,也就是说和家庭路由器WAN口直接相连的运营商路由器的WAN口出去又进入了另一个子网。 一般来说运营商子网有3层,其原因后面会提及。
③公网
公网IP地址不能和子网IP地址块、运营商子网地址块重合,所以我们可以直接通过IP的值就判断出这个IP到底是公网IP还是某一个私网的IP。 如看到192.168.1.5,我们能立刻能判断是一个私网IP,并且还能知道这类地址块分配的用户数较少;看到220.181.38.10,不在任何私网段、运营商子网地址块内,那么它就是公网IP。
公网IP具有全球唯一性,只要知道了IP并且判断其为公网IP之后,那么我们一定能够唯一地在全球某个地方找到它。
(2)NAPT
①NAPT过程
所有的路由器(家用、企业、运营商)都内置了NAT功能,用于IP地址的转换。但实际生活中采用的都是IP + 端口号的转换(NAPT,直接定位到一个主机里的进程),所以我们搞清楚NAPT即可,NAT同理。
NAPT是直接定位到某个具体的主机的某个具体的进程,IP定位主机,端口定位进程。
下面是NAPT核心流程图:
核心就是转换表:表左侧为转换前源IP + 源端口 + 目的IP + 目的端口(四元组),右侧是转换后的四元组,这两个四元组构成一对map。
左侧四元组在转换前的网段唯一,右侧四元组在另一个网段唯一。进程A、B离开局域网后,在外层的网段上看均来自同一个设备,就是路由器。
当服务器应答的时候,服务器只知道A、B均来自同一个地址,所以A、B的应答均会发给路由器,而路由器可以根据应答的目的端口号(对应转换表中的“转换后源端口号”)的不同,反向查表映射到子网下的具体设备,之后由交换机扩散转发。
我们可以将NAT形象地看作一次身份转换。出了子网就代表路由器的WAN口IP进行传输了。
真实的传输过程中,NAT可不止一次。当进程A发送数据时,在家庭路由器那里进行一次NAT,替换源IP和源端口号,其中源IP改成了路由器的WAN口IP;出了家庭路由器之后进入运营商子网,到达运营商路由器后再进行一次NAT,替换源IP和源端口号,其中源IP改成了运营商路由器的。之后在公网上传输,到此为止修改的全是源IP + 源Port,目的IP + 目的Port从来没有被修改过。
到指定IP地址后,其实还没完,万一这个目的IP其实只是对方的运营商路由器呢,根据转换表反向查表,替换目的IP和目的端口号,这就进入了运营商子网;找到对方的家庭路由器之后,根据对方家庭路由器的转换表反向查表,替换目的IP和目的端口号进入家庭子网,最后通过交换机扩散转发至目标主机上。
那么对于路由器来说,何时NAPT呢?什么情况下需要交给运营商路由器呢?万一通信双方都在运营商下的子网呢?
A要给B发消息,A首先要知道B的IP地址,同一局域网内的话这个地址就是子网IP,通过子网掩码判断网络号一致后直接通过交换机转发。如果不一致的话就交给路由器,路由器NAPT之后查看路由表,如果找到网络号匹配的下一跳,就会直接转发过去,找不到的话就交给默认路由(通常是运营商网关),继续NAPT和转发。
②理解NAPT
暂不考虑端口复用的情况。家庭路由器NAPT后出去的mac帧源IP都一样,靠的是端口号区分不同进程。到达运营商路由器之后,又被替代源IP和端口号,并且所有从运营商路由器出去的mac帧的源IP都是这个路由器的WAN口IP。这种分级结构能够极大的压缩IP地址的使用,成百上千的家庭发出去的mac帧经过一级路由器的NAT之后源IP都是一样的,这也是为什么运营商路由器一般会分成3级了。因此,我们能够很好地理解NAT在缓解IPv4地址枯竭问题上扮演的重要作用。
但是又出现了一个问题,端口怎么压缩呢?如果严格按照一一映射的方式,一个进程的mac帧被NAT映射之后虽然IP压缩了,但还是需要单独分配一个端口号来区分不同进程。端口复用是一个解决办法,端口复用有不同的方案,其核心思想就是找到映射前的信息不同之处,使得就算打破了一一映射之后,反向查表能区分开。
如果两个进程来自同一IP不同Port,但是两者的目的IP和端口不一样,这样NAPT映射后两个进程的源IP和Port可以一致。 因为对方应答的时候虽然通过转换后的IP + Port反向查表到了两条记录,但看到目的IP和Port不一致,它们就会去匹配目的IP + Port = 发起回应的源IP + Port这一项,这才符合正常的通信流程,这样就能找到正确的映射。
对于运营商来说,它们手上的公网IP都有成百上千个,加上有的采用五元组、七元组等方式设计端口复用。除此之外,还有很多方式尽量增加端口的利用,例如在TCP的情况下, 建立连接时, 就会生成转换表项,而在断开连接后,则会删除这个表项。
所以端口号也是可以进行数量压缩的,能够承担高并发的网络访问需求。
③理解源IP和目的IP
引入NAT之后,传输数据前半段源IP一直在变,后半段目的IP一直在变。那么如果我要给一个目的IP发数据,这个目的IP究竟是什么意思呢?如果我收到了一个消息,那个源IP又是什么意思呢?
我们忽略那些大型的直接接入公网的服务器,也认为所有家庭路由器都会接入运营商路由器的子网,即家庭路由器的WAN口IP是运营商子网下的一个私网IP。
a.目的IP
我要给目的IP发消息,首先思考我们拿到的目的IP为什么长这样?能长成什么样?
如果说通信双方的路由器在同一运营商子网下,我拿到的目的IP其实是对方路由器的WAN口IP,这个WAN口IP是运营商子网下的私网IP,只不过这个私网IP的网络号和我家里的网络号一定匹配不上,因为运营商有专用的私网网段,并且运营商采用的地址块会非常庞大,家里用的子网地址块不可能跟运营商用的一样。如果有的话那就归入企业的考量范围,直接接入公网而非运营商的子网了。这种情况下路由器一般在路由表上就能直接匹配上(都在同一运营商子网下,最长前缀匹配),转发过去,找不到的话交给默认路由,由默认路由进行转发。
如果我拿到一个公网IP,这个公网IP一定是对方主机本身吗?
我们拿到的公网IP,实际上是对方最外层接入了公网的运营商路由器的WAN口IP,我们发的数据被对方路由器接收到后需要不停反向查表、转发才能到达目标主机上。
b.源IP
同理,我收到消息了,如果这个源IP是一个子网IP,且网络号无法和当前局域网的网络号匹配的话,那么就一定是对方路由器的WAN口IP(运营商路由器下的子网IP);如果源IP是公网IP的话,这个IP一定是对方所在的接入公网的运营商路由器的WAN口IP。
当然,源IP和目的IP都有可能直接接入了对方的服务器(大型公司都有)或者路由器,我们上述是忽略了的,现实中都要进行考量。
③最长前缀匹配
路由器收到mac帧之后是如何转发的在这里的理解也很关键。
1. 解封装:从MAC帧中提取IP数据包
路由器接收MAC帧后,会先在数据链路层进行CRC校验,校验失败的话整个mac帧直接丢弃,不再进一步处理和转发。 之后就等待目标主机重组失败,发送端的传输层或应用层控制重传。
CRC校验通过的话,会继续解封装IP数据包,最终提取出目的IP地址,这个IP地址按理说分为网络号和主机号,但是由于IP报头没有子网掩码字段,所以路由器并不知道网络号占多少位。
2. 匹配:转发表查找并最长匹配
路由器的转发表每一项的条目都包含“网络地址 + 子网掩码 + 下一跳”,每一项都分别与提取的目的IP进行&运算,当路由表中/20、/24的网络地址均和目的IP的前几位匹配上时,就会选择/24的作为下一跳。因为网络号匹配得越长的离目标主机就越近。
如果路由表中的每一项都匹配不上,就会转发至默认路由,默认路由一般是运营商路由器,NAPT后进一步转发。
因此可以看出,路由器之间是一跳一跳的,收到数据报之后去最长匹配,然后发送过去。
对于一般的家庭路由器,其WAN口是运营商子网下的一个私网IP,那么这样的话转发表中的每一个待选项都不能是公网IP,否则直接转发过去,结果对方发现源IP是个私网IP,怎么找回来呢? 所以WAN口是子网IP的路由器只能在运营商子网内转发,但凡涉及到公网转发的,只有交给默认路由,由运营商路由器NAPT后转发。所以可以总结为WAN口IP是私网IP的路由器,其转发表中的项也都会是私网IP。
我们可以通过route查看本地的路由表
Destination表示目的网络的IP地址,default代表默认路由,当未被其他路由条目匹配的目的地址,都走这条路由;其它路由条目可以是一个网段(如 10.0.8.0),代表目标是这个网段内的所有主机;也可以是单个IP(如 183.60.82.98),目标是这台特定主机。可以看出,如果一个目的IP和网段路由和主机路由都匹配上了,那肯定是选择主机路由。
Gateway表示下一跳的IP地址。若为 0.0.0.0,无需再发给其他路由器了,已经到了最后一个路由器了,eth0网卡ARP解析目标IP的MAC地址,然后把数据包发给局域网内的交换机,交换机再直接转发到目标设备。 若为 _gateway,实际对应当前子网的网关IP,如路由器的LAN口IP,当本地主机想要跨网段发数据,就必须先发送数据到LAN口,路由器NAPT后再转发。
Genmask表示子网掩码。结合Destination和收到的数据的目的IP做&运算,判断目的IP是否属于该路由对应的网段,多次匹配的话选最长匹配的项(网段路由选最长的)。最长匹配的当然是 255.255.255.255的主机路由。
④NAT技术缺陷
其限制主要来源于 NAT 依赖的转换表:
1.无法从 NAT 外部向内部服务器建立连接
2.装换表的生成和销毁都需要额外开销
3.通信过程中一旦 NAT 设备异常,即使存在热备,所有的 TCP 连接也都会断开
1.当公网设备想主动连接内网里的服务器(比如在家搭建的文件服务器),最开始 NAT 设备上根本没有对应的映射表项,也没有办法向内建立映射,只有向外建立映射后反向查表,所以这种情况路由器不知道该把请求转发到哪个内网设备,因此连接无法建立。
2.频繁维护表项会提高性能需求。
3.如果当前 NAT 设备坏了,哪怕马上切换到备用机并马上开始工作,正在进行的网络连接(比如网游、视频通话)也会断连,因为就算启动备用机,但它的转换表是空的。
2.代理服务
(1)正向代理
正向代理简单来说就是正向代理服务器接收客户端的请求,将请求转发给目标服务器,最后将目标服务器的响应返回给客户端。 在目标服务器眼里,一直都是正向代理服务器在请求服务,而实际上代理服务器只负责转发请求和应答,这样就可以隐藏客户端的身份。
连接学校的校园内网,就是通过学校的正向代理服务器访问资源。用户请求通过正向代理服务器认证之后,由代理服务器负责出去访问资源,“认证”也就意味着正向代理服务器有权力拦截访问,这也是使用校园内网访问一些资源会被拦截的原因。访问的内网资源是交给代理服务器,由代理服务器转发回来。正向代理服务器还可以缓存一些常被客户端请求的资源。
正向代理服务器物理位置靠近客户端。
一般来讲,客户端和要访问目标服务器都有公网IP(这个公网IP是客户端经由家庭路由器NAPT到运营商子网,再由运营商子网NAPT得到的公网IP,并且这个公网IP并不是固定的),在不加限制的情况下其实能够直接通信。 加上正向代理服务器可以做到隐藏身份,并且像校园网那种虽然目标服务器有公网IP,但客户端直接访问的话目标服务器会直接拒绝,它只会回应正向代理服务器的请求。 这点和后面的反向代理有一定的区别。
(2)反向代理
当客户端发起请求时,请求会到达反向代理服务器。反向代理服务器会根据配置的规则将请求转发给后端众多服务器中的一个,服务器的应答交给代理服务器,由代理服务器返回给客户端。 在这个过程中,客户端并不知道实际与哪个服务器进行了交互,它只觉得是在与反向代理服务器进行通信。
当我们访问代理服务器时,代理服务器会把客户端的源IP + Port交给某一台内网服务器,然后这台服务器就和我们的主机进行通信。但注意服务器拿到我们的IP和Port后并不能直接传过来,一般而言,服务器只有内网IP而没有公网IP,真正传输需要先从内网传给代理服务器,由服务器通过公网传到客户端手上。同理,客户端拿到的服务器地址是公网IP,其实是NAPT后的代理服务器的公网IP,和服务器通信时,只有先将数据交给代理服务器,由代理服务器再转发给服务器的。所以无论服务器还是客户端都绕不开代理服务器。 代理服务器可以缓存一些客户端常常访问的资源(包括静态资源、图片等)。
反向代理服务器更靠近服务器端。
不管正向代理还是反向代理,代理服务器的角色和NAT很像。但NAT是网络基础设备,是网络层的设备,而代理服务器往往在应用层。NAT在局域网出口部署,而代理服务器在任何地方都能部署。
(3)内网穿透
现在有一台中转服务器,运行一个frps(服务端)程序。还有一台主机,运行frpc(客户端)程序。中转服务器有自己独立的公网IP,而主机虽然有公网IP,但那是NAPT后运营商提供的,这个公网IP完全不能唯一地定位到主机上。
虽然这台主机没有唯一的公网IP,但frpc(客户端)可以借助运营商提供的公网IP连接到中转服务器frps(服务端)上,建立长期连接,并且frpc的配置文件可以告诉这个中转服务器自己在家庭路由器划分的子网下面的私有IP地址是什么。
这个时候,我们可以粗略理解为主机获得了“两个公网IP”,其中一个就是运营商提供的公网IP,另一个就是中转服务器的公网IP,并且中转服务器直接知道了主机在家庭内网中的私有地址,这一点至关重要。
现在又有一台笔记本电脑(不需要安装frpc),它想要远程控制主机。那么它就连接至中转服务器,向中转服务器发起请求,中转服务器借助frpc - frps连接,向主机请求,主机回应后交给中转服务器,再发回笔记本电脑。
具体来说,主机建立frpc - frps连接时,frpc配置文件中就告知frps “我的本地服务在192.168.1.100:22,别人可以通过中转服务器公网IP:6000访问它” 。这样我们的笔记本电脑直接访问中转服务器公网IP:6000,中转服务器会转发需求和应答,实现控制。
整体上看,内网的主机就像是中转服务器公网IP下的一个服务,或是中转服务器划分子网下的一台主机。所以其他设备通过访问中转服务器就可访问内网的主机。但实际上这是需要依靠主机的运营商公网IP连接中转服务器实现的。
(3)内网打洞和P2P
一般内网打洞成功率高的都是家庭路由器(出入口路由器)的WAN口直接连接公网IP的,暂不考虑连接运营商子网的。
两边主机都通过出入口路由器连上中转服务器,中转服务器记录两边主机的出入口路由器的IP + Port,中转服务器交换两者的IP和Port给对方后,就不需要通过服务器转发了,两边可以直接借助互相的公网IP进行通信,这就是内网打洞。
“打洞”的含义就是直接通过一个中间服务器,交换双方主机的对外的IP + port,之后让双方直接通信。 有的时候双方打洞的IP也可以是同一运营商子网下的私网IP地址,也可能是运营商的公网IP,不过这些情况都有可能遇到拒绝转发的情况,运营商会不同程度限制。
下载的时候也可能打洞,如双方主机都在下载同一个资源时,资源提供商就直接交换双方出入口路由器的IP + Port,实现内网打洞。之后两边既是下载者,也是上传者,两边互相交换各自没有的需要下载的数据,这就是P2P。
(4)“科技”
以下仅为技术分享,请各位遵纪守法!
前面说过运营商路由器连上广域网,有公网IP。我们的如果要经由公网转发,就会经过运营商路由器,进行NAPT并转发。这也意味着我们的访问报文会被看到,可能被运营商拦截,常说的“Q”就设置在拦截这里。 “FQ”的基本思想就是想办法骗过运营商。
有些地区可以直接访问外网,如香港。假设有一台云服务器在香港,这个云服务器可以访问外网,而我们又能直接访问这个云服务器,那么我们就可以借助正向代理实现,这实际上借助了正向代理隐藏身份的特点。
某个客户端软件,这个软件能劫持主机上所有的流量,修改本地的路由表让它把下一跳改成软件自己,这样的话所有数据都会转给软件,这个软件叫透明代理软件(透明是因为我们用户感知不到)。 假设我们要访问google,软件会把www.google.com等敏感信息加密,即把真实请求藏起来(运营商扫描不出来),表面覆盖一个可以访问外网的正向代理服务器的IP + Port。这个代理服务器能够解密并提取信息,访问外网并应答。返回时同样进行加密,交给客户端解密。
本质上它就是搭建在公网上的正向代理。