目录
1、网络协议初识
1.1、协议分层
打电话的例子

比如我们有两个人分为人A和人B,他们需要联系时就拨通互相的电话然后就可以建立起对话了,通常我们在逻辑上都认为,这两个人是在互相和对面直接沟通的,但实际上呢?人A如果想要将对话传到人B那,就需要通过电话机A传输给电话机B然后再传输给人B,所以物理上两个人是在通过底层的硬件沟通,那么说到这,就要问几个问题了:
如何处理传来的声音数据?
长距离传输数据丢失怎么办?
如何定位到要打给谁呢?
你怎么保证你的数据可以准确的到达对面?
为了解决这些问题,一些互联网大牛们就会分层处理,每一层通过一个协议来规定,那么上面打电话的例子完整的应该是:

在这个例子里我们只分了两层,那么在网络通信中只会更加复杂,要分更多的层来解决。
那么为什么要分层呢?
分层最大的好处就在于封装,也就是追求软件工程中的高耦合、低内聚思想。
1.2、OSI七层模型
OSI(Open System Interconnection,开放系统互连)七层网络模型称为开放式系统互联参考模型,是一个逻辑上的定义和规范;
把网络从逻辑上分为了7层. 每一层都有相关、相对应的物理设备,比如路由器,交换机;
OSI 七层模型是一种框架性的设计方法,其最主要的功能使就是帮助不同类型的主机实现数据传输;
它的最大优点是将服务、接口和协议这三个概念明确地区分开来,概念清楚,理论也比较完整. 通过七个层次化的结构模型使不同的系统不同的网络之间实现可靠的通讯;
但是, 它既复杂又不实用; 所以我们按照TCP/IP四层模型来介绍.

1.3、TCP/IP(或四层)五层模型
TCP/IP是一组协议的代名词,它还包括许多协议,组成了TCP/IP协议簇.。
TCP/IP通讯协议采用了5层的层级结构,每一层都呼叫它的下一层所提供的网络来完成自己的需求。
物理层: 负责光/电信号的传递方式。 比如现在以太网通用的网线(双绞 线)、早期以太网采用的的同轴电缆(现在主要用于有线电视)、光纤, 现在的wifi无线网使用电磁波等都属于物理层的概念。物理层的能力决定了最大传输速率、传输距离、抗干扰性等. 集线器(Hub)工作在物理层。
数据链路层: 负责设备之间的数据帧的传送和识别.。例如网卡设备的驱动、帧同步(就是说从网线上检测到什么信号算作新帧的开始)、冲突检测(如果检测到冲突就自动重发)、数据差错校验等工作。 有以太网、令牌环网, 无线LAN等标准. 交换机(Switch)工作在数据链路层。
网络层: 负责地址管理和路由选择.。例如在IP协议中, 通过IP地址来标识一台主机, 并通过路由表的方式规划出两台主机之间的数据传输的线路(路由).。路由器(Router)工作在网路层。
传输层: 负责两台主机之间的数据传输. 如传输控制协议 (TCP), 能够确保数据可靠的从源主机发送到目标主机。
应用层: 负责应用程序间沟通,如简单电子邮件传输(SMTP)、文件传输协议(FTP)、网络远程访问协议(Telnet)等。 我们的网络编程主要就是针对应用层。

物理层我们考虑的比较少,因此很多时候也可以称为 TCP/IP四层模型。
1.4、网络分层和操作系统的联系
我们先来回顾一下计算机的组成

我们可以发现一台计算机的组成结构也是分层的,所以,其实网络的分层也就是在这些分层中分别实现的。

这下我们就知道了网络分层与计算机组成的联系,那么两台计算机到底是如何进行网络通信的呢?
我们从上面的打电话的例子也说过了,在逻辑层面,每一层都认为自己在和对面的层在进行直接通信,但是实际上,每一层之间的通信都需要进过底层硬件。
所以如果一台计算机想向另一台计算机发送信息,就必须从应用层开始一层一层向下传递,直到物理层,然后另一台计算机接受消息也必须从物理层开始,一层一层向上传递,一直到应用层发送给用户。

那么我们可以总结,网络通信的本质就是:贯穿协议栈的过程!
2、网络传输的基本流程
2.1、TCP/IP通讯传输
网络传输其实就是将用户数据从用户开始一层一层向下层封装,再从接受的计算中一层一层向上解包的过程。在封装的过程中,每经过一层就要添加一个报头,什么意思呢,我们画图来解释:

