Kubernets(k8s) 网络原理三:同主机内Pod相互访问

news2024/11/6 7:34:55

前两篇文章中我们介绍了pod怎么和宿主机通信以及pod怎么访问外网,这两种通信是理解pod间通信的基础。

关于pod间的相互访问,这里还需要细化一下。回想一下pod在k8s节点中的分布,两个pod可能分布在同一台宿主机上,也可能分布在不同宿主机上。这两种不同的拓扑结构,其组网模型也不一样。

本文先介绍第一种,同宿主内pod间如何访问

同宿主内pod间如何访问

关于同主机下的pod如何访问,有多种技术可以实现,因为这个pod发送的数据包,无论如何流转,始终不会出宿主机。

正如前文所说,要分析网络,总是离不开网络设备和路由表。

veth pair

既然之前文章我们说过,veth pair可以实现跨network namespace通信,最简单的我们可以用veth pair来做这件事情。

回想第一篇文章,我们的veth pair一端在pod的network namespace,另外一端在宿主机上,也就是root network namespace。如果我们将另外一端放到要通信pod的network namespace中不就可以了吗?

没错,这种模型完全可以。并且也很简单,但是要维护它却很困难。

因为这种模型类似一个点对点的结构,它要求pod两两之间都需要有veth pair。 

试想,如果同一个主机内存在N个Pod。那么每个pod ns中都会存在N-1个veth设备,以及N-1条路由规则,整个主机上存在N*N个veth pair。

那你可能会说了,node节点默认可运行的pod数目上限是110个,也不是天文数字,似乎也能接受

确实,但再试想一个场景,当一个pod的IP发生变化的时候,你需要做什么?这时候可能就需要修改其他所有pod的路由规则。

这样一想,似乎就不太好接受了,veth pair的数量和路由表的维护是一个麻烦事。

那如果有个角色,能够将这些veth pair 束口呢?


bridge

接着刚才那个问题,熟悉linux设备的同学可能马上会想到,Liunx网桥不就能干这件事情吗?

确实可以,Linux bridge可以让这些网络设备作为一个端口连接到网桥上来,如下图所示:

在这里,Linux bridge充当了一个二层交换机的角色。负责将来自不同veth设备的流量进行交换和转发。

网桥的定义:网桥是一个工作在数据链路层的网络设备,可以连接多个局域网段,它能够根据MAC地址来转发帧,使得多个网络段上的设备能够像在同一个网络中一样进行通信。
Linux网桥:在Linux系统中,网桥是通过软件模拟实现的。它允许系统管理员创建一个逻辑上的交换机,可以绑定多个物理或虚拟网络接口。

这个模型很简单,它解决了第一种模型下veth pair数量多和需要维护路由的问题。

还是以同一个主机下N个Pod为例,在这个模型下,每个Pod的network namespace下只需要存在一个veth设备,整个主机也只需要N个veth pair。同时pod间的路由规则不需要任何路由表来记录。

没了路由表,Linux bridge怎么知道发送给谁呢?

答案是广播和转发表

广播的含义是当Linux bridge一个端口收到报文,而转发表中没有目标地址的MAC时,就会广播所有连接到bridge上的网络接口。

转发表的含义是bridge会记录所有经过的报文的MAC地址,它是自学习的。

有了linux bridge,大大减少了管理的复杂度,下面通过一个小实验,感受一个pod间如何通信。

实验

本实验用到的命令在Kubernets(k8s) 网络原理一:Pod与宿主机通信文章中有简单介绍

如无特殊说明,我们实验都用network namespace代指pod

创建pod-1和pod-2

# ip netns add pod-1

# ip netns add pod-2

创建eth0和veth1,并将eth0加入pod-1 ns

# ip link add eth0 type veth peer name veth1

# ip link set eth0 netns pod-1

创建eth0和veth2,并将eth0加入pod-2 ns

# ip link add eth0 type veth peer name veth2

