目录
[OSI 七层模型](#OSI 七层模型)
[TCP/IP 五层(或四层)模型](#TCP/IP 五层(或四层)模型)
[TCP/IP 协议与操作系统的关系(宏观上,怎么实现的)](#TCP/IP 协议与操作系统的关系(宏观上,怎么实现的))
[6.Socket 编程预备](#6.Socket 编程预备)
[socket 编程接口](#socket 编程接口)
[sockaddr 结构](#sockaddr 结构)
1.计算机网络背景
网络发展
独立模式:计算机之间相互独立;

网络互联
多台计算机连接在一起,完成数据共享;

局域网LAN
计算机数量更多了,通过交换机和路由器连接在一起

广域网WAN
将远隔千里的计算机都连在一起;

计算机是人的工具,人要协同工作,注定了网络的产生是必然的.
2.初识协议
"协议"是一种约定.

计算机之间的传输媒介是光信号和电信号.通过"频率"和"强弱"来表示0和1这样的 信息.要想传递各种不同的信息,就需要约定好双方的数据格式.
思考:只要通信的两台主机,约定好协议就可以了么?
• 定好协议,但是你用频率表示01,我用强弱表示01,就好比我用中国话,你 用葡萄牙语一样,虽然大家可能遵守的一套通信规则,但是语言不同,即是订好了 基本的协议,也是无法正常通信的
所以,完善的协议,需要更多更细致的规定,并让参与的人都要遵守。
• 计算机生产厂商有很多;
• 计算机操作系统,也有很多
• 计算机网络硬件设备,还是有很多;
• 如何让这些不同厂商之间生产的计算机能够相互顺畅的通信?
就需要有人站出 来, 约定一个共同的标准,大家都来遵守,这就是网络协议;
3.协议分层
协议本质也是软件,在设计上为了更好的进行模块化,解耦合,也是被设计成为 层状结构的
软件分层的好处

在这个例子中,我们的"协议"只有两层:语言层、通信设备层。
但是实际的网络通信协议,设计的会更加复杂,需要分更多的层
•但是通过上面的简单例子,我们是能理解,分层可以实现解耦合,让软件维护的 成本更低
OSI 七层模型
• OSI(OpenSystemInterconnection,开放系统互连)七层网络模型称为开放 式系统互联参考模型,是一个逻辑上的定义和规范;
• 把网络从逻辑上分为了7层.每一层都有相关、相对应的物理设备,比如路由 器,交换机;
• OSI七层模型是一种框架性的设计方法其最主要的功能使就是帮助不同类型 的主机实现数据传输;
• 它的最大优点是将服务、接口和协议这三个概念明确地区分开来,概念清楚,理论也比较完整.通过七个层次化的结构模型使不同的系统不同的网络之间实现可 靠的通讯;
• 但是,它既复杂又不实用;所以我们按照TCP/IP四层模型来讲解


其实在网络角度,OSI定的协议7层模型其实非常完善,但是在实际操作的过程 中,会话层、表示层是不可能接入到操作系统中的,所以在工程实践中,最终落地的 是5层协议。
• 但是要理解上面的话,需要我们学习完网络才可以理解,这里就知道就可以。
TCP/IP 五层(或四层)模型
TCP/IP是一组协议的代名词,它还包括许多协议,组成了TCP/IP协议簇. TCP/IP通讯协议采用了5层的层级结构,每一层都呼叫它的下一层所提供的网络来完 成自己的需求.


物理层我们考虑的比较少,我们只考虑软件相关的内容.因此很多时候我们直接称为 TCP/IP四层模型
一般而言
• 对于一台主机,它的操作系统内核实现了从传输层到物理层的内容;
• 对于一台路由器,它实现了从网络层到物理层;
• 对于一台交换机,它实现了从数据链路层到物理层;
• 对于集线器,它只实现了物理层; 但是并不绝对.很多交换机也实现了网络层的转发;很多路由器也实现了部分传输层的 内容(比如端口转发)
4.再识协议
为什么要有TCP/IP协议?
首先,即便是单机,你的计算机内部,其实都是存在协议的,比如:其他设备和 内存通信,会有内存协议。其他设备和磁盘通信,会有磁盘相关的协议,比如: SATA,IDE,SCSI等。只不过我们感知不到罢了。而且这些协议都在本地主机各自 的硬件中,通信的成本、问题比较少。
其次,网络通信最大的特点就是主机之间变远了。任何通信特征的变化,一定会 带来新的问题,有问题就得解决问题,所以需要新的协议。

所以,为什么要有TCP/IP协议?本质就是通信主机距离变远了
什么是TCP/IP协议?
• TCP/IP协议的本质是一种解决方案
• TCP/IP协议能分层,前提是因为问题们本身能分层
TCP/IP 协议与操作系统的关系(宏观上,怎么实现的)

所以究竟什么是协议?
截止到目前,我们还没接触过任何协议,但是如何朴素的理解协议,我们已经可 以试试了。 • OS源代码一般都是用C/C++语言写的。

看上图提问题问题:主机B能识别data,并且准确提取a=10,b=20,c=30吗?
回答:答案是肯定的!因为双方都有同样的结构体类型structprotocol。也就是说, 用同样的代码实现协议,用同样的自定义数据类型,天然就具有"共识",能够识别 对方发来的数据,这不就是约定吗?
关于协议的朴素理解:所谓协议,就是通信双方都认识的结构化的数据类型
因为协议栈是分层的,所以,每层都有双方都有协议,同层之间,互相可以认识对 方的协议。
5.网络传输基本流程
局域网网络传输流程图
局域网(以太网为例)通信原理
• 首先回答,两台主机在同一个局域网,是否能够直接通信?
是的 ,原理类似上课 ,每台主机在局域网上,要有唯一的标识来保证主机的唯一性:mac地址
认识MAC地址


• 以太网中,任何时刻,只允许一台机器向网络中发送数据
• 如果有多台同时发送,会发生数据干扰,我们称之为数据碰撞
• 所有发送数据的主机要进行碰撞检测和碰撞避免
• 没有交换机的情况下,一个以太网就是一个碰撞域
• 局域网通信的过程中,主机对收到的报文确认是否是发给自己的,是通过目标 mac地址判定
• 这里可以试着从系统角度来理解局域网通信原理
初步明白了局域网通信原理,再来看同一个网段内的两台主机进行发送消息的过程

而其中每层都有协议,所以当我进行进行上述传输流程的时候,要进行封装和解包

下面我们明确一下概念

• 报头部分,就是对应协议层的结构体字段,我们一般叫做报头
• 除了报头,剩下的叫做有效载荷
• 故,报文=报头+有效载荷
然后,我们在明确一下不同层的完整报文的叫法

最后,在整体复盘一下:

在网络传输的过程中,数据不是直接发送给对方主机的,而是先要自定向下将数据交 付给下层协议,最后由底层发送,然后由对方主机的底层来进行接受,在自底向上进 行向上交付,
数据包封装和分用
下图为数据封装的过程

下图为数据分用的过程

从今天开始,我们学习任何协议,都要先宏观上建立这样的认识:
- 要学习的协议,是如何做到解包的?只有明确了解包,封包也就能理解
2.要学习的协议,是如何做到将自己的有效载荷,交付给上层协议的?
跨网络传输流程图
网络中的地址管理-认识IP地址
IP 协议有两个版本,IPv4和IPv6.
我们整个的课程,凡是提到IP协议,没有特殊说明的, 默认都是指IPv4

跨网段的主机的数据传输.数据从一台计算机到另一台计算机传输过程中要经过一个或 多个路由器. 下面是一张示意图:

首先理解一下IP地址的意义
• 为什么要去目标主机,先要走路由器?
• 目的IP的意义

然后结合封装与解包,体现路由器解包和重新封装的特点

对比IP地址和Mac地址的区别:
• IP地址在整个路由过程中,一直不变(目前,我们只能这样说明,后面在修正)
• Mac地址一直在变
• 目的IP是一种长远目标,Mac是下一阶段目标,目的IP是路径选择的重要依 据,mac地址是局域网转发的重要依据
提炼IP网络的意义和网络通信的宏观流程

IP网络层存在的意义:提供网络虚拟层,让世界的所有网络都是IP网络,屏蔽 最底层网络的差异
6.Socket 编程预备
理解源IP地址和目的IP地址
• IP在网络中,用来标识主机的唯一性
• 注意:后面我们会讲IP的分类,后面会详细阐述IP的特点
但是这里要思考一个问题:数据传输到主机是目的吗?不是的。因为数据是给人用 的。比如:聊天是人在聊天,下载是人在下载,浏览网页是人在浏览?
但是人是怎么看到聊天信息的呢?怎么执行下载任务呢?怎么浏览网页信息呢?通过 启动的qq,迅雷,浏览器。
而启动的qq,迅雷,浏览器都是进程。换句话说,进程是人在系统中的代表,只要把 数据给进程,人就相当于就拿到了数据。
所以:数据传输到主机不是目的,而是手段。到达主机内部,在交给主机内的进程, 才是目的。 但是系统中,同时会存在非常多的进程,当数据到达目标主机之后,怎么转发给目标 进程?这就要在网络的背景下,在系统中,标识主机的唯一性。

认识端口号
端口号(port)是传输层协议的内容.


端口号范围划分

理解"端口号"和"进程ID"
我们之前在学习系统编程的时候,学习了pid表示唯一一个进程;此处我们的端口号也 是唯一表示一个进程.那么这两者之间是怎样的关系?
一个进程可以绑定多个端口号;但是一个端口号不能被多个进程绑定; • 进程ID属于系统概念,技术上也具有唯一性,确实可以用来标识唯一的一个进 程,但是这样做,会让系统进程管理和网络强耦合,实际设计的时候,并没有选择这 样做。
理解源端口号和目的端口号
传输层协议(TCP和UDP)的数据段中有两个端口号,分别叫做源端口号和目的端口号. 就是在描述"数据是谁发的,要发给谁";
理解socket

传输层的典型代表
如果我们了解了系统,也了解了网络协议栈,我们就会清楚,传输层是属于内核 的,那么我们要通过网络协议栈进行通信,必定调用的是传输层提供的系统调用,来 进行的网络通信。

认识TCP协议
此处我们先对TCP(Transmission Control Protocol 传输控制协议)有一个直观的认识; 后面我们再详细讨论TCP的一些细节问题
. • 传输层协议 • 有连接 • 可靠传输 • 面向字节流
认识UDP协议
此处我们也是对UDP(UserDatagramProtocol 用户数据报协议)有一个直观的认识;后 面再详细讨论.
• 传输层协议 • 无连接 • 不可靠传输 • 面向数据报
网络字节序
我们已经知道,内存中的多字节数据相对于内存地址有大端和小端之分,磁盘文件中的 多字节数据相对于文件中的偏移地址也有大端小端之分,网络数据流同样有大端小端之 分. 那么如何定义网络数据流的地址呢?


socket 编程接口

sockaddr 结构
socket API 是一层抽象的网络编程接口,适用于各种底层网络协议,如IPv4、IPv6,以及 后面要讲的UNIXDomainSocket.然而,各种网络协议的地址格式并不相同.


sockaddr 结构

sockaddr_in

虽然socket api的接口是sockaddr, 但是我们真正在基于IPv4编程时,使用的数据结 构是sockaddr_in; 这个结构里主要有三部分信息:地址类型,端口号,IP地址.
in_addr 结构

in_addr 用来表示一个IPv4的IP地址.其实就是一个32位的整数;