从上到下这就是一个封装的过程,最后会形成一个报文进行发送,所以报文=报头+有效载荷。
那么解包的过程其实也就很明确了:

所以,通信的过程,本质就是不断地封装和解包的过程!
扩展:(大部分协议的共性)
1、几乎任何层的协议,都要提供一种能力,将报头和有效载荷分离的能力
2、几乎任何层的协议,都要在报头中提供,决定将自己的有效载荷交付给上层哪一个协力的能力
2.2、以太网(局域网)通信
每台主机在局域网上都要有自己的唯一标识,这个标识就是Mac地址。
那么在局域网中,主机是如何进行通信的呢?
我们先来打个比方,比如说在一个教室中,有一位同学叫小李,老师喊小李起来回答问题,那么其他同学也听到了老师喊小李的名字,他们都会确认喊得是不是自己,最后是小李站起来回答。
那么,在局域网中也是一样的道理,假如我们有十台主机分别标号M1-10,如果M1想和M10通信,那么所有主机都通过局域网收到了这个信息,但是最后比较Mac地址后只有M10接受信息,这就是局域网通信的原理。
再拿上面的例子,如果老师在喊小李时,下面各个同学都在很大声交流,那么小李能够听到老师的话吗,自然是不能的。
所以,在局域网中,某一时刻只有一台主机可以向局域网发送数据,也就是说局域网是一块临界资源,是通过数据碰撞避免算法实现的。
3、网络中的地址管理
3.1、横跨不同局域网的通讯

和上面所说的TCP/IP通讯传输不同的是,这里不是通过以太网,还要进过路由器的传输。那么我们要如何知道我们所要传输的目的地不在以太网中,而要通过路由器去其他局域网中寻找呢?还是看图解:

我们上面说过数据在传输其实就是封装和解包的过程,那么在封装的过程中呢,在IP层添加的报头中就会包括本机IP和目的IP的地址,没错,也就是在这一层,我们就要能够决定我们的目的IP到底是在以太网中,还是需要通过路由器去其他局域网寻找,那么自然在数据链路层也就是这里的以太网驱动程序添加的报头会包含本机的mac地址和目的路由器的mac地址。
那么ip地址和mac地址有什么区别呢?
先说结论:
ip地址,尤其是目的IP,一般都是不会改变的,协助我们进行路径选择;
Mac地址,出局域网之后,源和目的都要被丢弃,让路由器重新封装。
什么意思呢?我们接着看图分析:

这里路由器的数据链路层通过mac地址识别到了我们的数据包,那么就要进行解包然后向上传给路由器的ip层,此时注意了,路由器的ip层是直接将数据包传给目标的IP层吗?当然不是,我们之前就说过,数据的传输是贯穿协议栈的过程,所以这里路由器也必须先进行封装通过令牌环网让目标的数据链路层进行识别再一层一层解包传送给上层:

现在数据跨网传输的全流程就如上图,如果仔细观察可以发现,不论是客户端、路由器还是服务器端,ip层往上的报文都是一样的!这就说明了IP协议屏蔽了底层网络的差异化,靠的就是工作在IP层的路由器! 意思就是只要路由器支持,不管是哪两个局域网络都可以进行相互间的通信。所以IP实现了全球主机的软件虚拟层,一切皆是IP报文!
知道了这些,我们就能做一个小的总结,网络通信的基本脉络示意图:

3.2、一些补充
在封装和解包过程中的那些报文,它们还有一些别名,但实质上还是同一种东西。
在传输层一般都称为数据段、数据报;
在网络层一般称为数据报;
在数据链路层一般称为数据帧;
3.3、再次认识IP地址和MAC地址
IP协议有两个版本,一个是IPv4,另一个是IPv6,我们自己使用的网络大多都是IPv4。
对于IPv4来说,IP是地址是一个4字节,32位的整数;

每个点分割的一个数字表示一个字节,范围是0-255。
MAC地址用来识别数据链路层中相连的节点,长度为48位即6字节;

一般用16进制数字加冒号来表示,MAC地址在网卡出厂时就规定了,无法修改,通常是唯一的。