# ip link set eth0 netns pod-2

分别给pod-1和pod-2中的eth0配置ip

# ip netns exec pod-1 ip addr add 10.10.1.10/32 dev eth0

# ip netns exec pod-2 ip addr add 10.10.1.11/32 dev eth0

启动pod-1中veth pair,并添加路由,为什么添加路由请查看前一篇文章

# ip netns exec pod-1 ip link set eth0 up

# ip link set veth1 up

# ip netns exec pod-1  ip ro add default dev eth0

启动pod-2中veth pair,并添加路由

# ip netns exec pod-2 ip link set eth0 up

# ip link set veth2 up

# ip netns exec pod-2 ip ro add default dev eth0

创建网桥cbr0并启动,需要安装bridge-utils

# brctl addbr cbr0

# ip link set cbr0 up

将vteh1和veth2 添加进网桥

# brctl addif cbr0 veth1

# brctl addif cbr0 veth2

查看vteh1和veth2是否正确添加到网桥

# brctl show
bridge name     bridge id               STP enabled     interfaces
cbr0            8000.d6821b81f256       no              veth1
                                                        veth2

准备工作就绪,此时网络拓扑如下

我们尝试在pod-1中ping pod-2来模拟通信

# ip netns exec pod-1 ping -c 1 10.10.1.11
PING 10.10.1.11 (10.10.1.11) 56(84) bytes of data.
64 bytes from 10.10.1.11: icmp_seq=1 ttl=64 time=0.033 ms

--- 10.10.1.11 ping statistics ---
1 packets transmitted, 1 received, 0% packet loss, time 0ms
rtt min/avg/max/mdev = 0.033/0.033/0.033/0.000 ms

一切顺利,可以ping通,我们抓包看看这个过程发生了什么

# ip netns exec pod-1 tcpdump -pne -i eth0
12:20:24.329781 12:35:c3:bb:69:bc > Broadcast, ethertype ARP (0x0806), length 42: Request who-has 10.10.1.11 tell 10.10.1.10, length 28
12:20:24.329812 7e:55:17:b0:dc:bb > 12:35:c3:bb:69:bc, ethertype ARP (0x0806), length 42: Reply 10.10.1.11 is-at 7e:55:17:b0:dc:bb, length 28
12:20:24.329814 12:35:c3:bb:69:bc > 7e:55:17:b0:dc:bb, ethertype IPv4 (0x0800), length 98: 10.10.1.10 > 10.10.1.11: ICMP echo request, id 48389, seq 1, length 64
12:20:24.329827 7e:55:17:b0:dc:bb > 12:35:c3:bb:69:bc, ethertype IPv4 (0x0800), length 98: 10.10.1.11 > 10.10.1.10: ICMP echo reply, id 48389, seq 1, length 64
12:20:29.340282 7e:55:17:b0:dc:bb > 12:35:c3:bb:69:bc, ethertype ARP (0x0806), length 42: Request who-has 10.10.1.10 tell 10.10.1.11, length 28
12:20:29.340285 12:35:c3:bb:69:bc > 7e:55:17:b0:dc:bb, ethertype ARP (0x0806), length 42: Reply 10.10.1.10 is-at 12:35:c3:bb:69:bc, length 28

 查看MAC地址与端口的映射关系

# brctl showmacs cbr0
port no mac addr                is local?       ageing timer
  1     12:35:c3:bb:69:bc       no                 2.30
  2     7e:55:17:b0:dc:bb       no                 2.30
  1     d6:82:1b:81:f2:56       yes                0.00
  2     fe:c5:af:3f:03:b6       yes                0.00

值得说明的是,is local为no表示不是这个MAC地址不在root network namespace,上面回显中d6:82:1b:81:f2:56和fe:c5:af:3f:03:b6是veth1和veth2的mac地址,他们的is local为yes是因为veth1和veth2在root namespace。同时还可以看到相同端口号对应的正好是一对veth pair。

