【Linux网络编程】(一)初识计算机网络:从独立主机到协议世界的入门之旅


前言

作为一名程序员,不管是做后端开发、嵌入式开发还是前端开发,计算机网络都是绕不开的核心基础。我们每天用浏览器访问网页、用 IM 工具聊天、用服务器部署应用,背后都是计算机网络在默默支撑。从最初的单台独立计算机,到如今互联互通的互联网世界,网络的发展本质上是为了解决设备协同、数据共享的核心问题。这篇文章就从计算机网络的发展背景出发,带大家一步步认识网络的核心 ------ 协议,搞懂为什么网络需要协议、协议是如何设计的,为后续深入学习 TCP/IP、Socket 编程打下基础。下面就让我们正式开始吧!


一、计算机网络的发展:从 "各自为战" 到 "互联互通"

计算机刚诞生的时候,是以独立模式存在的,每一台计算机都是一个 "信息孤岛"。不同终端 A、B、C 各自存储客户数据,运行专属业务,比如终端 A 运行业务 1、终端 B 运行业务 2,一旦操作人员需要切换业务,就得物理移动到对应主机前操作,效率极低。此时的计算机只是单个的工具,无法发挥协同工作的价值。

随着计算机的普及,人们开始有了数据共享、业务互通 的需求,于是就有了网络互联 的雏形:将多台计算机连接在一起,为不同业务配置专用的服务器,比如小松专用计算机、小竹专用计算机,每个人可以在自己的独立计算机上自由切换业务 1、2、3,所有共享数据由服务器集中管理。这一步的改变,让计算机从 "单机工具" 变成了 "协同工具",也是网络的核心价值体现 ------连接产生价值

当连接的计算机数量越来越多,简单的互联已经满足不了需求,于是就有了局域网(LAN)广域网(WAN) 的概念。

  • 局域网通过交换机、路由器 将一定范围内的计算机连接起来,比如公司的内网、校园网,实现小范围的高速数据传输;
  • 广域网则把远隔千里的局域网连接在一起,比如大阪的 LAN、东京的 LAN、洛杉矶的 LAN,通过多台路由器的级联,实现跨地域的通信。

这里要注意,局域网和广域网其实是相对概念,比如我们常说的 "内网",对于整个互联网来说是局域网,但对于内网中的设备来说,就是一个完整的网络。而计算机网络的产生并不是偶然,因为计算机是人的工具,人需要协同工作,就注定了设备之间需要连接,网络的出现是技术发展的必然结果。

从独立模式到网络互联,再到局域网和广域网,每一步发展都围绕着一个核心:降低数据交互的成本,提升设备协同的效率。而要实现真正的互联互通,光有硬件连接还不够,还需要一套统一的 "沟通规则"------ 这就是协议。

二、初识协议:网络世界的 "通用语言"

2.1 协议是什么?本质是一种 "约定"

生活中我们处处有协议:打电话时约定电话铃响 3 声没人接就挂掉,见面时约定握手表示友好,这些双方达成一致的规则 ,就是协议。计算机网络中的协议,本质上也是一样的,是计算机之间进行数据通信的约定和规则

计算机之间的传输媒介是光信号和电信号 ,这些信号只能通过频率的高低、信号的强弱 来表示 0 和 1 这样的二进制信息。要想用 0 和 1 传递文字、图片、视频等复杂信息,就必须约定好双方的数据格式:比如用多少个 01 组合表示一个字符,用什么标识一段数据的开始和结束,用什么方式验证数据是否传输错误。

举个简单的例子:如果主机 A 用频率高低 表示 0 和 1,主机 B 用信号强弱表示 0 和 1,哪怕两者约定了 "传输 10 个字符就停止",最终也无法正常通信 ------ 就像一个人说中文,一个人说葡萄牙语,哪怕都遵守 "一句话说 10 个字" 的规则,也无法理解对方的意思。

所以,完善的协议必须是细致、统一的,不仅要约定通信的基本规则,还要约定数据的表示方式、传输方式、校验方式等,并且要求所有参与通信的设备都严格遵守。

