Avahi

出自 ArchWiki
(重定向自 MDNS

出自 Wikipedia:Avahi (软件)

Avahi 是一个自由的 零配置网络 (zeroconf) 实现,包括用于组播 DNS/DNS-SD 服务发现的系统。它允许程序发布和发现本地网络上运行的服务和主机,而无需特定配置。例如,您可以插入网络并立即找到要打印的打印机、要查看的文件以及要交谈的人。它在 GNU Lesser General Public License (LGPL) 许可下发布。

安装

安装 avahi 软件包并启用 avahi-daemon.service 或使用 套接字激活

注意: systemd-resolved 具有内置的 mDNS 服务,请确保禁用 systemd-resolved 的组播 DNS 解析器/响应器(请参阅 resolved.conf(5))或在 使用 Avahi 之前完全禁用 systemd-resolved.service

使用 Avahi

主机名解析

Avahi 使用 "hostname.local" 命名方案提供本地主机名解析。要启用它,请安装 nss-mdns 软件包并启动/启用 avahi-daemon.service

然后,编辑文件 /etc/nsswitch.conf 并更改 hosts 行,使其在 resolvedns 之前包含 mdns_minimal [NOTFOUND=return]

hosts: mymachines mdns_minimal [NOTFOUND=return] resolve [!UNAVAIL=return] files myhostname dns
注意
  • 如果您在解析 .local 主机时遇到速度减慢的情况(或者您不想使用 IPv6),请尝试使用 mdns4_minimalmdns4 分别代替 mdns_minimalmdns
  • 上面的行使 nss-mdns 成为 .local 域的权威,除非您的单播 DNS 服务器响应顶级 local 名称的 SOA 查询,或者如果请求具有两个以上的标签。请参阅 nss-mdns 激活说明

为自定义 TLD 配置 mDNS

mdns_minimal 模块仅处理对 .local TLD 的查询。请注意 [NOTFOUND=return],它指定如果 mdns_minimal 找不到 *.local,它将不会继续在 dnsmyhostname 等中搜索它。

如果您希望 Avahi 支持其他 TLD,您应该

  • mdns_minimal [NOTFOUND=return] 替换为完整的 mdns 模块。还有仅 IPv4 和仅 IPv6 模块 mdns[46](_minimal)
  • 使用您选择的 domain-name 自定义 /etc/avahi/avahi-daemon.conf
  • /etc/mdns.allow 中白名单 Avahi 自定义 TLD

工具

Avahi 包含几个实用程序,可帮助您发现网络上运行的服务。例如,运行此命令以发现网络中的服务

$ avahi-browse --all --ignore-local --resolve --terminate

如果此命令没有任何结果,则可能是由于防火墙阻止了 mDNS 流量。

如果您只想执行 mDNS 查询以将 .local 主机名解析为 IP 地址(类似于 dignslookup),请使用

$ avahi-resolve-host-name some-host-name.local

请注意,getent hosts 命令可以执行 DNS 和 mDNS 查找。

Avahi Zeroconf 浏览器 avahi-discover 显示您网络上的各种服务。请注意,它需要 Avahi 的可选依赖项 gtk3python-dbuspython-gobject。您也可以分别使用 bsshbvnc 浏览 SSH 和 VNC 服务器。

防火墙

如果您正在使用防火墙,请务必打开 UDP 端口 5353

链路本地 (Bonjour/Zeroconf) 聊天

Avahi 可用于 Linux 下的 Bonjour 协议支持。查看 Wikipedia:即时通讯客户端比较应用程序列表/互联网#即时通讯客户端,获取支持 Bonjour 协议的客户端列表。

获取 IPv4LL IP 地址

本文或章节候选合并至 dhcpcd

注意:应合并到主页面(在 Talk:Avahi 中讨论)

dhcpcd 客户端可以在通过 DHCP 获取地址失败时尝试获取 IPv4LL 地址。默认情况下,此选项处于禁用状态。要启用它,请注释掉 noipv4ll 字符串

/etc/dhcpcd.conf
...
#noipv4ll
...

或者,运行 avahi-autoipd

# avahi-autoipd -D

添加服务

Avahi 会通告在 /etc/avahi/services 中找到 *.service 文件的服务。此目录中的文件必须可由 avahi 用户/组读取。

如果您要通告没有 *.service 文件的服务,则创建自己的文件非常容易。例如,假设您要通告一个每日名言 (QOTD) 服务,该服务根据 RFC:865 在 TCP 端口 17 上运行,并且您正在您的机器上运行该服务

首先要做的是确定 <type>avahi.service(5) 指出类型应为“此服务的 DNS-SD 服务类型。例如 '_http._tcp'”。由于 DNS-SD 注册表已于 2010 年合并到 IANA 注册表,因此我们在 IANA 注册表/etc/services 文件中查找服务名称。那里显示的服务名称是 qotd。由于我们在 tcp 上运行 QOTD,因此我们现在知道该服务是 _qotd._tcp,并且端口(根据 IANA 和 RFC 865)是 17

因此,我们的服务文件是

qotd.service
<?xml version="1.0" standalone='no'?><!--*-nxml-*-->
<!DOCTYPE service-group SYSTEM "avahi-service.dtd">

<service-group>

  <name replace-wildcards="yes">%h</name>

  <service>
    <type>_qotd._tcp</type>
    <port>17</port>
  </service>

</service-group>

对于更复杂的场景,例如通告在不同服务器上运行的服务、DNS 子类型等,请查阅 avahi.service(5)

请记住,Avahi 不支持 <type> 字段中的任意字符串,您只能设置 Avahi 服务数据库中已知的值。如果您想注册一些自定义内容,您可能需要编辑数据库定义,构建更新的版本并将其分发给您的主机。

SSH

Avahi 附带一个示例服务文件来通告 SSH 服务器。要启用它

# cp /usr/share/doc/avahi/ssh.service /etc/avahi/services/

文件共享

NFS

如果您设置了 NFS 共享,则可以使用 Avahi 在启用 Zeroconf 的浏览器(例如 KDE 上的 Konqueror 和 macOS 上的 Finder)或文件管理器(例如 GNOME/文件)中自动挂载它们。

/etc/avahi/services 中创建一个包含以下内容的 .service 文件

/etc/avahi/services/nfs_Zephyrus_Music.service
<?xml version="1.0" standalone='no'?>
<!DOCTYPE service-group SYSTEM "avahi-service.dtd">
<service-group>
  <name replace-wildcards="yes">NFS Music Share on %h</name>
  <service>
    <type>_nfs._tcp</type>
    <port>2049</port>
    <txt-record>path=/data/shared/Music</txt-record>
  </service>
</service-group>

如果您的 /etc/exports 中有 insecure 选项,则端口是正确的;否则,需要更改端口(请注意,macOS 客户端需要 insecure)。路径是您的导出路径或其子目录。由于某种原因,自动挂载功能已从 Leopard 中删除,但是脚本可用。这是基于此帖子

Samba

在服务器和客户端上都运行 Avahi 守护程序的情况下,客户端上的文件管理器应自动找到服务器。

Vsftpd

您还可以自动发现常规 FTP 服务器,例如 vsftpd。安装 vsftpd 软件包并根据您自己的个人喜好更改 vsftpd 的设置(请参阅 ubuntuforums.org 上的此线程vsftpd.conf(5))。

/etc/avahi/services 中创建一个包含以下内容的 .service 文件

/etc/avahi/services/ftp.service
<?xml version="1.0" standalone='no'?>
<!DOCTYPE service-group SYSTEM "avahi-service.dtd">
<service-group>
  <name>FTP file sharing</name>
  <service>
    <type>_ftp._tcp</type>
    <port>21</port>
  </service>
</service-group>

FTP 服务器现在应该由 Avahi 通告。您现在应该可以从网络中另一台计算机上的文件管理器中找到 FTP 服务器。您可能需要在客户端上启用#主机名解析

故障排除

主机名更改时附加递增的数字

这是一个已知错误,是由主机名竞争条件引起的。一种可能的解决方法是禁用 IPv6 以尝试防止竞争条件。如果存在多个接口,请使用 allow-interfaces 将 Avahi 限制为单个接口。另一种可能的解决方法是禁用缓存,以防止 Avahi 完全检查主机名冲突,但这会阻止 Avahi 执行查找。

systemd-resolved 阻止 nss-mdns 工作

nss-mdns 仅当 /etc/resolv.conf 中列出的 DNS 服务器向“local”域的 SOA 查询返回 NXDOMAIN 时才有效。[1]

首先检查您配置的 DNS 服务器是否使用 NXDOMAIN 回答“local”域的 SOA 查询。例如

$ host -t SOA local

如果 DNS 服务器使用 NXDOMAIN 响应,则您无需执行以下步骤。即使使用 systemd-resolved,Avahi 也应该能够正常找到网络中的资源。

在旧版本的 systemd-resolved 中,resolved.conf(5) 中的全局设置 MulticastDNS=no 会导致“local”域的 Avahi 不兼容的响应代码。这导致 Avahi 无法正确找到资源(打印机)。有关参考,请参阅 systemd 问题 21659

但是,如果上面的 DNS 查询未能为“local”域返回 NXDOMAIN,您可以改用完整的 mdns NSS 模块,并创建 /etc/mdns.allow 以仅允许“local”域。例如

/etc/nsswitch.conf
hosts: mymachines mdns [NOTFOUND=return] resolve [!UNAVAIL=return] files myhostname dns
/etc/mdns.allow
.local.
.local
注意: 上述解决方案将破坏网络实用程序(例如 mtrtraceroute)中的反向查找。这些应用程序将尝试通过 Avahi 执行反向查找并超时,而不是回退到其他 DNS 服务。这似乎类似于 Debian 问题 433943,其中建议不幸的是使用 mdns_minimal 而不是 mdns

avahi 套接字上的 ECONNREFUSED(连接被拒绝)

如果您的 Avahi 实例启动并正常运行,但 nss 似乎没有将请求转发到 mdns,则可能是由于套接字 /run/avahi-daemon/socket 卡住引起的。例如,可以使用 strace 验证这一点。在这种情况下,您可能必须重启 avahi-daemon.serviceavahi-daemon.socket 才能使其正常工作。

KDE Connect 内置 mDNS 冲突

如果您使用 kdeconnect,则 kdeconnect 也运行其 mdns 服务器,因此与 avahi 存在 mDNS 冲突。这可能会导致主机名冲突,例如在网络重启后将您的主机重命名为 myhostname-2

要纠正此问题,请删除 kdeconnect,或构建一个没有 mDNS 支持的版本,例如 kdeconnect-no-mdnsAUR 中的版本。

请参阅 kde 错误 487719

参见