Skip to content

Commit 05e6317

Browse files
authored
xapi/nm: Send non-empty dns to networkd when using IPv6 autoconf (#6586)
Because Autoconf is not DHCP, networkd uses the dns value to write to resolv.conf. This is done on ocaml/networkd/bin/network_server.ml line 745 This allows to have non-empty resolv.conf when using IPv6 autoconf. This mismatch was caused byt technical debt that cause this check to be duplicated, the second removes it so xapi decides the instances where these values are written and networkd follows that decision. I've tested new isntallations using IPv4 and couldn't see any regression, two users have tested the patch and now the DNS entries don't get overriden when using IPv6 in Autoconf mode: xcp-ng/xcp#641 (comment) I'd like Rob to review this approach in any case
2 parents 1fbdaae + bdbd975 commit 05e6317

File tree

5 files changed

+43
-41
lines changed

5 files changed

+43
-41
lines changed

ocaml/networkd/bin/network_server.ml

Lines changed: 6 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -554,7 +554,8 @@ module Interface = struct
554554
let set_dns _ dbg ~name ~nameservers ~domains =
555555
Debug.with_thread_associated dbg
556556
(fun () ->
557-
update_config name {(get_config name) with dns= (nameservers, domains)} ;
557+
update_config name
558+
{(get_config name) with dns= Some (nameservers, domains)} ;
558559
debug "Configuring DNS for %s: nameservers: [%s]; domains: [%s]" name
559560
(String.concat ", " (List.map Unix.string_of_inet_addr nameservers))
560561
(String.concat ", " domains) ;
@@ -727,7 +728,7 @@ module Interface = struct
727728
; ipv6_conf
728729
; ipv6_gateway
729730
; ipv4_routes
730-
; dns= nameservers, domains
731+
; dns
731732
; mtu
732733
; ethtool_settings
733734
; ethtool_offload
@@ -736,15 +737,10 @@ module Interface = struct
736737
) ) ->
737738
update_config name c ;
738739
exec (fun () ->
739-
(* We only apply the DNS settings when not in a DHCP mode
740-
to avoid conflicts. The `dns` field
741-
should really be an option type so that we don't have to
742-
derive the intention of the caller by looking at other
743-
fields. *)
744-
match (ipv4_conf, ipv6_conf) with
745-
| Static4 _, _ | _, Static6 _ | _, Autoconf6 ->
740+
match dns with
741+
| Some (nameservers, domains) ->
746742
set_dns () dbg ~name ~nameservers ~domains
747-
| _ ->
743+
| None ->
748744
()
749745
) ;
750746
exec (fun () -> set_ipv4_conf dbg name ipv4_conf) ;

ocaml/networkd/bin_db/networkd_db.ml