2.2 为什么需要统一的网络协议?解决 "设备异构" 的问题

我们身边的计算机设备,有着各种各样的 "出身":

  • **硬件层面:**有戴尔、联想、华为等不同厂商的计算机,有交换机、路由器、集线器等不同的网络设备;
  • **软件层面:**有 Windows、Linux、macOS 等不同的操作系统,有不同的应用程序。

如果每个厂商都按照自己的规则设计通信方式,那么戴尔的电脑就无法和华为的服务器通信,Windows 系统就无法和 Linux 系统交换数据,整个网络世界就会回到 "各自为战" 的状态。

要解决这种设备异构 的问题,就需要有权威的组织或机构站出来,制定一套全球通用的网络协议标准,让所有厂商、所有设备都遵循这套标准进行设计和生产。这就像全世界的交通规则都约定 "靠右行驶(部分国家靠左)""红灯停绿灯行",只有这样,不同的车辆、不同的驾驶员才能在同一条道路上安全行驶。

2.3 谁有资格制定网络协议标准?业界公认的 "规则制定者"

网络协议标准的制定,需要具备技术权威性、行业认可度,不是任何公司或组织都能制定的。能定制协议标准的主体主要分为五类,涵盖国际组织、区域组织、企业、民间团体和官方机构,各自在不同领域发挥着重要作用:

(1)国际标准化组织:全球通用标准的核心制定者

这类组织是网络协议标准的 "核心玩家",制定的标准适用于全球范围,是互联网互联互通的基础。

  • IEEE(电气和电子工程师协会) :由计算机和工程领域的专家组成,是全球最大的技术专业组织之一,制定了全世界电子、电气、计算机领域约 30% 的标准。其中IEEE 802 系列标准是网络领域的核心,涵盖了局域网、广域网、无线局域网等多种网络技术,比如我们常用的以太网、WiFi,都基于 IEEE 802 标准。
  • ISO(国际标准化组织) :由多个国家的标准化团体组成,最著名的成果是OSI 七层网络模型,这个模型定义了网络通信的七层协议结构,为网络协议的设计提供了逻辑框架,虽然实际应用中 TCP/IP 更普及,但 OSI 模型在学术和理论研究中有着不可替代的地位。
  • ITU(国际电信联盟):联合国下属的专门机构,负责制定电信领域的国际标准,比如电话通信、宽带网络的标准。ITU-T 和 ISO 深度合作,确保了通信技术的全球兼容性,让不同国家的电信网络能够互联互通。

(2)区域标准化组织:针对特定区域的定制化标准

这类组织主要为特定区域的通信技术发展制定标准,解决区域内的网络互联问题,代表有:

  • ETSI(欧洲电信标准学会):由欧洲共同体各国政府资助,聚焦欧洲的电信行业,制定适合欧洲地区的网络、通信标准;
  • ASTAP(亚洲与泛太平洋电信标准化协会):由日本、韩国发起,专注于亚太地区的信息通信基础设施标准化,提升亚太地区各国之间的网络连接效率。

(3)企业:细分领域的协议定制者

部分技术实力雄厚的企业,会在通用标准的基础上,针对细分领域 自研协议栈,并进行定制化改动,这也是企业的核心竞争力。比如泰凌微,在低功耗蓝牙、ZigBee、Thread、Matter 等物联网协议领域深耕,自研了对应的软件协议栈,还将这些协议应用在智能电子价签、智能遥控、智能家居等物联网场景中。

企业定制的协议一般聚焦于特定场景,是对通用标准的补充,而非替代,最终还是会兼容全球通用标准。

(4)民间国际团体:互联网协议的 "迭代者"

这类团体并非官方组织,而是由全球的技术爱好者、工程师组成,专注于互联网协议的开发和推广,最具代表性的是IETF(互联网工程师任务组)

