Page MenuHomeVyOS Platform

vyos-hostsd overriding dns forward configuration
Open, Requires assessmentPublicBUG

Description

Hi all,

As described on the forum I noticed my DNS forwarding configuration went missing after a certain period. After debugging I found out the configuration change appeared at the same time vyos-hostsd was performing actions as result of a dhclient lease renewal. I've tested this on a clean installation of VyOS 1.2.5 with the configuration mentioned below and was able to reproduce this.

When I reboot the router the configuration is applied as it should. After a while the DHCP client will renew the DHCP release and triggers vyos-hostsd which overwrites the PowerDNS configuration. This overwrite causes the "dns forwarding domain" entries to be removed from "forward-zones-recurse" in /etc/powerdns/recursor.conf (the service dns forwarding name-server entries will persist). In addition I noticed that the "search" and "domain" entries in /etc/resolv.conf are also overwritten by the DHCP proposal (while "search" and "domain" have been configured statically by the system domain-name configuration setting).

I would expect that dynamic services (like DHCP) will never override (or be added to) static configurations that is defined explicitly. So in case I configure a static DNS server or domain-name, I expect only that entry to be configured. When a DHCP offer comes in I'd expect only the IP to be set, but DNS settings to be ignored.

Configuration to reproduce:

set interfaces ethernet eth0 address 'dhcp'
set interfaces ethernet eth0 description 'WAN'
set interfaces ethernet eth0 duplex 'auto'
set interfaces ethernet eth0 smp-affinity 'auto'
set interfaces ethernet eth0 speed 'auto'
set service dns forwarding allow-from '10.0.0.0/8'
set service dns forwarding domain mydomain.net server '10.0.0.100'
set service dns forwarding listen-address '0.0.0.0'
set service dns forwarding name-server '80.80.80.80'
set service dns forwarding name-server '80.80.81.81'
set system domain-name 'mydomain.net'
set system host-name 'vyos'

PowerDNS configuration before DHCP renewal:

vyos@vyos:~$ cat /etc/powerdns/recursor.conf 

### Autogenerated by dns_forwarding.py ###

# Non-configurable defaults
daemon=yes
threads=1
allow-from=10.0.0.0/8
log-common-errors=yes
non-local-bind=yes
query-local-address=0.0.0.0
query-local-address6=::

# cache-size
max-cache-entries=10000

# negative TTL for NXDOMAIN
max-negative-ttl=3600

# ignore-hosts-file
export-etc-hosts=yes

# listen-on
local-address=0.0.0.0

# dnssec
dnssec=process-no-validate

# forward-zones / recursion
#
# statement is only inserted if either one forwarding domain or nameserver is configured
# if nothing is given at all, powerdns will act as a real recursor and resolve all requests by its own
#
forward-zones-recurse=mydomain.net=10.0.0.100, .=80.80.80.80;80.80.81.81

PowerDNS configuration after DHCP renewal (see missing domain.net entry in forward-zones-recurse):

vyos@vyos:~$ cat /etc/powerdns/recursor.conf 

### Autogenerated by dns_forwarding.py ###

# Non-configurable defaults
daemon=yes
threads=1
allow-from=10.0.0.0/8
log-common-errors=yes
non-local-bind=yes
query-local-address=0.0.0.0
query-local-address6=::

# cache-size
max-cache-entries=10000

# negative TTL for NXDOMAIN
max-negative-ttl=3600

# ignore-hosts-file
export-etc-hosts=yes

# listen-on
local-address=0.0.0.0

# dnssec
dnssec=process-no-validate

# forward-zones / recursion
#
# statement is only inserted if either one forwarding domain or nameserver is configured
# if nothing is given at all, powerdns will act as a real recursor and resolve all requests by its own
#
forward-zones-recurse=.=80.80.80.80;80.80.81.81

Resolv.conf before DHCP renewal:

vyos@vyos:~$ cat /etc/resolv.conf 

### Autogenerated by VyOS ###
### Do not edit, your changes will get overwritten ###