Lines changed: 17 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -74,20 +74,25 @@ let _ =
7474
[("gateway", Unix.string_of_inet_addr addr)]
7575
in
7676
let dns =
77-
let dns' =
78-
List.map Unix.string_of_inet_addr (fst interface_config.dns)
79-
in
80-
if dns' = [] then
81-
[]
82-
else
83-
[("dns", String.concat "," dns')]
77+
interface_config.dns
78+
|> Option.map fst
79+
|> Option.map (List.map Unix.string_of_inet_addr)
80+
|> Option.fold ~none:[] ~some:(function
81+
| [] ->
82+
[]
83+
| dns' ->
84+
[("dns", String.concat "," dns')]
85+
)
8486
in
8587
let domains =
86-
let domains' = snd interface_config.dns in
87-
if domains' = [] then
88-
[]
89-
else
90-
[("domain", String.concat "," domains')]
88+
interface_config.dns
89+
|> Option.map snd
90+
|> Option.fold ~none:[] ~some:(function
91+
| [] ->
92+
[]
93+
| domains' ->
94+
[("domain", String.concat "," domains')]
95+
)
9196
in
9297
mode @ addrs @ gateway @ dns @ domains
9398
| None4 ->

ocaml/networkd/lib/network_config.ml

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,6 @@ let bridge_naming_convention (device : string) =
3737
let get_list_from ~sep ~key args =
3838
List.assoc_opt key args
3939
|> Option.map (fun v -> Astring.String.cuts ~empty:false ~sep v)
40-
|> Option.value ~default:[]
4140

4241
let parse_ipv4_config args = function
4342
| Some "static" ->
@@ -73,11 +72,13 @@ let parse_ipv6_config args = function
7372
(None6, None)
7473

7574
let parse_dns_config args =
76-
let nameservers =
77-
get_list_from ~sep:"," ~key:"DNS" args |> List.map Unix.inet_addr_of_string
75+
let ( let* ) = Option.bind in
76+
let* nameservers =
77+
get_list_from ~sep:"," ~key:"DNS" args
78+
|> Option.map (List.map Unix.inet_addr_of_string)
7879
in
79-
let domains = get_list_from ~sep:" " ~key:"DOMAIN" args in
80-
(nameservers, domains)
80+
let* domains = get_list_from ~sep:" " ~key:"DOMAIN" args in
81+
Some (nameservers, domains)
8182

8283
let read_management_conf () =
8384
try
@@ -103,15 +104,15 @@ let read_management_conf () =
103104
let device =
104105
(* Take 1st member of bond *)
105106
match (bond_mode, bond_members) with
106-
| None, _ | _, [] -> (
107+
| None, _ | _, (None | Some []) -> (
107108
match List.assoc_opt "LABEL" args with
108109
| Some x ->
109110
x
110111
| None ->
111112
error "%s: missing LABEL in %s" __FUNCTION__ management_conf ;
112113
raise Read_error
113114
)
114-
| _, hd :: _ ->
115+
| _, Some (hd :: _) ->
115116
hd
116117
in
117118
Inventory.reread_inventory () ;

ocaml/xapi-idl/network/network_interface.ml

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -158,7 +158,10 @@ type interface_config_t = {
158158
; ipv6_conf: ipv6 [@default None6]
159159
; ipv6_gateway: Unix.inet_addr option [@default None]
160160
; ipv4_routes: ipv4_route_t list [@default []]
161-
; dns: Unix.inet_addr list * string list [@default [], []]
161+
; dns: (Unix.inet_addr list * string list) option [@default None]
162+
(** the list
163+
of nameservers and domains to persist in /etc/resolv.conf. Must be None when
164+
using a DHCP mode *)
162165
; mtu: int [@default 1500]
163166
; ethtool_settings: (string * string) list [@default []]
164167
; ethtool_offload: (string * string) list [@default [("lro", "off")]]
@@ -200,7 +203,7 @@ let default_interface =
200203
; ipv6_conf= None6
201204
; ipv6_gateway= None
202205
; ipv4_routes= []
203-
; dns= ([], [])
206+
; dns= None
204207
; mtu= 1500
205208
; ethtool_settings= []
206209
; ethtool_offload= [("lro", "off")]

ocaml/xapi/nm.ml

Lines changed: 7 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -634,28 +634,25 @@ let bring_pif_up ~__context ?(management_interface = false) (pif : API.ref_PIF)
634634
rc.API.pIF_ip_configuration_mode = `Static
635635
| `IPv6 ->
636636
rc.API.pIF_ipv6_configuration_mode = `Static
637+
|| rc.API.pIF_ipv6_configuration_mode = `Autoconf
637638
in
638639
let dns =
639640
match (static, rc.API.pIF_DNS) with
640641
| false, _ | true, "" ->
641-
([], [])
642+
None
642643
| true, pif_dns ->
643644
let nameservers =
644645
List.map Unix.inet_addr_of_string
645-
(String.split ',' pif_dns)
646+
(String.split_on_char ',' pif_dns)
646647
in
647648
let domains =
648649
match List.assoc_opt "domain" rc.API.pIF_other_config with
649-
| None ->
650+
| None | Some "" ->
650651
[]
651-
| Some domains -> (
652-
try String.split ',' domains
653-
with _ ->
654-
warn "Invalid DNS search domains: %s" domains ;
655-
[]
656-
)
652+
| Some domains ->
653+
String.split_on_char ',' domains
657654
in
658-
(nameservers, domains)
655+
Some (nameservers, domains)
659656
in
660657
let mtu = determine_mtu rc net_rc in
661658
let ethtool_settings, ethtool_offload =

0 commit comments

Comments
 (0)