🏤unRAID macvlan 失联问题解析(以及如何给Docker分配独立网口)
00 分钟
2023-7-9
2024-1-30
type
status
date
slug
summary
tags
category
icon
password
💡
2023-08-31:Unraid 更新了 6.12.4 版本(官方版本说明),根据官方文档的说明,此版本解决了 macvlan call traces 问题,读者可以按照这里的方法步骤去解决:6.12.4 关于失联问题的解决办法以及相关更新说明
这段时间 6.12 版本出来之后,不少人遇到了 unRAID 失联的问题,比如:
但实际上类似的问题在 6.12 版本之前也或多或少有出现,因为这个问题跟特定的硬件(比如说路由器)和系统软件层面有关,有时候影响不大,但有时候影响大了就会出现这里所说的"失联”问题。
“失联”是表象,在操作系统层面, 此问题具体的体现是系统内核 macvlan_process_broadcast 报错(参考案例):
参考:报错日志
先说解决方法,官方针对此问题也提供了具体的两种解决办法:
  1. 在 Docker 设置中将自定义网络类型由 Macvlan 修改为 Ipvlan。
  1. 单独拿出一个网口来给到 Docker 容器使用。
本文将针对第二种方法进行具体介绍。

1、为什么会有这种问题出现

此问题与 Docker 的网络驱动(Docker Network Driver)—— Macvlan 和 Ipvlan 有关,同时也与路由器有关。
遇到此问题的不少用户往往都有以下特点:
  • Docker自定义网络类型”使用了 macvlan
    • notion image
  • 启用了 “自定义网络” (Custom Network):
    • notion image
  • 并给某些 Docker 容器分配了固定 IP 地址
    • notion image

1.2、影响因素:macvlan 和 ipvlan

当使用 Docker 构建应用程序时,Docker提供了多种网络驱动程序,其中包括 macvlan 和 ipvlan 。这些网络驱动程序允许 Docker 容器在宿主机网络上直接创建虚拟网络接口,使容器可以具有自己的独立网络身份。
  1. Macvlan(MAC VLAN)允许将容器连接到基础宿主机网络中的物理网络,每个容器都分配了一个唯一的 MAC 地址:
      • 容器通过宿主机的物理网络接口直接与网络通信,就像它们是物理设备一样。
      • 这使得容器可以与宿主机网络中的其他设备进行直接通信,而无需进行额外的NAT(网络地址转换)操作。
      • Macvlan网络适用于需要将容器直接连接到物理网络的场景,例如在容器中运行网络应用程序或需要访问外部网络资源的容器。
  1. Ipvlan(IP VLAN)也允许将容器连接到基础宿主机网络中的物理网络,但与Macvlan不同,每个容器分配了一个唯一的IP地址:
      • 容器通过宿主机的物理网络接口直接与网络通信,就像它们是独立的网络设备一样。
      • Ipvlan网络提供了更高的网络性能和更低的延迟,相对于Macvlan而言。
      • Ipvlan网络适用于需要高性能和低延迟的容器应用程序,例如高负载的网络应用程序或需要直接访问外部网络资源的容器。
由于 Macvlan 这种网络驱动的特点,每一个使用了固定 IP 地址的容器都会有一个独立的 MAC 地址,就好像每一个容器都是一个拥有物理网卡的独立设备。
这里就引出了一个问题,那就是在现实中一张物理网卡的一个网口有且只有一个 MAC 地址,但由于 Macvlan 可以允许给不同的容器分配独立的 MAC,那就相当于这张物理网卡除了自身现实中的 MAC 地址之外,它还会有很多个 MAC 地址,那么这时候对于路由器来说该怎么处理?

1.3、影响因素:路由器

在这种情况下,路由器的接口必须支持“混杂模式(Promiscuous Mode)”。
路由器的混杂模式(Promiscuous Mode)是一种网络接口的工作模式,允许网络设备(如网络接口卡)在接收到的网络数据包中捕获并处理不属于其自身的数据包。
通常情况下,网络设备(如路由器、交换机、网络接口卡等)只会处理发送给自己的数据包,而忽略其他目标地址的数据包。然而,在混杂模式下,设备会接收并处理通过网络传输的所有数据包,无论目标地址是否为自己。
虽然目前大多数的路由器都支持混杂模式,但是问题并没有因此而得到解决,因为不同的路由器可能对 macvlan 和 ipvlan 的兼容性不一样。