因此我们可以根据这两个信息总结关键流程如下:

  1. pod-1发起ICMP请求,因为无pod-2的MAC地址,于是先发起ARP请求
  2. pod-1 eth0发起ARP请求,希望获取10.1.10.11的mac地址
  3. cbr0收到广播的ARP请求,在转发表中记录MAC地址和端口
  4. 此时crb0中不存在pod-2中eth0的MAC地址,于是向所有将广播转发到其所绑定的所有端口,除了源veth
  5. pod-2 发现ieth0的ip刚好匹配,于是响应ARP请求,告诉自己的MAC地址
  6. crb0收到pod-2的ARP响应,在转发表中记录MAC地址和端口
  7. pod-1 向pod-2发起ICMP请求
  8. pod-2 响应ICMP请求

实验过程非常简单,这个模型能工作的原理就是利用了Linux bridge在二层通信。

实验环境清理

执行以下命令清理上文配置的设备

# ip netns del pod-1

# ip netns del pod-2

# ip link set cbr0 down

# brctl delbr cbr0

小结

整个模型非常简单,完全是利用Linux Bridge的特性,没有什么好总结的,既然不总结,那就提几个问题

  • veth1和veth2为什么不需要配置IP?
  • bridge模型下主机内pod通信需要主机的eth0参与吗?
  • 如果主机内pod通信不需要eth0参与,那什么时候需要它参与呢?
  • cbr0网桥什么时候需要配置IP?

这些问题可能没有一个唯一的答案,但是能够触发我们思考。

直接点就是想说,要分析一种网络模型,你必须要知道这个网络下的各种网络设备作用。以及当网络诉求变化时,相关网络设备应该如何变化。


route table

bridge可以充当束口的角色,但是如果不想引入Linux bridge这个网络设备,又该如何处理呢?

我们知道一个主机打开ip_forward转发的时候,他自己就可以转发报文。

转发报文也就意味着从一个网络接口,转给另外一个网络接口,这个好理解,也就是说只要将veth pair的另一端连接到root network namesapce,让主机就能看到这个网络设备就可以做到。

问题在于第二个,如何转发?

话都到这了,肯定会想到路由表嘛

没错,在这个模型下,就是让主机承担这个转发的任务,同时将这些veth pair收拢到root network namesapce里面来。

通信模型如下。

在这个模型下,省去了网桥概念,通信模型更为简单,但是需要维护root network namespace中的route规则。不过好在这不会太多。

还是以同一个主机下N个Pod为例,在这个模型下,每个Pod的network namespace下只需要存在一个veth设备,整个主机也只需要N个veth pair,此外root network namespace中还需要有N条路由规则。

同理,我们也进行一个小实验来模拟

实验

建议先查看Kubernets(k8s) 网络原理一:Pod与宿主机通信,理解network namespace怎么和主机通信

老规矩,我们创建pod-1和pod-2 network namespace代表两个pod

以路由的方式配置nework namespace在上一篇文章中已经介绍了每一条命令的作用,因此这里只罗列命令

配置pod-1

# ip netns add pod-1

# ip link add eth0 type veth peer name veth1

# ip link set eth0 netns pod-1

# ip netns exec pod-1 ip addr add 10.10.1.10 dev eth0

# ip netns exec pod-1 ip link set dev eth0 up

# ip netns exec pod-1 ip route add 169.254.1.1 dev eth0

# ip netns exec pod-1 ip route add default via 169.254.1.1 dev eth0

# ip link set dev veth1 up 

# echo 1 > /proc/sys/net/ipv4/conf/veth1/proxy_arp

# echo 1 > /proc/sys/net/ipv4/ip_forward

配置pod-2

# ip netns add pod-2

# ip link add eth0 type veth peer name veth2

# ip link set eth0 netns pod-2

# ip netns exec pod-2 ip addr add 10.10.1.11 dev eth0

# ip netns exec pod-2 ip link set dev eth0 up