nameserver 84.116.46.22
nameserver 84.116.46.23

domain mydomain.net
search mydomain.net

Resolv.conf after DHCP renewal:

vyos@vyos:~$ cat /etc/resolv.conf 

### Autogenerated by VyOS ###
### Do not edit, your changes will get overwritten ###

nameserver 84.116.46.22
nameserver 84.116.46.23

search home

Logs of behavior:

Jun 30 10:17:44 vyos dhclient: DHCPREQUEST on eth0 to 192.168.178.1 port 67
Jun 30 10:17:44 vyos dhclient: DHCPACK from 192.168.178.1
Jun 30 10:17:44 vyos vyos-hostsd[650]: Received a configuration change request
Jun 30 10:17:44 vyos vyos-hostsd[650]: Request data: {"type": "host_name", "op": "set", "data": {"domain_name": null, "search_domains": ["home"], "host_name": null}}
Jun 30 10:17:44 vyos vyos-hostsd[650]: Writing /etc/resolv.conf
Jun 30 10:17:44 vyos vyos-hostsd[650]: Writing /etc/hosts
Jun 30 10:17:44 vyos vyos-hostsd[650]: Saving state to /var/lib/vyos/hostsd.state
Jun 30 10:17:44 vyos vyos-hostsd[650]: Sent response: {'data': None}
Jun 30 10:17:44 vyos vyos-hostsd[650]: Received a configuration change request
Jun 30 10:17:44 vyos vyos-hostsd[650]: Request data: {"type": "name_servers", "tag": "dhcp-eth0", "op": "delete"}
Jun 30 10:17:44 vyos vyos-hostsd[650]: Writing /etc/resolv.conf
Jun 30 10:17:44 vyos vyos-hostsd[650]: Writing /etc/hosts
Jun 30 10:17:44 vyos vyos-hostsd[650]: Saving state to /var/lib/vyos/hostsd.state
Jun 30 10:17:44 vyos vyos-hostsd[650]: Sent response: {'data': None}
Jun 30 10:17:44 vyos vyos-hostsd[650]: Received a configuration change request
Jun 30 10:17:44 vyos vyos-hostsd[650]: Request data: {"data": ["84.116.46.23", "84.116.46.22"], "type": "name_servers", "tag": "dhcp-eth0", "op": "add"}
Jun 30 10:17:44 vyos vyos-hostsd[650]: Writing /etc/resolv.conf
Jun 30 10:17:44 vyos vyos-hostsd[650]: Writing /etc/hosts
Jun 30 10:17:44 vyos vyos-hostsd[650]: Saving state to /var/lib/vyos/hostsd.state
Jun 30 10:17:44 vyos vyos-hostsd[650]: Sent response: {'data': None}
Jun 30 10:17:45 vyos systemd[1]: Stopping PowerDNS Recursor...
Jun 30 10:17:45 vyos systemd[1]: Starting PowerDNS Recursor...
Jun 30 10:17:45 vyos pdns_recursor[3338]: PowerDNS Recursor 4.1.15 (C) 2001-2018 PowerDNS.COM BV
Jun 30 10:17:45 vyos pdns_recursor[3338]: Using 64-bits mode. Built using gcc 4.9.2 on Dec  3 2019 13:02:24 by root@613ec8350b02.
Jun 30 10:17:45 vyos pdns_recursor[3338]: PowerDNS comes with ABSOLUTELY NO WARRANTY. This is free software, and you are welcome to redistribute it according to the terms of the GPL version 2.
Jun 30 10:17:45 vyos pdns_recursor[3338]: Reading random entropy from '/dev/urandom'
Jun 30 10:17:45 vyos pdns_recursor[3338]: Enabling IPv6 transport for outgoing queries
Jun 30 10:17:45 vyos pdns_recursor[3338]: Only allowing queries from: 10.0.0.0/8
Jun 30 10:17:45 vyos pdns_recursor[3338]: Will not send queries to: 127.0.0.0/8, 10.0.0.0/8, 100.64.0.0/10, 169.254.0.0/16, 192.168.0.0/16, 172.16.0.0/12, ::1/128, fc00::/7, fe80::/10, 0.0.0.0/8, 192.0.0.0/24, 192.0.2.0/24, 198.51.100.0/24, 203.0.113.0/24, 240.0.0.0/4, ::/96, ::ffff:0:0/96, 100::/64, 2001:db8::/32, 0.0.0.0, ::
Jun 30 10:17:45 vyos pdns_recursor[3338]: Redirecting queries for zone '.' with recursion to: 80.80.80.80:53, 80.80.81.81:53
Jun 30 10:17:45 vyos pdns_recursor[3338]: Inserting forward zone 'localhost' based on hosts file
Jun 30 10:17:45 vyos pdns_recursor[3338]: Inserting reverse zone '1.0.0.127.in-addr.arpa' based on hosts file
Jun 30 10:17:45 vyos pdns_recursor[3338]: Inserting forward zone 'vyos' based on hosts file
Jun 30 10:17:45 vyos pdns_recursor[3338]: Inserting reverse zone '1.1.0.127.in-addr.arpa' based on hosts file
Jun 30 10:17:45 vyos pdns_recursor[3338]: Inserting rfc 1918 private space zones
Jun 30 10:17:45 vyos pdns_recursor[3338]: Listening for UDP queries on 0.0.0.0:53
Jun 30 10:17:45 vyos pdns_recursor[3338]: Enabled TCP data-ready filter for (slight) DoS protection
Jun 30 10:17:45 vyos pdns_recursor[3338]: Listening for TCP queries on 0.0.0.0:53
Jun 30 10:17:45 vyos pdns_recursor[3338]: Operating unthreaded
Jun 30 10:17:45 vyos systemd[1]: Started PowerDNS Recursor.
Jun 30 10:17:45 vyos pdns_recursor[3338]: Done priming cache with root hints
Jun 30 10:17:45 vyos pdns_recursor[3338]: Done priming cache with root hints
Jun 30 10:17:45 vyos pdns_recursor[3338]: Enabled 'epoll' multiplexer
Jun 30 10:17:45 vyos dhclient: bound to 192.168.178.169 -- renewal in 1675 seconds.
Jun 30 10:17:49 vyos systemd[1]: serial-getty@ttyS0.service holdoff time over, scheduling restart.
Jun 30 10:17:49 vyos systemd[1]: Stopping Serial Getty on ttyS0...
Jun 30 10:17:49 vyos systemd[1]: Starting Serial Getty on ttyS0...
Jun 30 10:17:49 vyos systemd[1]: Started Serial Getty on ttyS0.
Jun 30 10:17:49 vyos agetty[3349]: /dev/ttyS0: not a tty
Jun 30 10:17:51 vyos pdns_recursor[3338]: PowerDNS Security Update Mandatory: Upgrade now, see https://doc.powerdns.com/recursor/security-advisories/powerdns-advisory-2020-01.html https://doc.powerdns.com/recursor/security-advisories/powerdns-advisory-2020-02.html https://doc.powerdns.com/recursor/security-advisories/powerdns-adv" "isory-2020-03.html

Details

Difficulty level
Normal (likely a few hours)
Version
1.2.5
Why the issue appeared?
Will be filled on close
Is it a breaking change?
Behavior change

Event Timeline

rednax created this task.Tue, Jun 30, 10:29 AM
jjakob added a subscriber: jjakob.Tue, Jun 30, 1:57 PM

This is already fixed in 1.3

Ok, nice. And how about 1.2? Is it possible to fix this with the 1.2.6 release?

Possible by backporting https://github.com/vyos/vyos-1x/pull/452 and https://github.com/vyos/vyatta-cfg-system/pull/125 though I think some code using Config would need to be modified - add .exists calls before each .return_value(s) - 1.3's vyos.config doesn't require them, 1.2's I think does.

pasik added a subscriber: pasik.Sat, Jul 4, 8:34 AM