fputc('\n', f);
}
+ sd_dns_resolver *resolvers;
+ r = sd_dhcp_lease_get_dnr(lease, &resolvers);
+ if (r > 0) {
+ fputs("DNR=", f);
+ serialize_dnr(f, resolvers, r, NULL);
+ fputc('\n', f);
+ }
+
r = sd_dhcp_lease_get_ntp(lease, &addresses);
if (r > 0) {
fputs("NTP=", f);
*next_server = NULL,
*broadcast = NULL,
*dns = NULL,
+ *dnr = NULL,
*ntp = NULL,
*sip = NULL,
*pop3 = NULL,
"NEXT_SERVER", &next_server,
"BROADCAST", &broadcast,
"DNS", &dns,
+ "DNR", &dnr,
"NTP", &ntp,
"SIP", &sip,
"POP3", &pop3,
lease->servers[SD_DHCP_LEASE_DNS].size = r;
}
+ if (dnr) {
+ r = deserialize_dnr(&lease->dnr, dnr);
+ if (r < 0)
+ log_debug_errno(r, "Failed to deserialize DNR servers %s, ignoring: %m", dnr);
+ lease->n_dnr = r;
+ }
+
if (ntp) {
r = deserialize_in_addrs(&lease->servers[SD_DHCP_LEASE_NTP].addr, ntp);
if (r < 0)
return log_link_debug_errno(link, r, "DHCPv4 CLIENT: Failed to set request flag for SIP server: %m");
}
- if (network_dhcp_use_dnr(link->network)) {
+ if (link_get_use_dnr(link, NETWORK_CONFIG_SOURCE_DHCP4)) {
r = sd_dhcp_client_set_request_option(link->dhcp_client, SD_DHCP_OPTION_V4_DNR);
if (r < 0)
return log_link_debug_errno(link, r, "DHCPv4 CLIENT: Failed to set request flag for DNR: %m");
return true;
}
+bool link_get_use_dnr(Link *link, NetworkConfigSource proto) {
+ int n;
+
+ assert(link);
+
+ if (!link->network)
+ return false;
+
+ switch (proto) {
+ case NETWORK_CONFIG_SOURCE_DHCP4:
+ n = link->network->dhcp_use_dnr;
+ break;
+ default:
+ assert_not_reached();
+ }
+
+ /* If set explicitly, use that */
+ if (n >= 0)
+ return n;
+
+ /* Otherwise, default to the same as the UseDNS setting. After all,
+ * this is just another way for the server to tell us about DNS configuration. */
+ return link_get_use_dns(link, proto);
+}
+
int config_parse_domains(
const char *unit,
const char *filename,
}
}
+ if (link->dhcp_lease && link_get_use_dnr(link, NETWORK_CONFIG_SOURCE_DHCP4)) {
+ sd_dns_resolver *resolvers;
+
+ r = sd_dhcp_lease_get_dnr(link->dhcp_lease, &resolvers);
+ if (r >= 0) {
+ struct in_addr_full **dot_servers;
+ size_t n = 0;
+ CLEANUP_ARRAY(dot_servers, n, in_addr_full_array_free);
+
+ r = dns_resolvers_to_dot_addrs(resolvers, r, &dot_servers, &n);
+ if (r < 0)
+ return r;
+ r = ordered_set_put_dns_servers(s, link->ifindex, dot_servers, n);
+ if (r < 0)
+ return r;
+ }
+ }
+
if (link->dhcp6_lease && link_get_use_dns(link, NETWORK_CONFIG_SOURCE_DHCP6)) {
const struct in6_addr *addresses;
fputc('\n', f);
}
+static void serialize_resolvers(
+ FILE *f,
+ const char *lvalue,
+ bool *space,
+ sd_dhcp_lease *lease,
+ bool conditional) {
+
+ bool _space = false;
+ if (!space)
+ space = &_space;
+
+ if (lvalue)
+ fprintf(f, "%s=", lvalue);
+
+ if (lease && conditional) {
+ sd_dns_resolver *resolvers;
+ _cleanup_strv_free_ char **names = NULL;
+ int r;
+
+ r = sd_dhcp_lease_get_dnr(lease, &resolvers);
+ if (r < 0)
+ return (void) log_warning_errno(r, "Failed to get DNR from DHCP lease, ignoring.");
+
+ r = dns_resolvers_to_dot_strv(resolvers, r, &names);
+ if (r < 0)
+ return (void) log_warning_errno(r, "Failed to get DoT servers from DHCP DNR, ignoring.");
+ if (r > 0)
+ fputstrv(f, names, NULL, space);
+ }
+
+ if (lvalue)
+ fputc('\n', f);
+
+ return;
+}
+
static void link_save_domains(Link *link, FILE *f, OrderedSet *static_domains, UseDomains use_domains) {
bool space = false;
const char *p;
space = false;
link_save_dns(link, f, link->network->dns, link->network->n_dns, &space);
+ /* DNR resolvers are not required to provide Do53 service, however resolved doesn't
+ * know how to handle such a server so for now Do53 service is required, and
+ * assumed. */
+ serialize_resolvers(f, NULL, &space,
+ link->dhcp_lease,
+ link_get_use_dnr(link, NETWORK_CONFIG_SOURCE_DHCP4));
+
serialize_addresses(f, NULL, &space,
NULL,
link->dhcp_lease,