]> git.ipfire.org Git - thirdparty/systemd.git/blob - src/resolve/resolved-manager.c
Merge pull request #1010 from poettering/resolved-question-key
[thirdparty/systemd.git] / src / resolve / resolved-manager.c
1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
2
3 /***
4 This file is part of systemd.
5
6 Copyright 2014 Tom Gundersen <teg@jklm.no>
7
8 systemd is free software; you can redistribute it and/or modify it
9 under the terms of the GNU Lesser General Public License as published by
10 the Free Software Foundation; either version 2.1 of the License, or
11 (at your option) any later version.
12
13 systemd is distributed in the hope that it will be useful, but
14 WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Lesser General Public License for more details.
17
18 You should have received a copy of the GNU Lesser General Public License
19 along with systemd; If not, see <http://www.gnu.org/licenses/>.
20 ***/
21
22 #include <resolv.h>
23 #include <sys/ioctl.h>
24 #include <poll.h>
25 #include <netinet/in.h>
26
27 #include "netlink-util.h"
28 #include "network-internal.h"
29 #include "socket-util.h"
30 #include "af-list.h"
31 #include "utf8.h"
32 #include "fileio-label.h"
33 #include "ordered-set.h"
34 #include "random-util.h"
35 #include "hostname-util.h"
36
37 #include "dns-domain.h"
38 #include "resolved-conf.h"
39 #include "resolved-bus.h"
40 #include "resolved-manager.h"
41 #include "resolved-llmnr.h"
42
43 #define SEND_TIMEOUT_USEC (200 * USEC_PER_MSEC)
44
45 static int manager_process_link(sd_netlink *rtnl, sd_netlink_message *mm, void *userdata) {
46 Manager *m = userdata;
47 uint16_t type;
48 Link *l;
49 int ifindex, r;
50
51 assert(rtnl);
52 assert(m);
53 assert(mm);
54
55 r = sd_netlink_message_get_type(mm, &type);
56 if (r < 0)
57 goto fail;
58
59 r = sd_rtnl_message_link_get_ifindex(mm, &ifindex);
60 if (r < 0)
61 goto fail;
62
63 l = hashmap_get(m->links, INT_TO_PTR(ifindex));
64
65 switch (type) {
66
67 case RTM_NEWLINK:{
68 bool is_new = !l;
69
70 if (!l) {
71 r = link_new(m, &l, ifindex);
72 if (r < 0)
73 goto fail;
74 }
75
76 r = link_update_rtnl(l, mm);
77 if (r < 0)
78 goto fail;
79
80 r = link_update_monitor(l);
81 if (r < 0)
82 goto fail;
83
84 if (is_new)
85 log_debug("Found new link %i/%s", ifindex, l->name);
86
87 break;
88 }
89
90 case RTM_DELLINK:
91 if (l) {
92 log_debug("Removing link %i/%s", l->ifindex, l->name);
93 link_free(l);
94 }
95
96 break;
97 }
98
99 return 0;
100
101 fail:
102 log_warning_errno(r, "Failed to process RTNL link message: %m");
103 return 0;
104 }
105
106 static int manager_process_address(sd_netlink *rtnl, sd_netlink_message *mm, void *userdata) {
107 Manager *m = userdata;
108 union in_addr_union address;
109 uint16_t type;
110 int r, ifindex, family;
111 LinkAddress *a;
112 Link *l;
113
114 assert(rtnl);
115 assert(mm);
116 assert(m);
117
118 r = sd_netlink_message_get_type(mm, &type);
119 if (r < 0)
120 goto fail;
121
122 r = sd_rtnl_message_addr_get_ifindex(mm, &ifindex);
123 if (r < 0)
124 goto fail;
125
126 l = hashmap_get(m->links, INT_TO_PTR(ifindex));
127 if (!l)
128 return 0;
129
130 r = sd_rtnl_message_addr_get_family(mm, &family);
131 if (r < 0)
132 goto fail;
133
134 switch (family) {
135
136 case AF_INET:
137 r = sd_netlink_message_read_in_addr(mm, IFA_LOCAL, &address.in);
138 if (r < 0) {
139 r = sd_netlink_message_read_in_addr(mm, IFA_ADDRESS, &address.in);
140 if (r < 0)
141 goto fail;
142 }
143
144 break;
145
146 case AF_INET6:
147 r = sd_netlink_message_read_in6_addr(mm, IFA_LOCAL, &address.in6);
148 if (r < 0) {
149 r = sd_netlink_message_read_in6_addr(mm, IFA_ADDRESS, &address.in6);
150 if (r < 0)
151 goto fail;
152 }
153
154 break;
155
156 default:
157 return 0;
158 }
159
160 a = link_find_address(l, family, &address);
161
162 switch (type) {
163
164 case RTM_NEWADDR:
165
166 if (!a) {
167 r = link_address_new(l, &a, family, &address);
168 if (r < 0)
169 return r;
170 }
171
172 r = link_address_update_rtnl(a, mm);
173 if (r < 0)
174 return r;
175
176 break;
177
178 case RTM_DELADDR:
179 link_address_free(a);
180 break;
181 }
182
183 return 0;
184
185 fail:
186 log_warning_errno(r, "Failed to process RTNL address message: %m");
187 return 0;
188 }
189
190 static int manager_rtnl_listen(Manager *m) {
191 _cleanup_netlink_message_unref_ sd_netlink_message *req = NULL, *reply = NULL;
192 sd_netlink_message *i;
193 int r;
194
195 assert(m);
196
197 /* First, subscribe to interfaces coming and going */
198 r = sd_netlink_open(&m->rtnl);
199 if (r < 0)
200 return r;
201
202 r = sd_netlink_attach_event(m->rtnl, m->event, 0);
203 if (r < 0)
204 return r;
205
206 r = sd_netlink_add_match(m->rtnl, RTM_NEWLINK, manager_process_link, m);
207 if (r < 0)
208 return r;
209
210 r = sd_netlink_add_match(m->rtnl, RTM_DELLINK, manager_process_link, m);
211 if (r < 0)
212 return r;
213
214 r = sd_netlink_add_match(m->rtnl, RTM_NEWADDR, manager_process_address, m);
215 if (r < 0)
216 return r;
217
218 r = sd_netlink_add_match(m->rtnl, RTM_DELADDR, manager_process_address, m);
219 if (r < 0)
220 return r;
221
222 /* Then, enumerate all links */
223 r = sd_rtnl_message_new_link(m->rtnl, &req, RTM_GETLINK, 0);
224 if (r < 0)
225 return r;
226
227 r = sd_netlink_message_request_dump(req, true);
228 if (r < 0)
229 return r;
230
231 r = sd_netlink_call(m->rtnl, req, 0, &reply);
232 if (r < 0)
233 return r;
234
235 for (i = reply; i; i = sd_netlink_message_next(i)) {
236 r = manager_process_link(m->rtnl, i, m);
237 if (r < 0)
238 return r;
239 }
240
241 req = sd_netlink_message_unref(req);
242 reply = sd_netlink_message_unref(reply);
243
244 /* Finally, enumerate all addresses, too */
245 r = sd_rtnl_message_new_addr(m->rtnl, &req, RTM_GETADDR, 0, AF_UNSPEC);
246 if (r < 0)
247 return r;
248
249 r = sd_netlink_message_request_dump(req, true);
250 if (r < 0)
251 return r;
252
253 r = sd_netlink_call(m->rtnl, req, 0, &reply);
254 if (r < 0)
255 return r;
256
257 for (i = reply; i; i = sd_netlink_message_next(i)) {
258 r = manager_process_address(m->rtnl, i, m);
259 if (r < 0)
260 return r;
261 }
262
263 return r;
264 }
265
266 static int on_network_event(sd_event_source *s, int fd, uint32_t revents, void *userdata) {
267 Manager *m = userdata;
268 Iterator i;
269 Link *l;
270 int r;
271
272 assert(m);
273
274 sd_network_monitor_flush(m->network_monitor);
275
276 HASHMAP_FOREACH(l, m->links, i) {
277 r = link_update_monitor(l);
278 if (r < 0)
279 log_warning_errno(r, "Failed to update monitor information for %i: %m", l->ifindex);
280 }
281
282 r = manager_write_resolv_conf(m);
283 if (r < 0)
284 log_warning_errno(r, "Could not update resolv.conf: %m");
285
286 return 0;
287 }
288
289 static int manager_network_monitor_listen(Manager *m) {
290 int r, fd, events;
291
292 assert(m);
293
294 r = sd_network_monitor_new(&m->network_monitor, NULL);
295 if (r < 0)
296 return r;
297
298 fd = sd_network_monitor_get_fd(m->network_monitor);
299 if (fd < 0)
300 return fd;
301
302 events = sd_network_monitor_get_events(m->network_monitor);
303 if (events < 0)
304 return events;
305
306 r = sd_event_add_io(m->event, &m->network_event_source, fd, events, &on_network_event, m);
307 if (r < 0)
308 return r;
309
310 return 0;
311 }
312
313 static int determine_hostname(char **llmnr_hostname, char **mdns_hostname) {
314 _cleanup_free_ char *h = NULL, *n = NULL;
315 char label[DNS_LABEL_MAX];
316 const char *p;
317 int r, k;
318
319 assert(llmnr_hostname);
320 assert(mdns_hostname);
321
322 /* Extract and normalize the first label of the locally
323 * configured hostname, and check it's not "localhost". */
324
325 h = gethostname_malloc();
326 if (!h)
327 return log_oom();
328
329 p = h;
330 r = dns_label_unescape(&p, label, sizeof(label));
331 if (r < 0)
332 return log_error_errno(r, "Failed to unescape host name: %m");
333 if (r == 0) {
334 log_error("Couldn't find a single label in hosntame.");
335 return -EINVAL;
336 }
337
338 k = dns_label_undo_idna(label, r, label, sizeof(label));
339 if (k < 0)
340 return log_error_errno(k, "Failed to undo IDNA: %m");
341 if (k > 0)
342 r = k;
343
344 if (!utf8_is_valid(label)) {
345 log_error("System hostname is not UTF-8 clean.");
346 return -EINVAL;
347 }
348
349 r = dns_label_escape(label, r, &n);
350 if (r < 0)
351 return log_error_errno(r, "Failed to escape host name: %m");
352
353 if (is_localhost(n)) {
354 log_debug("System hostname is 'localhost', ignoring.");
355 return -EINVAL;
356 }
357
358 r = dns_name_concat(n, "local", mdns_hostname);
359 if (r < 0)
360 return log_error_errno(r, "Failed to determine mDNS hostname: %m");
361
362 *llmnr_hostname = n;
363 n = NULL;
364
365 return 0;
366 }
367
368 static int on_hostname_change(sd_event_source *es, int fd, uint32_t revents, void *userdata) {
369 _cleanup_free_ char *llmnr_hostname = NULL, *mdns_hostname = NULL;
370 Manager *m = userdata;
371 int r;
372
373 assert(m);
374
375 r = determine_hostname(&llmnr_hostname, &mdns_hostname);
376 if (r < 0)
377 return 0; /* ignore invalid hostnames */
378
379 if (streq(llmnr_hostname, m->llmnr_hostname) && streq(mdns_hostname, m->mdns_hostname))
380 return 0;
381
382 log_info("System hostname changed to '%s'.", llmnr_hostname);
383
384 free(m->llmnr_hostname);
385 free(m->mdns_hostname);
386
387 m->llmnr_hostname = llmnr_hostname;
388 m->mdns_hostname = mdns_hostname;
389
390 llmnr_hostname = mdns_hostname = NULL;
391
392 manager_refresh_rrs(m);
393
394 return 0;
395 }
396
397 static int manager_watch_hostname(Manager *m) {
398 int r;
399
400 assert(m);
401
402 m->hostname_fd = open("/proc/sys/kernel/hostname", O_RDONLY|O_CLOEXEC|O_NDELAY|O_NOCTTY);
403 if (m->hostname_fd < 0) {
404 log_warning_errno(errno, "Failed to watch hostname: %m");
405 return 0;
406 }
407
408 r = sd_event_add_io(m->event, &m->hostname_event_source, m->hostname_fd, 0, on_hostname_change, m);
409 if (r < 0) {
410 if (r == -EPERM)
411 /* kernels prior to 3.2 don't support polling this file. Ignore the failure. */
412 m->hostname_fd = safe_close(m->hostname_fd);
413 else
414 return log_error_errno(r, "Failed to add hostname event source: %m");
415 }
416
417 r = determine_hostname(&m->llmnr_hostname, &m->mdns_hostname);
418 if (r < 0) {
419 log_info("Defaulting to hostname 'linux'.");
420 m->llmnr_hostname = strdup("linux");
421 if (!m->llmnr_hostname)
422 return log_oom();
423
424 m->mdns_hostname = strdup("linux.local");
425 if (!m->mdns_hostname)
426 return log_oom();
427 } else
428 log_info("Using system hostname '%s'.", m->llmnr_hostname);
429
430 return 0;
431 }
432
433 int manager_new(Manager **ret) {
434 _cleanup_(manager_freep) Manager *m = NULL;
435 int r;
436
437 assert(ret);
438
439 m = new0(Manager, 1);
440 if (!m)
441 return -ENOMEM;
442
443 m->llmnr_ipv4_udp_fd = m->llmnr_ipv6_udp_fd = -1;
444 m->llmnr_ipv4_tcp_fd = m->llmnr_ipv6_tcp_fd = -1;
445 m->hostname_fd = -1;
446
447 m->llmnr_support = SUPPORT_YES;
448 m->read_resolv_conf = true;
449
450 r = manager_parse_dns_server(m, DNS_SERVER_FALLBACK, DNS_SERVERS);
451 if (r < 0)
452 return r;
453
454 r = sd_event_default(&m->event);
455 if (r < 0)
456 return r;
457
458 sd_event_add_signal(m->event, NULL, SIGTERM, NULL, NULL);
459 sd_event_add_signal(m->event, NULL, SIGINT, NULL, NULL);
460
461 sd_event_set_watchdog(m->event, true);
462
463 r = manager_watch_hostname(m);
464 if (r < 0)
465 return r;
466
467 r = dns_scope_new(m, &m->unicast_scope, NULL, DNS_PROTOCOL_DNS, AF_UNSPEC);
468 if (r < 0)
469 return r;
470
471 r = manager_network_monitor_listen(m);
472 if (r < 0)
473 return r;
474
475 r = manager_rtnl_listen(m);
476 if (r < 0)
477 return r;
478
479 r = manager_connect_bus(m);
480 if (r < 0)
481 return r;
482
483 *ret = m;
484 m = NULL;
485
486 return 0;
487 }
488
489 int manager_start(Manager *m) {
490 int r;
491
492 assert(m);
493
494 r = manager_llmnr_start(m);
495 if (r < 0)
496 return r;
497
498 return 0;
499 }
500
501 Manager *manager_free(Manager *m) {
502 Link *l;
503
504 if (!m)
505 return NULL;
506
507 while ((l = hashmap_first(m->links)))
508 link_free(l);
509
510 while (m->dns_queries)
511 dns_query_free(m->dns_queries);
512
513 manager_flush_dns_servers(m, DNS_SERVER_SYSTEM);
514 manager_flush_dns_servers(m, DNS_SERVER_FALLBACK);
515
516 dns_scope_free(m->unicast_scope);
517
518 hashmap_free(m->links);
519 hashmap_free(m->dns_transactions);
520
521 sd_event_source_unref(m->network_event_source);
522 sd_network_monitor_unref(m->network_monitor);
523
524 manager_llmnr_stop(m);
525
526 sd_bus_slot_unref(m->prepare_for_sleep_slot);
527 sd_event_source_unref(m->bus_retry_event_source);
528 sd_bus_unref(m->bus);
529
530 sd_event_unref(m->event);
531
532 dns_resource_key_unref(m->llmnr_host_ipv4_key);
533 dns_resource_key_unref(m->llmnr_host_ipv6_key);
534
535 safe_close(m->hostname_fd);
536 sd_event_source_unref(m->hostname_event_source);
537 free(m->llmnr_hostname);
538 free(m->mdns_hostname);
539
540 free(m);
541
542 return NULL;
543 }
544
545 int manager_read_resolv_conf(Manager *m) {
546 _cleanup_fclose_ FILE *f = NULL;
547 struct stat st, own;
548 char line[LINE_MAX];
549 DnsServer *s, *nx;
550 usec_t t;
551 int r;
552
553 assert(m);
554
555 /* Reads the system /etc/resolv.conf, if it exists and is not
556 * symlinked to our own resolv.conf instance */
557
558 if (!m->read_resolv_conf)
559 return 0;
560
561 r = stat("/etc/resolv.conf", &st);
562 if (r < 0) {
563 if (errno != ENOENT)
564 log_warning_errno(errno, "Failed to open /etc/resolv.conf: %m");
565 r = -errno;
566 goto clear;
567 }
568
569 /* Have we already seen the file? */
570 t = timespec_load(&st.st_mtim);
571 if (t == m->resolv_conf_mtime)
572 return 0;
573
574 m->resolv_conf_mtime = t;
575
576 /* Is it symlinked to our own file? */
577 if (stat("/run/systemd/resolve/resolv.conf", &own) >= 0 &&
578 st.st_dev == own.st_dev &&
579 st.st_ino == own.st_ino) {
580 r = 0;
581 goto clear;
582 }
583
584 f = fopen("/etc/resolv.conf", "re");
585 if (!f) {
586 if (errno != ENOENT)
587 log_warning_errno(errno, "Failed to open /etc/resolv.conf: %m");
588 r = -errno;
589 goto clear;
590 }
591
592 if (fstat(fileno(f), &st) < 0) {
593 log_error_errno(errno, "Failed to stat open file: %m");
594 r = -errno;
595 goto clear;
596 }
597
598 LIST_FOREACH(servers, s, m->dns_servers)
599 s->marked = true;
600
601 FOREACH_LINE(line, f, r = -errno; goto clear) {
602 union in_addr_union address;
603 int family;
604 char *l;
605 const char *a;
606
607 truncate_nl(line);
608
609 l = strstrip(line);
610 if (*l == '#' || *l == ';')
611 continue;
612
613 a = first_word(l, "nameserver");
614 if (!a)
615 continue;
616
617 r = in_addr_from_string_auto(a, &family, &address);
618 if (r < 0) {
619 log_warning("Failed to parse name server %s.", a);
620 continue;
621 }
622
623 LIST_FOREACH(servers, s, m->dns_servers)
624 if (s->family == family && in_addr_equal(family, &s->address, &address) > 0)
625 break;
626
627 if (s)
628 s->marked = false;
629 else {
630 r = dns_server_new(m, NULL, DNS_SERVER_SYSTEM, NULL, family, &address);
631 if (r < 0)
632 goto clear;
633 }
634 }
635
636 LIST_FOREACH_SAFE(servers, s, nx, m->dns_servers)
637 if (s->marked) {
638 LIST_REMOVE(servers, m->dns_servers, s);
639 dns_server_unref(s);
640 }
641
642 /* Whenever /etc/resolv.conf changes, start using the first
643 * DNS server of it. This is useful to deal with broken
644 * network managing implementations (like NetworkManager),
645 * that when connecting to a VPN place both the VPN DNS
646 * servers and the local ones in /etc/resolv.conf. Without
647 * resetting the DNS server to use back to the first entry we
648 * will continue to use the local one thus being unable to
649 * resolve VPN domains. */
650 manager_set_dns_server(m, m->dns_servers);
651
652 return 0;
653
654 clear:
655 while (m->dns_servers) {
656 s = m->dns_servers;
657
658 LIST_REMOVE(servers, m->dns_servers, s);
659 dns_server_unref(s);
660 }
661
662 return r;
663 }
664
665 static void write_resolv_conf_server(DnsServer *s, FILE *f, unsigned *count) {
666 _cleanup_free_ char *t = NULL;
667 int r;
668
669 assert(s);
670 assert(f);
671 assert(count);
672
673 r = in_addr_to_string(s->family, &s->address, &t);
674 if (r < 0) {
675 log_warning_errno(r, "Invalid DNS address. Ignoring: %m");
676 return;
677 }
678
679 if (*count == MAXNS)
680 fputs("# Too many DNS servers configured, the following entries may be ignored.\n", f);
681
682 fprintf(f, "nameserver %s\n", t);
683 (*count) ++;
684 }
685
686 static void write_resolv_conf_search(
687 const char *domain, FILE *f,
688 unsigned *count,
689 unsigned *length) {
690
691 assert(domain);
692 assert(f);
693 assert(length);
694
695 if (*count >= MAXDNSRCH ||
696 *length + strlen(domain) > 256) {
697 if (*count == MAXDNSRCH)
698 fputs(" # Too many search domains configured, remaining ones ignored.", f);
699 if (*length <= 256)
700 fputs(" # Total length of all search domains is too long, remaining ones ignored.", f);
701
702 return;
703 }
704
705 fprintf(f, " %s", domain);
706
707 (*length) += strlen(domain);
708 (*count) ++;
709 }
710
711 static int write_resolv_conf_contents(FILE *f, OrderedSet *dns, OrderedSet *domains) {
712 Iterator i;
713
714 fputs("# This file is managed by systemd-resolved(8). Do not edit.\n#\n"
715 "# Third party programs must not access this file directly, but\n"
716 "# only through the symlink at /etc/resolv.conf. To manage\n"
717 "# resolv.conf(5) in a different way, replace the symlink by a\n"
718 "# static file or a different symlink.\n\n", f);
719
720 if (ordered_set_isempty(dns))
721 fputs("# No DNS servers known.\n", f);
722 else {
723 DnsServer *s;
724 unsigned count = 0;
725
726 ORDERED_SET_FOREACH(s, dns, i)
727 write_resolv_conf_server(s, f, &count);
728 }
729
730 if (!ordered_set_isempty(domains)) {
731 unsigned length = 0, count = 0;
732 char *domain;
733
734 fputs("search", f);
735 ORDERED_SET_FOREACH(domain, domains, i)
736 write_resolv_conf_search(domain, f, &count, &length);
737 fputs("\n", f);
738 }
739
740 return fflush_and_check(f);
741 }
742
743 int manager_write_resolv_conf(Manager *m) {
744 static const char path[] = "/run/systemd/resolve/resolv.conf";
745 _cleanup_free_ char *temp_path = NULL;
746 _cleanup_fclose_ FILE *f = NULL;
747 _cleanup_ordered_set_free_ OrderedSet *dns = NULL, *domains = NULL;
748 DnsServer *s;
749 Iterator i;
750 Link *l;
751 int r;
752
753 assert(m);
754
755 /* Read the system /etc/resolv.conf first */
756 manager_read_resolv_conf(m);
757
758 /* Add the full list to a set, to filter out duplicates */
759 dns = ordered_set_new(&dns_server_hash_ops);
760 if (!dns)
761 return -ENOMEM;
762
763 domains = ordered_set_new(&dns_name_hash_ops);
764 if (!domains)
765 return -ENOMEM;
766
767 /* First add the system-wide servers */
768 LIST_FOREACH(servers, s, m->dns_servers) {
769 r = ordered_set_put(dns, s);
770 if (r == -EEXIST)
771 continue;
772 if (r < 0)
773 return r;
774 }
775
776 /* Then, add the per-link servers and domains */
777 HASHMAP_FOREACH(l, m->links, i) {
778 char **domain;
779
780 LIST_FOREACH(servers, s, l->dns_servers) {
781 r = ordered_set_put(dns, s);
782 if (r == -EEXIST)
783 continue;
784 if (r < 0)
785 return r;
786 }
787
788 if (!l->unicast_scope)
789 continue;
790
791 STRV_FOREACH(domain, l->unicast_scope->domains) {
792 r = ordered_set_put(domains, *domain);
793 if (r == -EEXIST)
794 continue;
795 if (r < 0)
796 return r;
797 }
798 }
799
800 /* If we found nothing, add the fallback servers */
801 if (ordered_set_isempty(dns)) {
802 LIST_FOREACH(servers, s, m->fallback_dns_servers) {
803 r = ordered_set_put(dns, s);
804 if (r == -EEXIST)
805 continue;
806 if (r < 0)
807 return r;
808 }
809 }
810
811 r = fopen_temporary_label(path, path, &f, &temp_path);
812 if (r < 0)
813 return r;
814
815 fchmod(fileno(f), 0644);
816
817 r = write_resolv_conf_contents(f, dns, domains);
818 if (r < 0)
819 goto fail;
820
821 if (rename(temp_path, path) < 0) {
822 r = -errno;
823 goto fail;
824 }
825
826 return 0;
827
828 fail:
829 (void) unlink(path);
830 (void) unlink(temp_path);
831 return r;
832 }
833
834 int manager_recv(Manager *m, int fd, DnsProtocol protocol, DnsPacket **ret) {
835 _cleanup_(dns_packet_unrefp) DnsPacket *p = NULL;
836 union {
837 struct cmsghdr header; /* For alignment */
838 uint8_t buffer[CMSG_SPACE(MAXSIZE(struct in_pktinfo, struct in6_pktinfo))
839 + CMSG_SPACE(int) /* ttl/hoplimit */
840 + EXTRA_CMSG_SPACE /* kernel appears to require extra buffer space */];
841 } control;
842 union sockaddr_union sa;
843 struct msghdr mh = {};
844 struct cmsghdr *cmsg;
845 struct iovec iov;
846 int ms = 0, r;
847 ssize_t l;
848
849 assert(m);
850 assert(fd >= 0);
851 assert(ret);
852
853 r = ioctl(fd, FIONREAD, &ms);
854 if (r < 0)
855 return -errno;
856 if (ms < 0)
857 return -EIO;
858
859 r = dns_packet_new(&p, protocol, ms);
860 if (r < 0)
861 return r;
862
863 iov.iov_base = DNS_PACKET_DATA(p);
864 iov.iov_len = p->allocated;
865
866 mh.msg_name = &sa.sa;
867 mh.msg_namelen = sizeof(sa);
868 mh.msg_iov = &iov;
869 mh.msg_iovlen = 1;
870 mh.msg_control = &control;
871 mh.msg_controllen = sizeof(control);
872
873 l = recvmsg(fd, &mh, 0);
874 if (l < 0) {
875 if (errno == EAGAIN || errno == EINTR)
876 return 0;
877
878 return -errno;
879 }
880
881 if (l <= 0)
882 return -EIO;
883
884 assert(!(mh.msg_flags & MSG_CTRUNC));
885 assert(!(mh.msg_flags & MSG_TRUNC));
886
887 p->size = (size_t) l;
888
889 p->family = sa.sa.sa_family;
890 p->ipproto = IPPROTO_UDP;
891 if (p->family == AF_INET) {
892 p->sender.in = sa.in.sin_addr;
893 p->sender_port = be16toh(sa.in.sin_port);
894 } else if (p->family == AF_INET6) {
895 p->sender.in6 = sa.in6.sin6_addr;
896 p->sender_port = be16toh(sa.in6.sin6_port);
897 p->ifindex = sa.in6.sin6_scope_id;
898 } else
899 return -EAFNOSUPPORT;
900
901 CMSG_FOREACH(cmsg, &mh) {
902
903 if (cmsg->cmsg_level == IPPROTO_IPV6) {
904 assert(p->family == AF_INET6);
905
906 switch (cmsg->cmsg_type) {
907
908 case IPV6_PKTINFO: {
909 struct in6_pktinfo *i = (struct in6_pktinfo*) CMSG_DATA(cmsg);
910
911 if (p->ifindex <= 0)
912 p->ifindex = i->ipi6_ifindex;
913
914 p->destination.in6 = i->ipi6_addr;
915 break;
916 }
917
918 case IPV6_HOPLIMIT:
919 p->ttl = *(int *) CMSG_DATA(cmsg);
920 break;
921
922 }
923 } else if (cmsg->cmsg_level == IPPROTO_IP) {
924 assert(p->family == AF_INET);
925
926 switch (cmsg->cmsg_type) {
927
928 case IP_PKTINFO: {
929 struct in_pktinfo *i = (struct in_pktinfo*) CMSG_DATA(cmsg);
930
931 if (p->ifindex <= 0)
932 p->ifindex = i->ipi_ifindex;
933
934 p->destination.in = i->ipi_addr;
935 break;
936 }
937
938 case IP_TTL:
939 p->ttl = *(int *) CMSG_DATA(cmsg);
940 break;
941 }
942 }
943 }
944
945 /* The Linux kernel sets the interface index to the loopback
946 * device if the packet came from the local host since it
947 * avoids the routing table in such a case. Let's unset the
948 * interface index in such a case. */
949 if (p->ifindex == LOOPBACK_IFINDEX)
950 p->ifindex = 0;
951
952 if (protocol != DNS_PROTOCOL_DNS) {
953 /* If we don't know the interface index still, we look for the
954 * first local interface with a matching address. Yuck! */
955 if (p->ifindex <= 0)
956 p->ifindex = manager_find_ifindex(m, p->family, &p->destination);
957 }
958
959 *ret = p;
960 p = NULL;
961
962 return 1;
963 }
964
965 static int sendmsg_loop(int fd, struct msghdr *mh, int flags) {
966 int r;
967
968 assert(fd >= 0);
969 assert(mh);
970
971 for (;;) {
972 if (sendmsg(fd, mh, flags) >= 0)
973 return 0;
974
975 if (errno == EINTR)
976 continue;
977
978 if (errno != EAGAIN)
979 return -errno;
980
981 r = fd_wait_for_event(fd, POLLOUT, SEND_TIMEOUT_USEC);
982 if (r < 0)
983 return r;
984 if (r == 0)
985 return -ETIMEDOUT;
986 }
987 }
988
989 static int write_loop(int fd, void *message, size_t length) {
990 int r;
991
992 assert(fd >= 0);
993 assert(message);
994
995 for (;;) {
996 if (write(fd, message, length) >= 0)
997 return 0;
998
999 if (errno == EINTR)
1000 continue;
1001
1002 if (errno != EAGAIN)
1003 return -errno;
1004
1005 r = fd_wait_for_event(fd, POLLOUT, SEND_TIMEOUT_USEC);
1006 if (r < 0)
1007 return r;
1008 if (r == 0)
1009 return -ETIMEDOUT;
1010 }
1011 }
1012
1013 int manager_write(Manager *m, int fd, DnsPacket *p) {
1014 int r;
1015
1016 log_debug("Sending %s packet with id %u", DNS_PACKET_QR(p) ? "response" : "query", DNS_PACKET_ID(p));
1017
1018 r = write_loop(fd, DNS_PACKET_DATA(p), p->size);
1019 if (r < 0)
1020 return r;
1021
1022 return 0;
1023 }
1024
1025 static int manager_ipv4_send(Manager *m, int fd, int ifindex, const struct in_addr *addr, uint16_t port, DnsPacket *p) {
1026 union sockaddr_union sa = {
1027 .in.sin_family = AF_INET,
1028 };
1029 union {
1030 struct cmsghdr header; /* For alignment */
1031 uint8_t buffer[CMSG_SPACE(sizeof(struct in_pktinfo))];
1032 } control;
1033 struct msghdr mh = {};
1034 struct iovec iov;
1035
1036 assert(m);
1037 assert(fd >= 0);
1038 assert(addr);
1039 assert(port > 0);
1040 assert(p);
1041
1042 iov.iov_base = DNS_PACKET_DATA(p);
1043 iov.iov_len = p->size;
1044
1045 sa.in.sin_addr = *addr;
1046 sa.in.sin_port = htobe16(port),
1047
1048 mh.msg_iov = &iov;
1049 mh.msg_iovlen = 1;
1050 mh.msg_name = &sa.sa;
1051 mh.msg_namelen = sizeof(sa.in);
1052
1053 if (ifindex > 0) {
1054 struct cmsghdr *cmsg;
1055 struct in_pktinfo *pi;
1056
1057 zero(control);
1058
1059 mh.msg_control = &control;
1060 mh.msg_controllen = CMSG_LEN(sizeof(struct in_pktinfo));
1061
1062 cmsg = CMSG_FIRSTHDR(&mh);
1063 cmsg->cmsg_len = mh.msg_controllen;
1064 cmsg->cmsg_level = IPPROTO_IP;
1065 cmsg->cmsg_type = IP_PKTINFO;
1066
1067 pi = (struct in_pktinfo*) CMSG_DATA(cmsg);
1068 pi->ipi_ifindex = ifindex;
1069 }
1070
1071 return sendmsg_loop(fd, &mh, 0);
1072 }
1073
1074 static int manager_ipv6_send(Manager *m, int fd, int ifindex, const struct in6_addr *addr, uint16_t port, DnsPacket *p) {
1075 union sockaddr_union sa = {
1076 .in6.sin6_family = AF_INET6,
1077 };
1078 union {
1079 struct cmsghdr header; /* For alignment */
1080 uint8_t buffer[CMSG_SPACE(sizeof(struct in6_pktinfo))];
1081 } control;
1082 struct msghdr mh = {};
1083 struct iovec iov;
1084
1085 assert(m);
1086 assert(fd >= 0);
1087 assert(addr);
1088 assert(port > 0);
1089 assert(p);
1090
1091 iov.iov_base = DNS_PACKET_DATA(p);
1092 iov.iov_len = p->size;
1093
1094 sa.in6.sin6_addr = *addr;
1095 sa.in6.sin6_port = htobe16(port),
1096 sa.in6.sin6_scope_id = ifindex;
1097
1098 mh.msg_iov = &iov;
1099 mh.msg_iovlen = 1;
1100 mh.msg_name = &sa.sa;
1101 mh.msg_namelen = sizeof(sa.in6);
1102
1103 if (ifindex > 0) {
1104 struct cmsghdr *cmsg;
1105 struct in6_pktinfo *pi;
1106
1107 zero(control);
1108
1109 mh.msg_control = &control;
1110 mh.msg_controllen = CMSG_LEN(sizeof(struct in6_pktinfo));
1111
1112 cmsg = CMSG_FIRSTHDR(&mh);
1113 cmsg->cmsg_len = mh.msg_controllen;
1114 cmsg->cmsg_level = IPPROTO_IPV6;
1115 cmsg->cmsg_type = IPV6_PKTINFO;
1116
1117 pi = (struct in6_pktinfo*) CMSG_DATA(cmsg);
1118 pi->ipi6_ifindex = ifindex;
1119 }
1120
1121 return sendmsg_loop(fd, &mh, 0);
1122 }
1123
1124 int manager_send(Manager *m, int fd, int ifindex, int family, const union in_addr_union *addr, uint16_t port, DnsPacket *p) {
1125 assert(m);
1126 assert(fd >= 0);
1127 assert(addr);
1128 assert(port > 0);
1129 assert(p);
1130
1131 log_debug("Sending %s packet with id %u on interface %i/%s", DNS_PACKET_QR(p) ? "response" : "query", DNS_PACKET_ID(p), ifindex, af_to_name(family));
1132
1133 if (family == AF_INET)
1134 return manager_ipv4_send(m, fd, ifindex, &addr->in, port, p);
1135 else if (family == AF_INET6)
1136 return manager_ipv6_send(m, fd, ifindex, &addr->in6, port, p);
1137
1138 return -EAFNOSUPPORT;
1139 }
1140
1141 DnsServer* manager_find_dns_server(Manager *m, int family, const union in_addr_union *in_addr) {
1142 DnsServer *s;
1143
1144 assert(m);
1145 assert(in_addr);
1146
1147 LIST_FOREACH(servers, s, m->dns_servers)
1148 if (s->family == family && in_addr_equal(family, &s->address, in_addr) > 0)
1149 return s;
1150
1151 LIST_FOREACH(servers, s, m->fallback_dns_servers)
1152 if (s->family == family && in_addr_equal(family, &s->address, in_addr) > 0)
1153 return s;
1154
1155 return NULL;
1156 }
1157
1158 DnsServer *manager_set_dns_server(Manager *m, DnsServer *s) {
1159 assert(m);
1160
1161 if (m->current_dns_server == s)
1162 return s;
1163
1164 if (s) {
1165 _cleanup_free_ char *ip = NULL;
1166
1167 in_addr_to_string(s->family, &s->address, &ip);
1168 log_info("Switching to system DNS server %s.", strna(ip));
1169 }
1170
1171 m->current_dns_server = s;
1172
1173 if (m->unicast_scope)
1174 dns_cache_flush(&m->unicast_scope->cache);
1175
1176 return s;
1177 }
1178
1179 DnsServer *manager_get_dns_server(Manager *m) {
1180 Link *l;
1181 assert(m);
1182
1183 /* Try to read updates resolv.conf */
1184 manager_read_resolv_conf(m);
1185
1186 if (!m->current_dns_server)
1187 manager_set_dns_server(m, m->dns_servers);
1188
1189 if (!m->current_dns_server) {
1190 bool found = false;
1191 Iterator i;
1192
1193 /* No DNS servers configured, let's see if there are
1194 * any on any links. If not, we use the fallback
1195 * servers */
1196
1197 HASHMAP_FOREACH(l, m->links, i)
1198 if (l->dns_servers) {
1199 found = true;
1200 break;
1201 }
1202
1203 if (!found)
1204 manager_set_dns_server(m, m->fallback_dns_servers);
1205 }
1206
1207 return m->current_dns_server;
1208 }
1209
1210 void manager_next_dns_server(Manager *m) {
1211 assert(m);
1212
1213 /* If there's currently no DNS server set, then the next
1214 * manager_get_dns_server() will find one */
1215 if (!m->current_dns_server)
1216 return;
1217
1218 /* Change to the next one */
1219 if (m->current_dns_server->servers_next) {
1220 manager_set_dns_server(m, m->current_dns_server->servers_next);
1221 return;
1222 }
1223
1224 /* If there was no next one, then start from the beginning of
1225 * the list */
1226 if (m->current_dns_server->type == DNS_SERVER_FALLBACK)
1227 manager_set_dns_server(m, m->fallback_dns_servers);
1228 else
1229 manager_set_dns_server(m, m->dns_servers);
1230 }
1231
1232 uint32_t manager_find_mtu(Manager *m) {
1233 uint32_t mtu = 0;
1234 Link *l;
1235 Iterator i;
1236
1237 /* If we don't know on which link a DNS packet would be
1238 * delivered, let's find the largest MTU that works on all
1239 * interfaces we know of */
1240
1241 HASHMAP_FOREACH(l, m->links, i) {
1242 if (l->mtu <= 0)
1243 continue;
1244
1245 if (mtu <= 0 || l->mtu < mtu)
1246 mtu = l->mtu;
1247 }
1248
1249 return mtu;
1250 }
1251
1252 int manager_find_ifindex(Manager *m, int family, const union in_addr_union *in_addr) {
1253 LinkAddress *a;
1254
1255 assert(m);
1256
1257 a = manager_find_link_address(m, family, in_addr);
1258 if (a)
1259 return a->link->ifindex;
1260
1261 return 0;
1262 }
1263
1264 void manager_refresh_rrs(Manager *m) {
1265 Iterator i;
1266 Link *l;
1267
1268 assert(m);
1269
1270 m->llmnr_host_ipv4_key = dns_resource_key_unref(m->llmnr_host_ipv4_key);
1271 m->llmnr_host_ipv6_key = dns_resource_key_unref(m->llmnr_host_ipv6_key);
1272
1273 HASHMAP_FOREACH(l, m->links, i) {
1274 link_add_rrs(l, true);
1275 link_add_rrs(l, false);
1276 }
1277 }
1278
1279 int manager_next_hostname(Manager *m) {
1280 const char *p;
1281 uint64_t u, a;
1282 char *h, *k;
1283 int r;
1284
1285 assert(m);
1286
1287 p = strchr(m->llmnr_hostname, 0);
1288 assert(p);
1289
1290 while (p > m->llmnr_hostname) {
1291 if (!strchr("0123456789", p[-1]))
1292 break;
1293
1294 p--;
1295 }
1296
1297 if (*p == 0 || safe_atou64(p, &u) < 0 || u <= 0)
1298 u = 1;
1299
1300 /* Add a random number to the old value. This way we can avoid
1301 * that two hosts pick the same hostname, win on IPv4 and lose
1302 * on IPv6 (or vice versa), and pick the same hostname
1303 * replacement hostname, ad infinitum. We still want the
1304 * numbers to go up monotonically, hence we just add a random
1305 * value 1..10 */
1306
1307 random_bytes(&a, sizeof(a));
1308 u += 1 + a % 10;
1309
1310 if (asprintf(&h, "%.*s%" PRIu64, (int) (p - m->llmnr_hostname), m->llmnr_hostname, u) < 0)
1311 return -ENOMEM;
1312
1313 r = dns_name_concat(h, "local", &k);
1314 if (r < 0) {
1315 free(h);
1316 return r;
1317 }
1318
1319 log_info("Hostname conflict, changing published hostname from '%s' to '%s'.", m->llmnr_hostname, h);
1320
1321 free(m->llmnr_hostname);
1322 m->llmnr_hostname = h;
1323
1324 free(m->mdns_hostname);
1325 m->mdns_hostname = k;
1326
1327 manager_refresh_rrs(m);
1328
1329 return 0;
1330 }
1331
1332 LinkAddress* manager_find_link_address(Manager *m, int family, const union in_addr_union *in_addr) {
1333 Iterator i;
1334 Link *l;
1335
1336 assert(m);
1337
1338 HASHMAP_FOREACH(l, m->links, i) {
1339 LinkAddress *a;
1340
1341 a = link_find_address(l, family, in_addr);
1342 if (a)
1343 return a;
1344 }
1345
1346 return NULL;
1347 }
1348
1349 bool manager_our_packet(Manager *m, DnsPacket *p) {
1350 assert(m);
1351 assert(p);
1352
1353 return !!manager_find_link_address(m, p->family, &p->sender);
1354 }
1355
1356 DnsScope* manager_find_scope(Manager *m, DnsPacket *p) {
1357 Link *l;
1358
1359 assert(m);
1360 assert(p);
1361
1362 l = hashmap_get(m->links, INT_TO_PTR(p->ifindex));
1363 if (!l)
1364 return NULL;
1365
1366 if (p->protocol == DNS_PROTOCOL_LLMNR) {
1367 if (p->family == AF_INET)
1368 return l->llmnr_ipv4_scope;
1369 else if (p->family == AF_INET6)
1370 return l->llmnr_ipv6_scope;
1371 }
1372
1373 return NULL;
1374 }
1375
1376 void manager_verify_all(Manager *m) {
1377 DnsScope *s;
1378
1379 assert(m);
1380
1381 LIST_FOREACH(scopes, s, m->dns_scopes)
1382 dns_zone_verify_all(&s->zone);
1383 }
1384
1385 void manager_flush_dns_servers(Manager *m, DnsServerType t) {
1386 DnsServer *s;
1387
1388 assert(m);
1389
1390 if (t == DNS_SERVER_SYSTEM)
1391 while (m->dns_servers) {
1392 s = m->dns_servers;
1393
1394 LIST_REMOVE(servers, m->dns_servers, s);
1395 dns_server_unref(s);
1396 }
1397
1398 if (t == DNS_SERVER_FALLBACK)
1399 while (m->fallback_dns_servers) {
1400 s = m->fallback_dns_servers;
1401
1402 LIST_REMOVE(servers, m->fallback_dns_servers, s);
1403 dns_server_unref(s);
1404 }
1405 }
1406
1407 int manager_is_own_hostname(Manager *m, const char *name) {
1408 int r;
1409
1410 assert(m);
1411 assert(name);
1412
1413 if (m->llmnr_hostname) {
1414 r = dns_name_equal(name, m->llmnr_hostname);
1415 if (r != 0)
1416 return r;
1417 }
1418
1419 if (m->mdns_hostname)
1420 return dns_name_equal(name, m->mdns_hostname);
1421
1422 return 0;
1423 }
1424
1425 static const char* const support_table[_SUPPORT_MAX] = {
1426 [SUPPORT_NO] = "no",
1427 [SUPPORT_YES] = "yes",
1428 [SUPPORT_RESOLVE] = "resolve",
1429 };
1430 DEFINE_STRING_TABLE_LOOKUP(support, Support);