IETF 是一个志愿组织,通过RFC(请求评论) 文档发布新的协议标准或取代旧的标准,我们熟知的TCP/IP 协议族,就是由 IETF 主导开发和推广的。IETF 的特点是开放、灵活,能快速响应互联网技术的发展,及时迭代协议标准,适应新的网络场景。

(5)官方机构:协议标准的 "监督者"

这类机构主要负责对通信技术、协议标准进行审查和监督 ,确保其符合公众利益和国家法规,代表是FCC(美国联邦通信委员会)。FCC 负责管理美国的无线电、电视、有线通信,对通信产品的技术特性、协议标准进行审查,确保产品的安全性和兼容性,间接推动了协议标准的规范化。

2.4 协议分层:让网络协议更 "易维护、可扩展"

协议的本质也是软件,而软件设计的核心原则之一是模块化、解耦合 ,网络协议也遵循这个原则,被设计成层状结构 ,这就是协议分层。协议分层不是凭空设计的,而是为了解决协议设计和维护中的实际问题,我们先从一个生活中的例子,理解协议分层的好处。

生活中的分层例子:打电话的 "两层协议"

我们打电话的过程,可以拆分成语言层通信设备层两层协议:

  • 语言层:双方约定用同一种语言沟通,比如都用汉语,这一层的核心是 "内容的表达和理解";
  • 通信设备层:双方使用的电话机、电话线组成的通信系统,这一层的核心是 "信号的传输和转换"。

这两层协议是解耦合的:

  • 如果只是更换通信设备,比如从电话机换成无线电,只需要修改通信设备层的协议,语言层仍然可以用汉语,不需要做任何改动;
  • 如果只是更换沟通语言,比如从汉语换成英语,只需要修改语言层的协议,通信设备层仍然可以用电话机,不需要做任何改动。

这样的设计,让每一层的修改都不会影响到其他层,降低了维护成本 ,也让协议的可扩展性更强。如果没有分层,把 "语言规则" 和 "设备规则" 混在一起,那么更换任何一个环节,都需要重新制定整套规则,效率极低。

网络协议的分层:从两层到七层,再到工程实践的五层 / 四层

打电话的例子只有两层协议,而计算机网络的通信场景更复杂,需要处理数据的封装、传输、路由、校验、应用等多个环节,因此网络协议需要分更多的层。

最经典的协议分层模型是OSI 七层模型 ,由 ISO 制定,将网络通信从逻辑上分为 7 层,每一层都有明确的功能和对应的物理设备,核心作用是帮助不同类型的主机实现可靠的数据传输。OSI 七层模型的最大优点是将服务、接口、协议三个概念明确区分,概念清晰、理论完整,为网络协议的设计提供了完整的框架。

OSI 七层模型的分层及核心功能如下:

  1. 应用层:针对特定应用的协议,负责应用程序间的沟通,比如电子邮件(SMTP)、文件传输(FTP)、远程登录(Telnet),还负责设备固有数据格式和网络标准数据格式的转换;
  2. 表示层:负责数据的加密、解密、压缩、解压缩,将应用层的数据转换成适合网络传输的格式(文档中因排版略去,是 OSI 七层的重要组成);
  3. 会话层:负责通信管理,建立和断开通信连接,管理传输层以下的分层,比如约定连接的建立时间、断开时间、保持时长;
  4. 传输层:负责两台主机之间的可靠数据传输,解决数据丢失、重复传输的问题;
  5. 网络层:负责地址管理和路由选择,比如通过 IP 地址标识主机,通过路由表规划数据传输的路径;
  6. 数据链路层:负责互连设备之间的数据帧传送和识别,实现数据帧与比特流之间的转换、分段转发;
  7. 物理层:负责光 / 电信号的传递,界定连接器和网线的规格,将 0 和 1 转换成电压的高低、灯光的闪灭等物理信号。

虽然 OSI 七层模型理论上非常完善,但在工程实践 中,会话层和表示层的功能很难直接接入到操作系统中,无法落地实现。因此,实际应用中我们采用的是TCP/IP 五层模型 ,而如果忽略物理层(硬件层面),只考虑软件层面,就成了TCP/IP 四层模型,这也是我们学习网络编程的核心模型。