# ip netns exec pod-2 ip route add 169.254.1.1 dev eth0

# ip netns exec pod-2 ip route add default via 169.254.1.1 dev eth0

# ip link set dev veth2 up 

# echo 1 > /proc/sys/net/ipv4/conf/veth2/proxy_arp

# echo 1 > /proc/sys/net/ipv4/ip_forward

然后在主机上配置路由表

# ip route add 10.10.1.10 dev veth1 scope link

# ip route add 10.10.1.11 dev veth2 scope link 

路由表的意思是说,所有发给10.10.1.10的报文都从veth1出去,同理,所有发给10.10.1.11的报文都从veth2 出去。

此时网络拓扑如下图所示:

此时我们尝试在pod-1中ping pod-2来模拟通信

# ip netns exec pod-1 ping -c 1 10.10.1.11
PING 10.10.1.11 (10.10.1.11) 56(84) bytes of data.
64 bytes from 10.10.1.11: icmp_seq=1 ttl=63 time=0.035 ms

--- 10.10.1.11 ping statistics ---
1 packets transmitted, 1 received, 0% packet loss, time 0ms
rtt min/avg/max/mdev = 0.035/0.035/0.035/0.000 ms

没有问题,但是整个过程发生了什么呢,我们来抓包看一下

在pod-1中抓包

# ip netns exec pod-1 tcpdump -n -i eth0
09:53:29.297355 ARP, Request who-has 169.254.1.1 tell 10.10.1.10, length 28
09:53:29.382379 ARP, Reply 169.254.1.1 is-at be:7c:fa:0e:81:25, length 28
09:53:29.382386 IP 10.10.1.10 > 10.10.1.11: ICMP echo request, id 36618, seq 1, length 64
09:53:29.541810 IP 10.10.1.11 > 10.10.1.10: ICMP echo reply, id 36618, seq 1, length 64

这个过程其实我们已经在pod与宿主机通信文章中分析过了,这里简单梳理以下流程

  • pod-1中执行ping命令,通过socket调用给到pod-1协议栈
  • pod-1协议栈准备发起ICMP报文,查找路由表,获知从eth0出去,下一跳是169.254.1.1
  • pod-1协议栈查找Arp表,没有169.254.1.1的MAC地址,于是先发起Arp请求
  • veth1收到pod-1中eth0发来的Arp请求,因为配置了proxy_arp,于是响应自己的MAC地址
  • pod-1协议栈收到响应,组装ICMP报文,发送给veth-1
  • veth-1收到ICMP报文,交给自己的协议栈,即host协议栈
  • host协议栈因开启了ip_forward,于是查找本地路由表,发现应该从veth2设备发送
  • veth2和pod-2中eth0为veth pair关系,于是eth0收到pod-1发送的ICMP报文,交给pod-2协议栈
  • pod-2协议栈处理报文,按照原路返回响应报文。

小结

路由规则关心的是IP,而不是MAC地址,换句话说当跨物理网络时,路由模式的好处就显示出来了。虽然我们一台主机内不会存在跨网段,但是在后面我们总会用到的。

此外还值得说的一点是使用bridge的方式,Linux bridge会根据目的地址进行广播,所有设备都能收到,而L3 路由的方式则会隔离广播,请求的目的地址是固定的,因此广播限定在指定的广播域中,其它设备不会收到广播。

总结

本文分析两种主机内的组网模型,他们都可以达到主机内Pod相互通信的目的。只是采用不同的技术去实现,这两种方式没有严格的好坏之分,只是适用的场景不一样。

例如fiannel和docker就是采用bridge这种方式,依赖于一个网桥cni0(docker0)进行二层数据的转发。而calico就使用的L3路由的方式。

理解了主机内pod如何通信,在下一篇文章中,我们将分析整个容器组网最复杂的一部分,不同主机上的pod如何通信。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1979609.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

可视化图表与页面源代码显示