1.4、失联的原因到底是什么造成的?

我也不知道。
除了上面提到的两个因素,在我了解到的信息中,还有更多可能的因素造成了失联的问题。我估计有些读者在按照本文介绍的方法去实施后并不一定能完全解决问题,所以我在本文的最后一章做了相应的信息补充来给大到家参考。

2、解决办法

文章开头已经说了解决办法,其中第一种办法是将 macvlan 修改为 ipvlan,但并不一定能解决问题,甚至结果可能会更糟糕,比如改为 ipvlan 之后 Docker 和 unRAID 都连不上网了(也还是跟路由器有关,路由器设备不一定能跟 ipvlan 这种网络模式兼容)。
所以本文着重介绍第二种方法:单独拿出一个物理网口给到 Docker 去单独使用。
官方也给出了具体的实施方案:
那么这里作者就依据官方的指导来给大家详细介绍解决办法。

2.1、硬性条件:设备至少得有两个网口

前面说了,解决办法是单独拿出一个网口给到 Docker 去使用,如果你的设备只有一个网口,那么解决办法只能是尝试更改成 Ipvlan 网络类型或者使用其他 unRAID 版本。

2.2、释放网口

如果你的主板是双网口,那么你需要从“桥接其成员 br0”或者“绑定成员”中剔除另一个网口,也就是将另一个网口从绑定中释放出来。
如果绑定了多个成员,需要释放其中一个网口
如果绑定了多个成员,需要释放其中一个网口
如果你的主板只有一个网口,但是你有 PCIE 网卡,那么你需要保证不要将 PCIE 网卡的所有网口都绑定到 VFIO-PCI ,你需要将其中一个取消绑定。
例如作者板载网口只有一个,但是有一个四口的 PCIE 千兆网卡,此时就不能将所有网口都绑定到 VFIO-PCI :
同样的,你也需要保证不要让这个 PCIE 网口被绑定到桥接成员或者绑定成员中。
notion image
释放了网口之后,在网络设置中看起来应该像是这样的:
notion image

2.3、网口的网络设置

释放出网口之后,接下里在网络设置中对这一网口进行相关的设置。
notion image
如上图所示:
  1. 不需要启动绑定功能。
  1. 桥接也不需要启用。
  1. 网络协议选择 IPV4
  1. 不需要分配 IP 地址。
注意,在上面的设置中,如果你需要使用给容器分配 IPV6 地址,你需要开启 IPV6 的同时设置一个固定的 IPV4 地址。
notion image

2.4、为第二个接口设置自定义网络

notion image
  1. 选择 mcvlan 模式。
  1. 禁用“主机访问自定义网络”。
  1. 取消默认的 br0 的自定义网络。
  1. 开启第二个网口的自定义网络,并设置原先 br0 对应的网段、网关和 DHCP 池等。
最后应用设置。

2.5、让 Docker 使用自定义网络

notion image
  1. Docker 容器网络类型选择前面设置的设置的自定义网络(原先哪些 Docker 是使用的固定 IP 地址,就给那些 Docker 应用新的设置就行,原先使用 Bridge、Host 之类的不用改)。
  1. 可以手动分配一个固定的 IP 地址,或者留空自动分配也行。

3、其他补充

当你按照以上方式处理之后,那么失联问题可以得到解决(起码官方是这么说的)。但由于此问题比较复杂,每个人遇到问题表现出来的问题特征可能不一样,所以我在这里补充一些查到的相关信息作为记录,供大家参考。

3.1、网口桥接功能与 Macvlan 可能存在冲突

根据官方人员在这个帖子的解释,造成 MACVLAN CALL TRACES 问题可能是由于网卡在开启了桥接的同时(如下图),与 Macvlan 产生了冲突。
Fix Common Problem
Fix Common Problem
解决办法是关闭网口的桥接功能:
notion image

3.2、此问题与 unRAID 的版本有关

我了解到的信息中,不少人升级到 6.12 之后才会出现此问题,所以我建议读者们不着急着升级系统版本,可以稍微再等等,等到 unRAID 6.12.3 或者更高一点的版本出来之后再尝试升级。

3.3、Realteck 2.5G 网卡

