如何使用 systemd-resolved 排除 DNS 故障?

如何使用 systemd-resolved 排除 DNS 故障?

您将如何查找 所使用的 DNS 服务器systemd-resolved以进行故障排除?

一般来说,我可以使用dig和测试 中所示的 DNS 服务器/etc/resolv.conf。 (或 Windows - ipconfig /all+ nslookup)。但是,当 resolv.conf 仅指向环回地址上的本地解析器守护程序时,该方法不起作用。 systemd-resolved下使用什么方法来显示它使用的DNS服务器?


unbound有我可以查看的配置文件。 dnsmasq也有,但我不确定是否可以在没有配置文件的情况下动态添加服务器。即使是 NetworkManager,现在也有nmcli,而且我看到您可以查询nmcli d show wlan0以显示接口的 DNS 配置。 )

答案1

对于故障排除也非常有帮助:

journalctl -u systemd-resolved -f

在那里你可以看到systemd-resolved真正在做什么。就我而言,它systemd-resolve --status根本没有联系所报告的 DNS 服务器。如果它做了类似的奇怪的事情,那么有时重新启动sudo systemctl restart systemd-resolved是一个好主意。

编辑:

为了获得更多信息,resolved你需要

[Service]
Environment=SYSTEMD_LOG_LEVEL=debug

进入override.conf通过systemd-resolved

sudo systemctl edit systemd-resolved

重启生效:

sudo systemctl restart systemd-resolved

编辑2:

不要忘记随后恢复此操作,正如@bmaupin 和@Aminovic 在评论中指出的那样。

sudo systemctl revert systemd-resolved
sudo systemctl restart systemd-resolved

答案2

使用resolvectl status(systemd-resolve --status当使用早于239)来展示你的全局和每个链接的 DNS 设置

答案3

文件resolv.conf

手册说:

解析器是 C 库中的一组例程,提供对 Internet 域名系统 (DNS) 的访问。解析器配置文件包含解析器例程第一次被进程调用时读取的信息。

如果该文件不存在,则仅查询本地机器上的名称服务器,并且搜索列表包含根据主机名确定的本地域名。

systemd-resolved

在 Ubuntu 20.04 上,systemd-resolved是包含在内的本地 DNS 服务器systemd它充当存根解析器,它应该自动/etc/resolv.conf使用正确的配置进行编辑。

在旧版本上,您可能需要使用以下内容手动对其进行符号链接:

$ sudo ln -sf /run/systemd/resolve/stub-resolv.conf /etc/resolv.conf

默认情况下,systemd-resolved配置本地 DNS 服务器侦听127.0.0.53端口53,您可以运行lsof -i @127.0.0.53:53来验证。确保您没有任何其他服务,例如dnsmasq监听相同的地址和端口。

请注意,这127.0.0.53是环回接口,但您可以让另一个 DNS 服务器在环回接口上另一个 IP 地址的端口 53 上侦听,例如127.0.0.1127.0.0.2

如果不起作用,请尝试以下操作:

$ sudo ln -sf /run/systemd/resolve/resolv.conf /etc/resolv.conf

此文件包含来自 DHCP 租约的 DNS 服务器,但请注意,您不会从存根解析器缓存功能中受益。

dnsmasqNetworkManager

dnsmasq轻量级缓存 DNS 服务器接受 DNS 查询,并从小型本地缓存中回答它们,或者将它们转发到真实的递归 DNS 服务器。

对于 Web 开发机器来说,拥有一个小小的 DNS 服务来测试本地网站是非常好的。

首先,验证NetworkManager管理您当前的界面(wlp0s20f3在我的例子中):

$ nmcli dev
$ nmcli dev set wlp0s20f3 managed yes

现在您可以启用NetworkManager内置dnsmasq解析器:

$ cat /etc/NetworkManager/NetworkManager.conf
[main]
dns=dnsmasq

NetworkManager您现在可以受益于沿的灵活性dnsmasq,其配置位于/etc/NetworkManager/dnsmasq.d