可视化图表与页面源代码显示 页面效果&#xff1a; <!DOCTYPE html> <html lang"en" style"height: 100%"> <head><meta charset"utf-8"><title>饼状图</title><style>body {display: flex;height:…

基于51单片机的交通信号灯proteus仿真设计

1.功能简介 交通信号灯是一种经典应用电路&#xff0c;本设计基于51单片机&#xff0c;利用Proteus仿真软件构建了一个模拟交通信号灯系统。该系统能够模拟真实交通环境中的信号变化&#xff0c;包括红灯、黄灯和绿灯的切换&#xff0c;以及倒计时显示等功能&#xff0c;各种灯…

谷歌出品,一款免费的智能绘图工具

AutoDraw是由Google开发的一款基于网络的智能绘图工具&#xff0c;旨在通过人工智能技术帮助用户快速、简便地创建图画和图表。该工具于2017年4月11日由谷歌创意实验室推出&#xff0c;并迅速获得了广泛关注。 AutoDraw的核心功能是利用机器学习算法识别用户的草图或涂鸦&…

C++STL专题-string类

目录 1.标准库中的string类 1.1 string类 2.2 auto和范围for 2.2.1 auto关键字 2.2.2 范围for 2.3 string类的常用接口讲解 1.string类对象的常见构造 2.元素访问 3.迭代器(iterator) 3.1 begin 和 end 3.2 rbegin 和 rend 4.容器 5.修改 5.1 append 5.2 assign…

在C#中为图片添加数字水印的几种办法

最近在写个人项目时&#xff0c;有遇到需要将图片加上水印防止被盗取的需求。这里找了几种实现方式&#xff0c;可供有需要的朋友参考。 本身我不是搞算法这块的&#xff0c;所以这里只是找了一些实现&#xff0c;也没有继续深究下去。 以前在学校的时候从书上了解过可以将一…

cmake常用命令学习

1.include https://blog.csdn.net/qq_38410730/article/details/102677143 CmakeLists.txt才是cmake的正统文件&#xff0c;而.cmake文件是一个模块文件&#xff0c;可以被include到CMakeLists.txt中。 include指令一般用于语句的复用&#xff0c;也就是说&#xff0c;如果有…

OBS Studio:如何打造专业级的视频直播体验

1.简介 OBS&#xff08;Open Broadcaster Software&#xff09;是一款开源的视频录制和直播软件&#xff0c;广泛用于视频制作、游戏直播和网络直播。它支持多种操作系统&#xff0c;包括Windows、macOS和Linux。OBS提供了丰富的功能&#xff0c;包括但不限于&#xff1a; **…

聊聊跨境电商平台与固定IP的那些事

IP地址网络地址&#xff08;网络号&#xff09;主机地址&#xff08;地址号&#xff09;&#xff0c;IP地址是一台电脑在网络中的唯一标识&#xff0c;可分为固定IP与动态IP。那么IP地址的分类有哪些&#xff1f;什么IP适合亚马逊/eBay/速卖通等平台运营时使用&#xff1f; A类…

Spring5 的日志学习

我们在使用 Spring5 的过程中会出现这样的现像&#xff0c;就是 Spring5 内部代码打印的日志和我们自己的业务代码打印日志使用的不是统一日志实现&#xff0c;尤其是在项目启动的时候&#xff0c;Spring5 的内部日志使用的是 log4j2&#xff0c;但是业务代码打印使用的可能是 …

DNS安全概述

一、DNS的解析过程 1.递归解析 递归解析是一种由DNS客户端&#xff08;通常是用户的应用程序&#xff0c;如一个浏览器&#xff09;向本地DNS解析器发出解析请求&#xff0c;然后本地DNS解析器负责查询最终结果并将结果返回给客户端&#xff0c;而中间的所有查询请求都由本地D…

每日OJ_牛客HJ62 查找输入整数二进制中1的个数