TCP/IP 五层模型的分层及核心功能、对应设备如下,是我们后续学习的重点:

  1. 应用层:负责应用程序间的沟通,如 HTTP、SMTP、FTP、Telnet,网络编程主要针对这一层;
  2. 传输层:负责两台主机之间的数据传输,核心协议是 TCP(可靠传输)和 UDP(无连接传输);
  3. 网络层 :负责地址管理和路由选择,核心协议是 IP,对应的物理设备是路由器
  4. 数据链路层 :负责设备间的数据帧传送和识别,核心标准有以太网、无线 LAN,对应的物理设备是交换机
  5. 物理层 :负责光 / 电信号的传递,涉及网线、光纤、WiFi 电磁波等,对应的物理设备是集线器(Hub)

不同网络设备的协议实现范围

协议分层后,不同的网络设备实现的协议层也不同,这也是设备功能差异的核心原因:

  • 主机:操作系统内核实现了从传输层到物理层的所有内容,应用层由用户程序实现;
  • 路由器:实现了从网络层到物理层的内容,核心功能是路由选择和跨网段数据转发;
  • 交换机:实现了从数据链路层到物理层的内容,核心功能是局域网内的数据帧转发;
  • 集线器:只实现了物理层的内容,只是简单的信号放大和转发,无数据识别能力。

当然这不是绝对的,现在很多网络设备都做了功能扩展,比如部分交换机支持网络层的转发,部分路由器支持传输层的端口转发,但其核心功能仍然对应着固定的协议层。

三、协议的本质:通信双方都认识的 "结构化数据"

学到这里,我们已经知道协议是网络通信的规则,是分层设计的,但协议在代码层面到底是什么样的?其实用一句朴素的话总结:协议就是通信双方都认识的结构化数据类型

我们可以用 C/C++ 的结构体来理解这个概念,因为操作系统的源代码一般都是用 C/C++ 编写的,网络协议的实现也不例外。

3.1 用结构体理解协议:共识的本质是 "相同的代码实现"

假设在网络协议的某一层,通信双方都定义了同一个 C 语言结构体:

cpp 复制代码
// 通信双方共同约定的协议结构体
struct Protocol {
    int a;    // 字段1
    int b;    // 字段2
    int c;    // 字段3
    char data[1024]; // 有效载荷
};

主机 A 要给主机 B 发送数据,会创建这个结构体的实例,赋值后发送:

cpp 复制代码
#include <stdio.h>
#include <string.h>

// 共同约定的协议结构体
struct Protocol {
    int a;
    int b;
    int c;
    char data[1024];
};

int main() {
    // 主机A构造协议数据
    struct Protocol send_data;
    send_data.a = 10;
    send_data.b = 20;
    send_data.c = 30;
    strcpy(send_data.data, "Hello, Network Protocol!");
    
    // 将结构体数据发送到网络(后续通过Socket实现,此处仅示意)
    send_to_network(&send_data, sizeof(send_data));
    
    return 0;
}

主机 B 接收到数据后,用同一个结构体来解析:

cpp 复制代码
#include <stdio.h>

// 与主机A完全相同的协议结构体
struct Protocol {
    int a;
    int b;
    int c;
    char data[1024];
};

int main() {
    struct Protocol recv_data;
    // 从网络接收数据(后续通过Socket实现,此处仅示意)
    recv_from_network(&recv_data, sizeof(recv_data));
    
    // 解析数据
    printf("a = %d\n", recv_data.a);  // 输出a = 10
    printf("b = %d\n", recv_data.b);  // 输出b = 20
    printf("c = %d\n", recv_data.c);  // 输出c = 30
    printf("data = %s\n", recv_data.data); // 输出data = Hello, Network Protocol!
    
    return 0;
}