$ cat /etc/NetworkManager/dnsmasq.d/custom.conf
# Resolve all domains ending in .dev to 127.0.0.1
address=/.dev/127.0.0.1

不要忘记禁用系统范围的dnsmasq服务(如果存在)并应用您的更改:

$ sudo systemctl stop dnsmasq.service && sudo systemctl disable dnsmasq.service
$ sudo systemctl restart NetworkManager.service

如果由于某些原因您希望dnsmasq单独运行,则必须首先防止NetworkManager覆盖/etc/resolv.conf

$ cat /etc/NetworkManager/NetworkManager.conf
[main]
dns=none

现在您必须告诉dnsmasq从其他地方获取其上游服务器/etc/resolv.conf

$ cat /etc/dnsmasq.conf
listen-address=127.0.0.53
resolv-file=/run/NetworkManager/resolv.conf

该文件由 DHCP 租约生成NetworkManager,也包含 DNS 服务器。现在配置dnsmasq解决:

$ cat /etc/resolv.conf
# Use local dnsmasq resolver
nameserver 127.0.0.53

配置您自己的本地 DNS 设置:

$ cat /etc/dnsmasq.d/custom.conf
# Resolve all domains ending in .dev to 127.0.0.1
address=/.dev/127.0.0.1

应用您的新配置:

$ sudo systemctl stop systemd-resolved.service && sudo systemctl disable systemd-resolved.service
$ sudo systemctl restart dnsmasq.service

dnsmasqsystemd-networkd

不幸的是,它并不像使用 那样容易NetworkManager,这是因为它systemd-networkd没有公开从 DHCP 服务器获得的 DNS 名称服务器的文件,因为它是由 DHCP 服务器管理的systemd-resolved

如果您使用完全不推荐使用的软件包,情况也会如此ifupdown

打开mandhclient-script

$ man 8 dhclient-script

挂钩部分说:

当它启动时,客户端脚本首先定义一个 shell 函数 ,make_resolv_conf该函数稍后用于创建/etc/resolv.conf文件。要覆盖默认行为,请在 Enter 挂钩脚本中重新定义此函数。

dnsmasq因此,如果您仍然想一起使用,systemd-networkd则需要重新定义make_resolv_conf以创建resolv-filefor ,dnsmasq以便它可以从您的 DHCP 设置获取其上游服务器。

resolvconfpackage 围绕填充中涉及的不同守护进程提供了一个包装器接口/etc/resolv.conf,您可以使用它来配置make_resolv_conf行为。


如果您需要从路由器通告消息中的 RDNSS 获取 IPv6 上游服务器,也会发生同样的问题(请参阅邻居发现协议),因为这也是由 管理的systemd-resolved

尝试从以下命令ndisc6包裹:

$ rdisc6 wlp0s20f3

您应该会看到来自路由器的各种信息,包括 IPv6 地址前缀和 DNS 服务器。如果您没有看到任何内容,则您的路由器可能不支持它。

rdisc6程序在用户空间中实现了 ICMPv6 路由器发现,使用NETLINK_ROUTELinux 内核 2.6.24 中添加了 RDNSS 支持的套接字。如果你想支持旧版本,你别无选择,只能与 OSI 第 2 层的设备驱动程序交互,使用SOCK_RAW插座。

答案4

这里的答案都没有让我更接近工作systemd-resolved。解决所有问题的一种方法systemd-resolved是将其从方程中删除。

首先禁用它(以 root 身份):

service systemd-resolved stop
systemctl disable systemd-resolved

但这还不够。 Systemd 将重新启用它并在几分钟后重新启动它。因此,您必须通过systemd-resolved从服务器中完全删除来防止这种情况:

rm -f /lib/systemd/systemd-resolved

我从来没有因为这样做而遇到 systemd 其他部分的问题,但是 YMMV。您可以重命名它,而不是删除它。

最后,编辑/etc/resolv.conf并放入一些名称服务器:

nameserver 8.8.8.8
nameserver 8.8.4.4

相关内容