命名空间------网络(net)
一、网络命名空间:每个都是独立的"网络房间"
想象你的电脑是一栋大楼,每个网络命名空间就是大楼里的一个"独立房间":
- 每个房间里有自己的"网线接口"(网卡)、"门牌号"(IP 地址)、"导航地图"(路由表);
- 房间之间的网络互不干扰:你在 A 房间插网线、设 IP,B 房间完全看不到;
- 要让两个房间通信,必须用"特殊的线"(比如虚拟网线)连接它们。
二、一步步理解材料中的操作
1. 创建网络命名空间:建一个"新房间"
材料中用两种方式创建网络命名空间:
sudo unshare -n
:创建一个临时的网络命名空间(退出后自动销毁);sudo ip netns add mynet
:创建一个"持久化"的网络命名空间(名字叫mynet
),即使里面没有进程运行也不会消失(相当于给房间挂了个牌子,不会被轻易拆掉)。
查看已有的命名空间:
bash
sudo ip netns list # 会显示刚才创建的 mynet
2. 进入命名空间操作:"走进房间"
要操作 mynet
这个"房间"里的网络,需要用 ip netns exec
命令"进入房间":
bash
sudo ip netns exec mynet [命令] # 表示在 mynet 命名空间中执行某个命令
比如,查看 mynet
里的网卡:
bash
sudo ip netns exec mynet ip link show
此时会看到一个叫 lo
的网卡(环回接口),这是每个网络命名空间默认自带的"内部回环接口"(相当于房间里的"内部电话",用于进程自己跟自己通信)。
3. 启用环回接口:"接通内部电话"
默认情况下,lo
接口是关闭的(就像内部电话没插线),需要手动打开:
bash
sudo ip netns exec mynet ip link set dev lo up
打开后,命名空间内的程序可以通过 127.0.0.1
访问自己(比如本地服务)。
4. 创建 veth 对:拉一根"虚拟网线"
现在 mynet
这个房间是完全孤立的,和主机(默认命名空间)没有连接。怎么让它们通信?需要一根"虚拟网线"------veth 对(虚拟以太网接口对)。
veth 对是一对"捆绑在一起的虚拟网卡":就像一根网线的两端,一端插在主机(默认命名空间),另一端插在 mynet
房间,这样两边就能传数据了。
创建 veth 对:
bash
sudo ip link add veth0 type veth peer name veth1
- 这会创建两个虚拟网卡:
veth0
和veth1
,它们是"一对"------veth0
收到的数据会自动传给veth1
,反之亦然。
5. 连接命名空间:把网线"插进房间"
现在 veth0
和 veth1
都在主机的默认命名空间里,我们需要把 veth1
移到 mynet
房间:
bash
sudo ip link set veth1 netns mynet
此时:
- 主机(默认命名空间)里只剩
veth0
; mynet
房间里多了veth1
(相当于网线一端插进了房间)。
6. 配置 IP 地址:给"网线接口"分配门牌号
有了网线,还需要给两端的接口分配 IP 地址(门牌号)才能通信:
-
给
mynet
房间里的veth1
分配 IP:172.2.0.1/24
bashsudo ip netns exec mynet ip addr add 172.2.0.1/24 dev veth1 sudo ip netns exec mynet ip link set dev veth1 up # 启用这个接口
-
给主机的
veth0
分配 IP:172.2.0.2/24
bashsudo ip addr add 172.2.0.2/24 dev veth0 sudo ip link set dev veth0 up # 启用这个接口
7. 测试通信:两个"房间"能通话了
现在主机和 mynet
房间通过 veth 对连接,应该能互相 ping 通:
-
主机 ping
mynet
里的veth1
(IP:172.2.0.1):bashping -c1 172.2.0.1 # 成功收到回复
-
mynet
房间 ping 主机的veth0
(IP:172.2.0.2):bashsudo ip netns exec mynet ping -c1 172.2.0.2 # 成功收到回复
8. 为什么访问不了互联网?
此时 mynet
房间只能和主机通信,但不能上互联网(比如 ping 百度)。原因是:
mynet
房间的"导航地图"(路由表)里,没有"如何走到互联网"的路线。
要解决这个问题,需要:
- 在主机上创建一个"网桥"(相当于路由器),连接主机的物理网卡(能上互联网)和
veth0
; - 在
mynet
房间里设置"默认路由":告诉房间里的设备"上网请找主机的veth0
(172.2.0.2)"; - 主机开启 NAT 转发(相当于路由器的"地址转换"功能),让
mynet
的流量能通过主机的网卡访问互联网。
三、总结:网络命名空间的核心
- 每个网络命名空间是一个"独立的网络环境",有自己的网卡、IP、路由;
- veth 对是连接不同命名空间的"虚拟网线",让隔离的网络能通信;
- 容器(如 Docker)的网络隔离就是用网络命名空间实现的:每个容器一个独立的网络命名空间,通过 veth 对和主机/其他容器通信。
简单说,网络命名空间让进程"生活在不同的网络世界里",彼此独立又能通过"虚拟设备"按需连接。