因为主机 A 和主机 B 使用了完全相同的结构体类型 ,所以主机 B 能准确识别并提取出a=10b=20c=30以及有效载荷数据。这种双方共同遵守的结构化数据定义,就是协议的本质 ------ 共识。

3.2 分层协议的核心:每层都有自己的 "结构化数据"

协议是分层的,因此每一层都有自己的协议结构体(报头),同层之间互相认识对方的协议,不同层之间通过 "接口" 传递数据。

比如 TCP/IP 五层模型中,应用层有应用层的协议结构体(如 HTTP 的请求头),传输层有传输层的协议结构体(如 TCP 的报头),网络层有网络层的协议结构体(如 IP 的报头),数据链路层有数据链路层的协议结构体(如以太网的帧头)。

当数据在网络中传输时,会经历封装解包的过程:

  • 封装:数据从应用层向下传递,每一层都会在数据前面加上自己的协议报头(结构化数据),最终形成一个完整的数据包;
  • 解包:数据到达目标主机后,从物理层向上传递,每一层都会剥掉自己的协议报头,解析后将数据传递给上一层,最终到达应用层。

这个过程就像我们寄快递:

  • 封装:把要寄的东西(有效载荷)装进快递盒,贴上快递单(应用层报头),然后交给快递公司,快递公司加上物流单(传输层报头),再交给分拣中心,分拣中心加上路由单(网络层报头),最后交给快递员,快递员加上面单(数据链路层报头);
  • 解包:快递到达目的地后,快递员剥掉面单,分拣中心剥掉路由单,快递公司剥掉物流单,收件人剥掉快递单,最终拿到里面的东西。

其中,快递单、物流单、路由单、面单 就是各层的协议报头,要寄的东西 就是有效载荷,而报头 + 有效载荷就是每一层的报文。

3.3 网络报文的不同称谓:段、数据报、帧

不同的协议层,对封装后的数据包有不同的称谓,这是网络学习中需要记住的基础概念:

  • 传输层 :数据包称为段(Segment),如 TCP 段、UDP 段;
  • 网络层 :数据包称为数据报(Datagram),如 IP 数据报;
  • 数据链路层 :数据包称为帧(Frame),如以太网帧;
  • 应用层 :一般直接称为数据(Data)有效载荷(Payload)

这些称谓的差异,本质上是因为各层的协议报头和功能不同,但核心都是 "结构化数据 + 有效载荷"。


总结

这篇文章是计算机网络的入门内容,搞懂这些基础概念,才能为后续学习局域网通信原理、IP 地址、MAC 地址、端口号、TCP/UDP 协议、Socket 编程打下基础。下一篇文章,我们会深入讲解局域网的通信原理,搞懂 MAC 地址、IP 地址的区别,以及数据在局域网中是如何传输的。

我后续会结合 C/C++ 的 Socket 编程代码,从实践角度讲解网络协议的使用,让大家真正理解 "协议在代码中如何实现"。如果这篇文章对你有帮助,欢迎点赞、收藏、关注,一起学习计算机网络!

相关推荐
原来是猿2 小时前
Linux-【文件系统上】
linux·服务器·数据库
寂柒5 小时前
信号量——基于环形队列的生产消费模型
linux·ubuntu
一袋米扛几楼986 小时前
【密码学】CrypTool2 工具是什么?
服务器·网络·密码学
林姜泽樾9 小时前
Linux入门第十二章,创建用户、用户组、主组附加组等相关知识详解
linux·运维·服务器·centos
xiaokangzhe9 小时前
Linux系统安全
linux·运维·系统安全
feng一样的男子9 小时前
NFS 扩展属性 (xattr) 提示操作不支持解决方案
linux·go
南棱笑笑生9 小时前
20260310在瑞芯微原厂RK3576的Android14查看系统休眠时间
服务器·网络·数据库·rockchip
yy55279 小时前
LNAMP 网络架构与部署
网络·架构
XDHCOM10 小时前
ORA-32152报错咋整啊,数据库操作遇到null number问题远程帮忙修复
服务器·数据库·oracle