目录 牛客HJ62 查找输入整数二进制中1的个数 解析代码 牛客HJ62 查找输入整数二进制中1的个数 查找输入整数二进制中1的个数_牛客题霸_牛客网 解析代码 本题是计算一个数二进制表示中1的个数&#xff0c;通过&#xff08;n >> i) & 1可以获取第i位的二进制值&…

基于Spring boot + Vue的校园论坛

作者的B站地址&#xff1a;程序员云翼的个人空间-程序员云翼个人主页-哔哩哔哩视频 csdn地址&#xff1a;程序员云翼-CSDN博客 1.项目技术栈&#xff1a; 前后端分离的项目 后端&#xff1a;Springboot MybatisPlus 前端&#xff1a;Vue ElementUI 数据库&#xff1a; …

聚星文社 聚星3高级推理创作

聚星文社 聚星3高级推理创作 Docshttps://qvfbz6lhqnd.feishu.cn/wiki/D3YLwmIzmivZ7BkDij6coVcbn7W

CAS5.3自定义登录校验规则

前一篇文章介绍过CAS自定义用户信息, 这个用户信息实在登录成功后加到session中的, 今天来介绍一下CAS5.3怎么自定义登录校验逻辑 思路 有了前一篇文章的铺垫这一次自定义登录校验其实就很简单了, 因为想要把用户信息放入到session中是一定要在登陆的时候完成的,因此这次我们…

Codeforces Round 960 (Div. 2) A~E

A. Submission Bait &#xff08;思维&#xff09; 题意&#xff1a; A l i c e Alice Alice 和 B o b Bob Bob 正在玩一个数组 a a a 中大小为 n n n 的游戏。 他们轮流进行操作&#xff0c; A l i c e Alice Alice先开始。无法操作的玩家将输掉。首先&#xff0c;将变量…

常用控件之 QWidget

目录 一、控件概述 1.关于控件体系的发展&#xff1a; 二、QWidget 核心属性 1.核心属性概览 2.enabled 3.geometry &#x1f335;window frame&#xff08;窗口框架&#xff09; 的影响 4.windowTitle 5.windowIcon &#x1f335;使用 qrc 文件管理资源 6.windowOpa…

微信公众号上线12周年了,12年前的公众号历史文章怎么找?抓取了公众号历史文章同步到博客,找起来方便了

为了方便看看12年来这些号发过的文章 2023 批量下载公众号文章内容/话题/图片/封面/视频/音频&#xff0c;导出文章pdf和抓取文章数据包含阅读数/点赞数/在看数/留言数&#xff0c;我抓取了其中一些号的所有历史文章同步到博客 : 比如深圳卫健委从2014年更新&#xff0c;到2023…

Reqable:跨平台HTTP开发与调试工具

在当今快速发展的互联网时代&#xff0c;HTTP协议作为网络通信的基础&#xff0c;其开发和调试工具的选择对开发效率有着重要影响。本文将详细介绍一款新型的跨平台HTTP开发和调试工具——Reqable&#xff0c;它支持HTTP1、HTTP2以及最新的HTTP3(QUIC)协议&#xff0c;为开发、…

超秒集物:助力品牌商腾飞,共筑强国梦想

在当今竞争激烈的商业世界中&#xff0c;每一个小微企业都怀揣着成为世界 500 强的梦想。它们虽然微小&#xff0c;但都在努力绽放出属于自己的光芒。而超秒集物&#xff0c;以其独特的平台力量&#xff0c;为众多小微企业照亮了前行的道路&#xff0c;助力它们追逐梦想&#x…

贝叶斯之光:照亮机器学习领域的算法瑰宝

一、贝叶斯算法概述 贝叶斯算法起源于英国数学家托马斯贝叶斯&#xff08;Thomas Bayes&#xff09;在18世纪提出的贝叶斯定理。该定理是概率论中的一个重要定理&#xff0c;描述了条件概率之间的关系。其基本形式可以表示为&#xff1a; P(A∣B)P(B)P(B∣A)P(A)​ 其中&…