我不确定是不是跟 Realtek 的 2.5G 网卡有关,毕竟 Realtek 的 驱动问题老生常谈了,所以为了避免这种情况,如果你目前用的是 Realtek 的 2.5G 网卡,可以不着急升级 6.12 版本,目前可用的比较稳定的是 6.11.5,建议等 6.12 再多更新两个版本之后再升级。

2023-08-27:WireGuard 无法访问固定 IP 地址 Docker 的案例

此问题也可以通过本文介绍的方法解决。

2023-09-01:因 IPV6 导致的失联问题( 500 Internal Server Error )

1、可能是由于 IPV6 导致的

经查找相关的资料,目前有足够多的证据可以证明对于某些失联的情况,可以通过关闭 IPV6 或者给 IPV6 指定一个固定地址可以解决此问题。
💡
注意: 需要是说明的是,这里提到的方法不一定就能解决你遇到的失联问题,因为有些人也表示即使没有开启 IPV6 也一样出现失联问题(参考案例)。所以如果没有特别的需求,博主建议遇到此类问题的朋友先暂时使用旧版本(例如 6.11.5 ),等 Unraid 更新。
通过关闭 IPV6 解决此问题的案例
通过设置一个固定 IPV6 地址来解决此问题的案例
https://forums.unraid.net/bug-reports/stable-releases/612-unraid-webui-stop-responding-then-nginx-crash-r2451/?do=findComment&comment=25608
但也有人表示可以通过设置一个固定的 IPV6 DNS 来解决问题,因为这个网友发现设置了一个固定的 IPV6 DNS 之后(IPV6 地址动态获取)没有出现失联问题:
此问题会导致 Unraid 上的 Nginx 进程出现错误,体现在 Unraid 的 Web 界面出现 500 Internal Server Error 报错:
notion image
或者出现网页页面无反应的情况。
日志报错信息(博主在查找资料的时候也发现,CloudFlare Tunnel 的 Docker 应用也会导致此类问题,参考:6.12 WEBUI INACCESSIBLE, AND /VAR/LOG FULL
沟通记录
notion image
notion image
notion image
notion image

2、过程记录

根据 [6.12] UNRAID WEBUI STOP RESPONDING THEN NGINX CRASH 帖子中同样出现此问题的网友反馈,可以通过手动结束 Nginx 进程来临时解决问题:
  1. 查找 Nginx 进程号
    1. 输出结果类似如下:
  1. 结束 Nginx 进程:
    1. 结束之后重新启动 Nginx 进程
      对于重启和关闭 Unraid 的 Nginx 进程,也有人写了脚本来实现自动重启 Nginx 进程:
      此问题可能与 Unraid 内核有关,所以如果读者遇到此问题,建议先暂时不去使用 IPV6,等 Unraid 发布先新版本后在尝试去更新(截至作者写下此内容时 Unraid 刚于 8月31日发布了 6.12.4 版本)。
      如果日常使用离不开 IPV6,建议可以尝试利用第二个网口去使用。不过需要注意的是,第二个网口开启 IPV6 需要一同开启 IPV4 ,并且还需要给第二个网口分配一个 IPV4 的地址,这样在 Docker 中才能正常分配 IPV6 地址给到容器。具体为什么需要这么来做,你可以参考下面的说明。
      说明:为什么需要同时给到 IPV4 和 IPV6
      根据以上说明,由于在 6.12 版本中对安全性做了提升,系统的服务需要绑定到有效的 V4 和 V6 地址(但在先前的版本中并没有这个要求)。
      另外需要补充的是,第二个网口的 IPV4 地址最好不要跟第一个网口的 IPV4 地址同一个网段。也就是说假如你的 Unraid IPV4 地址是 192.168.1.10 ,那么第二个网口就不要使用同一网段的 IPV4 比如说 192.168.1.20
      你可以添加一个新网段下的 IP 地址给到第二个网口,例如 192.168.2.10 ,然后为了能让第二个网段能够正常联网,你需要在路由器添加第二个网段,例如:
      notion image
      如果你使用的是 Openwrt,你可以参考这里的方法去添加第二个网段:

      3、补充第二个因 IPV6 而出现”失联“问题的案例

      案例源自 unRAID 官方中文论坛的一个求助帖子:
      notion image
      解决办法也是一样的,可以尝试关闭 IPV6 或者尝试重启 Nginx 服务,具体细节请看前文。

      评论