]> git.ipfire.org Git - thirdparty/systemd.git/blob - src/network/networkd-link.c
networkd: netdev - introduce vtable for netdev kinds
[thirdparty/systemd.git] / src / network / networkd-link.c
1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
2
3 /***
4 This file is part of systemd.
5
6 Copyright 2013 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 <netinet/ether.h>
23 #include <linux/if.h>
24 #include <unistd.h>
25
26 #include "networkd.h"
27 #include "networkd-netdev.h"
28 #include "libudev-private.h"
29 #include "udev-util.h"
30 #include "util.h"
31 #include "virt.h"
32 #include "bus-util.h"
33 #include "network-internal.h"
34 #include "conf-parser.h"
35
36 #include "network-util.h"
37 #include "dhcp-lease-internal.h"
38
39 static int ipv4ll_address_update(Link *link, bool deprecate);
40 static bool ipv4ll_is_bound(sd_ipv4ll *ll);
41
42 static int link_new(Manager *manager, sd_rtnl_message *message, Link **ret) {
43 _cleanup_link_unref_ Link *link = NULL;
44 uint16_t type;
45 char *ifname;
46 int r, ifindex;
47
48 assert(manager);
49 assert(manager->links);
50 assert(message);
51 assert(ret);
52
53 r = sd_rtnl_message_get_type(message, &type);
54 if (r < 0)
55 return r;
56 else if (type != RTM_NEWLINK)
57 return -EINVAL;
58
59 r = sd_rtnl_message_link_get_ifindex(message, &ifindex);
60 if (r < 0)
61 return r;
62 else if (ifindex <= 0)
63 return -EINVAL;
64
65 r = sd_rtnl_message_read_string(message, IFLA_IFNAME, &ifname);
66 if (r < 0)
67 return r;
68
69 link = new0(Link, 1);
70 if (!link)
71 return -ENOMEM;
72
73 link->n_ref = 1;
74 link->manager = manager;
75 link->state = LINK_STATE_INITIALIZING;
76 link->ifindex = ifindex;
77 link->ifname = strdup(ifname);
78 if (!link->ifname)
79 return -ENOMEM;
80
81 r = sd_rtnl_message_read_ether_addr(message, IFLA_ADDRESS, &link->mac);
82 if (r < 0)
83 log_debug_link(link, "MAC address not found for new device, continuing without");
84
85 r = asprintf(&link->state_file, "/run/systemd/netif/links/%"PRIu64,
86 link->ifindex);
87 if (r < 0)
88 return -ENOMEM;
89
90 r = asprintf(&link->lease_file, "/run/systemd/netif/leases/%"PRIu64,
91 link->ifindex);
92 if (r < 0)
93 return -ENOMEM;
94
95 r = hashmap_put(manager->links, &link->ifindex, link);
96 if (r < 0)
97 return r;
98
99 *ret = link;
100 link = NULL;
101
102 return 0;
103 }
104
105 static void link_free(Link *link) {
106 Address *address;
107
108 if (!link)
109 return;
110
111 while ((address = link->addresses)) {
112 LIST_REMOVE(addresses, link->addresses, address);
113 address_free(address);
114 }
115
116 while ((address = link->pool_addresses)) {
117 LIST_REMOVE(addresses, link->pool_addresses, address);
118 address_free(address);
119 }
120
121 sd_dhcp_client_unref(link->dhcp_client);
122 sd_dhcp_lease_unref(link->dhcp_lease);
123
124 unlink(link->lease_file);
125 free(link->lease_file);
126
127 sd_ipv4ll_unref(link->ipv4ll);
128 sd_dhcp6_client_unref(link->dhcp6_client);
129 sd_icmp6_nd_unref(link->icmp6_router_discovery);
130
131 if (link->manager)
132 hashmap_remove(link->manager->links, &link->ifindex);
133
134 free(link->ifname);
135
136 unlink(link->state_file);
137 free(link->state_file);
138
139 udev_device_unref(link->udev_device);
140
141 free(link);
142 }
143
144 Link *link_unref(Link *link) {
145 if (link && (-- link->n_ref <= 0))
146 link_free(link);
147
148 return NULL;
149 }
150
151 Link *link_ref(Link *link) {
152 if (link)
153 assert_se(++ link->n_ref >= 2);
154
155 return link;
156 }
157
158 int link_get(Manager *m, int ifindex, Link **ret) {
159 Link *link;
160 uint64_t ifindex_64;
161
162 assert(m);
163 assert(m->links);
164 assert(ifindex);
165 assert(ret);
166
167 ifindex_64 = ifindex;
168 link = hashmap_get(m->links, &ifindex_64);
169 if (!link)
170 return -ENODEV;
171
172 *ret = link;
173
174 return 0;
175 }
176
177 void link_drop(Link *link) {
178 if (!link || link->state == LINK_STATE_LINGER)
179 return;
180
181 link->state = LINK_STATE_LINGER;
182
183 log_debug_link(link, "link removed");
184
185 link_unref(link);
186
187 return;
188 }
189
190 static void link_enter_unmanaged(Link *link) {
191 assert(link);
192
193 log_debug_link(link, "unmanaged");
194
195 link->state = LINK_STATE_UNMANAGED;
196
197 link_save(link);
198 }
199
200 static int link_stop_clients(Link *link) {
201 int r = 0, k;
202
203 assert(link);
204 assert(link->manager);
205 assert(link->manager->event);
206
207 if (!link->network)
208 return 0;
209
210 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V6)) {
211 assert(link->dhcp_client);
212
213 k = sd_dhcp_client_stop(link->dhcp_client);
214 if (k < 0) {
215 log_warning_link(link, "Could not stop DHCPv4 client: %s", strerror(-r));
216 r = k;
217 }
218 }
219
220 if (link->network->ipv4ll) {
221 assert(link->ipv4ll);
222
223 k = sd_ipv4ll_stop(link->ipv4ll);
224 if (k < 0) {
225 log_warning_link(link, "Could not stop IPv4 link-local: %s", strerror(-r));
226 r = k;
227 }
228 }
229
230 if (link->network->dhcp_server) {
231 assert(link->dhcp_server);
232
233 k = sd_dhcp_server_stop(link->dhcp_server);
234 if (k < 0) {
235 log_warning_link(link, "Could not stop DHCPv4 server: %s", strerror(-r));
236 r = k;
237 }
238 }
239
240 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V6)) {
241 assert(link->icmp6_router_discovery);
242
243 if (link->dhcp6_client) {
244 k = sd_dhcp6_client_stop(link->dhcp6_client);
245 if (k < 0) {
246 log_warning_link(link, "Could not stop DHCPv6 client: %s", strerror(-r));
247 r = k;
248 }
249 }
250
251 k = sd_icmp6_nd_stop(link->icmp6_router_discovery);
252 if (k < 0) {
253 log_warning_link(link, "Could not stop ICMPv6 router discovery: %s", strerror(-r));
254 r = k;
255 }
256 }
257
258 return r;
259 }
260
261 static void link_enter_failed(Link *link) {
262 assert(link);
263
264 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
265 return;
266
267 log_warning_link(link, "failed");
268
269 link->state = LINK_STATE_FAILED;
270
271 link_stop_clients(link);
272
273 link_save(link);
274 }
275
276 static Address* link_find_dhcp_server_address(Link *link) {
277 Address *address;
278
279 assert(link);
280 assert(link->network);
281
282 /* The the first statically configured address if there is any */
283 LIST_FOREACH(addresses, address, link->network->static_addresses) {
284
285 if (address->family != AF_INET)
286 continue;
287
288 if (in_addr_null(address->family, &address->in_addr))
289 continue;
290
291 return address;
292 }
293
294 /* If that didn't work, find a suitable address we got from the pool */
295 LIST_FOREACH(addresses, address, link->pool_addresses) {
296 if (address->family != AF_INET)
297 continue;
298
299 return address;
300 }
301
302 return NULL;
303 }
304
305 static int link_enter_configured(Link *link) {
306 int r;
307
308 assert(link);
309 assert(link->network);
310 assert(link->state == LINK_STATE_SETTING_ROUTES);
311
312 if (link->network->dhcp_server &&
313 !sd_dhcp_server_is_running(link->dhcp_server)) {
314 struct in_addr pool_start;
315 Address *address;
316
317 address = link_find_dhcp_server_address(link);
318 if (!address) {
319 log_warning_link(link, "Failed to find suitable address for DHCPv4 server instance.");
320 link_enter_failed(link);
321 return 0;
322 }
323
324 log_debug_link(link, "offering DHCPv4 leases");
325
326 r = sd_dhcp_server_set_address(link->dhcp_server, &address->in_addr.in);
327 if (r < 0)
328 return r;
329
330 /* offer 32 addresses starting from the address following the server address */
331 pool_start.s_addr = htobe32(be32toh(address->in_addr.in.s_addr) + 1);
332 r = sd_dhcp_server_set_lease_pool(link->dhcp_server,
333 &pool_start, 32);
334 if (r < 0)
335 return r;
336
337 /* TODO:
338 r = sd_dhcp_server_set_router(link->dhcp_server,
339 &main_address->in_addr.in);
340 if (r < 0)
341 return r;
342
343 r = sd_dhcp_server_set_prefixlen(link->dhcp_server,
344 main_address->prefixlen);
345 if (r < 0)
346 return r;
347 */
348
349 r = sd_dhcp_server_start(link->dhcp_server);
350 if (r < 0) {
351 log_warning_link(link, "could not start DHCPv4 server "
352 "instance: %s", strerror(-r));
353
354 link_enter_failed(link);
355
356 return 0;
357 }
358 }
359
360 log_info_link(link, "link configured");
361
362 link->state = LINK_STATE_CONFIGURED;
363
364 link_save(link);
365
366 return 0;
367 }
368
369 static int route_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
370 _cleanup_link_unref_ Link *link = userdata;
371 int r;
372
373 assert(link->route_messages > 0);
374 assert(IN_SET(link->state, LINK_STATE_SETTING_ADDRESSES,
375 LINK_STATE_SETTING_ROUTES, LINK_STATE_FAILED,
376 LINK_STATE_LINGER));
377
378 link->route_messages --;
379
380 if (IN_SET(LINK_STATE_FAILED, LINK_STATE_LINGER))
381 return 1;
382
383 r = sd_rtnl_message_get_errno(m);
384 if (r < 0 && r != -EEXIST)
385 log_struct_link(LOG_WARNING, link,
386 "MESSAGE=%-*s: could not set route: %s",
387 IFNAMSIZ,
388 link->ifname, strerror(-r),
389 "ERRNO=%d", -r,
390 NULL);
391
392 /* we might have received an old reply after moving back to SETTING_ADDRESSES,
393 * ignore it */
394 if (link->route_messages == 0 && link->state == LINK_STATE_SETTING_ROUTES) {
395 log_debug_link(link, "routes set");
396 link_enter_configured(link);
397 }
398
399 return 1;
400 }
401
402 static int link_set_dhcp_routes(Link *link) {
403 struct sd_dhcp_route *static_routes;
404 size_t static_routes_size;
405 int r;
406 unsigned i;
407
408 assert(link);
409
410 r = sd_dhcp_lease_get_routes(link->dhcp_lease, &static_routes, &static_routes_size);
411 if (r < 0) {
412 if (r != -ENOENT)
413 log_warning_link(link, "DHCP error: could not get routes: %s", strerror(-r));
414 return r;
415 }
416
417 for (i = 0; i < static_routes_size; i++) {
418 _cleanup_route_free_ Route *route = NULL;
419
420 r = route_new_dynamic(&route);
421 if (r < 0) {
422 log_error_link(link, "Could not allocate route: %s",
423 strerror(-r));
424 return r;
425 }
426
427 route->family = AF_INET;
428 route->in_addr.in = static_routes[i].gw_addr;
429 route->dst_addr.in = static_routes[i].dst_addr;
430 route->dst_prefixlen = static_routes[i].dst_prefixlen;
431 route->metrics = DHCP_ROUTE_METRIC;
432
433 r = route_configure(route, link, &route_handler);
434 if (r < 0) {
435 log_warning_link(link,
436 "could not set host route: %s", strerror(-r));
437 return r;
438 }
439
440 link->route_messages ++;
441 }
442
443 return 0;
444 }
445
446 static int link_enter_set_routes(Link *link) {
447 Route *rt;
448 int r;
449
450 assert(link);
451 assert(link->network);
452 assert(link->state == LINK_STATE_SETTING_ADDRESSES);
453
454 link->state = LINK_STATE_SETTING_ROUTES;
455
456 if (!link->network->static_routes && !link->dhcp_lease &&
457 (!link->ipv4ll || ipv4ll_is_bound(link->ipv4ll) == false))
458 return link_enter_configured(link);
459
460 log_debug_link(link, "setting routes");
461
462 LIST_FOREACH(routes, rt, link->network->static_routes) {
463 r = route_configure(rt, link, &route_handler);
464 if (r < 0) {
465 log_warning_link(link,
466 "could not set routes: %s", strerror(-r));
467 link_enter_failed(link);
468 return r;
469 }
470
471 link->route_messages ++;
472 }
473
474 if (link->ipv4ll && !link->dhcp_lease) {
475 _cleanup_route_free_ Route *route = NULL;
476 struct in_addr addr;
477
478 r = sd_ipv4ll_get_address(link->ipv4ll, &addr);
479 if (r < 0 && r != -ENOENT) {
480 log_warning_link(link, "IPV4LL error: no address: %s",
481 strerror(-r));
482 return r;
483 }
484
485 if (r != -ENOENT) {
486 r = route_new_dynamic(&route);
487 if (r < 0) {
488 log_error_link(link, "Could not allocate route: %s",
489 strerror(-r));
490 return r;
491 }
492
493 route->family = AF_INET;
494 route->scope = RT_SCOPE_LINK;
495 route->metrics = IPV4LL_ROUTE_METRIC;
496
497 r = route_configure(route, link, &route_handler);
498 if (r < 0) {
499 log_warning_link(link,
500 "could not set routes: %s", strerror(-r));
501 link_enter_failed(link);
502 return r;
503 }
504
505 link->route_messages ++;
506 }
507 }
508
509 if (link->dhcp_lease) {
510 _cleanup_route_free_ Route *route = NULL;
511 _cleanup_route_free_ Route *route_gw = NULL;
512 struct in_addr gateway;
513
514 r = sd_dhcp_lease_get_router(link->dhcp_lease, &gateway);
515 if (r < 0 && r != -ENOENT) {
516 log_warning_link(link, "DHCP error: could not get gateway: %s",
517 strerror(-r));
518 return r;
519 }
520
521 if (r >= 0) {
522 r = route_new_dynamic(&route);
523 if (r < 0) {
524 log_error_link(link, "Could not allocate route: %s",
525 strerror(-r));
526 return r;
527 }
528
529 r = route_new_dynamic(&route_gw);
530 if (r < 0) {
531 log_error_link(link, "Could not allocate route: %s",
532 strerror(-r));
533 return r;
534 }
535
536 /* The dhcp netmask may mask out the gateway. Add an explicit
537 * route for the gw host so that we can route no matter the
538 * netmask or existing kernel route tables. */
539 route_gw->family = AF_INET;
540 route_gw->dst_addr.in = gateway;
541 route_gw->dst_prefixlen = 32;
542 route_gw->scope = RT_SCOPE_LINK;
543 route_gw->metrics = DHCP_ROUTE_METRIC;
544
545 r = route_configure(route_gw, link, &route_handler);
546 if (r < 0) {
547 log_warning_link(link,
548 "could not set host route: %s", strerror(-r));
549 return r;
550 }
551
552 link->route_messages ++;
553
554 route->family = AF_INET;
555 route->in_addr.in = gateway;
556 route->metrics = DHCP_ROUTE_METRIC;
557
558 r = route_configure(route, link, &route_handler);
559 if (r < 0) {
560 log_warning_link(link,
561 "could not set routes: %s", strerror(-r));
562 link_enter_failed(link);
563 return r;
564 }
565
566 link->route_messages ++;
567 }
568
569 if (link->network->dhcp_routes)
570 link_set_dhcp_routes(link);
571 }
572
573 if (link->route_messages == 0) {
574 link_enter_configured(link);
575 }
576
577 return 0;
578 }
579
580 static int route_drop_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
581 _cleanup_link_unref_ Link *link = userdata;
582 int r;
583
584 assert(m);
585 assert(link);
586 assert(link->ifname);
587
588 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
589 return 1;
590
591 r = sd_rtnl_message_get_errno(m);
592 if (r < 0 && r != -ESRCH)
593 log_struct_link(LOG_WARNING, link,
594 "MESSAGE=%-*s: could not drop route: %s",
595 IFNAMSIZ,
596 link->ifname, strerror(-r),
597 "ERRNO=%d", -r,
598 NULL);
599
600 return 1;
601 }
602
603 static int link_get_address_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
604 _cleanup_link_unref_ Link *link = userdata;
605 int r;
606
607 assert(rtnl);
608 assert(m);
609 assert(link);
610 assert(link->manager);
611
612 for (; m; m = sd_rtnl_message_next(m)) {
613 r = sd_rtnl_message_get_errno(m);
614 if (r < 0) {
615 log_debug_link(link, "getting address failed: %s", strerror(-r));
616 continue;
617 }
618
619 r = link_rtnl_process_address(rtnl, m, link->manager);
620 if (r < 0)
621 log_warning_link(link, "could not process address: %s", strerror(-r));
622 }
623
624 return 1;
625 }
626
627 static int address_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
628 _cleanup_link_unref_ Link *link = userdata;
629 int r;
630
631 assert(rtnl);
632 assert(m);
633 assert(link);
634 assert(link->ifname);
635 assert(link->addr_messages > 0);
636 assert(IN_SET(link->state, LINK_STATE_SETTING_ADDRESSES,
637 LINK_STATE_FAILED, LINK_STATE_LINGER));
638
639 link->addr_messages --;
640
641 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
642 return 1;
643
644 r = sd_rtnl_message_get_errno(m);
645 if (r < 0 && r != -EEXIST)
646 log_struct_link(LOG_WARNING, link,
647 "MESSAGE=%-*s: could not set address: %s",
648 IFNAMSIZ,
649 link->ifname, strerror(-r),
650 "ERRNO=%d", -r,
651 NULL);
652 else if (r >= 0) {
653 /* calling handler directly so take a ref */
654 link_ref(link);
655 link_get_address_handler(rtnl, m, link);
656 }
657
658 if (link->addr_messages == 0) {
659 log_debug_link(link, "addresses set");
660 link_enter_set_routes(link);
661 }
662
663 return 1;
664 }
665
666 static int link_enter_set_addresses(Link *link) {
667 Address *ad;
668 int r;
669 uint32_t lifetime = CACHE_INFO_INFINITY_LIFE_TIME;
670
671 assert(link);
672 assert(link->network);
673 assert(link->state != _LINK_STATE_INVALID);
674
675 link->state = LINK_STATE_SETTING_ADDRESSES;
676
677 if (!link->network->static_addresses && !link->dhcp_lease &&
678 (!link->ipv4ll || ipv4ll_is_bound(link->ipv4ll) == false))
679 return link_enter_set_routes(link);
680
681 log_debug_link(link, "setting addresses");
682
683 LIST_FOREACH(addresses, ad, link->network->static_addresses) {
684 r = address_configure(ad, link, &address_handler);
685 if (r < 0) {
686 log_warning_link(link,
687 "could not set addresses: %s", strerror(-r));
688 link_enter_failed(link);
689 return r;
690 }
691
692 link->addr_messages ++;
693 }
694
695 if (link->ipv4ll && !link->dhcp_lease) {
696 _cleanup_address_free_ Address *ll_addr = NULL;
697 struct in_addr addr;
698
699 r = sd_ipv4ll_get_address(link->ipv4ll, &addr);
700 if (r < 0 && r != -ENOENT) {
701 log_warning_link(link, "IPV4LL error: no address: %s",
702 strerror(-r));
703 return r;
704 }
705
706 if (r != -ENOENT) {
707 r = address_new_dynamic(&ll_addr);
708 if (r < 0) {
709 log_error_link(link, "Could not allocate address: %s", strerror(-r));
710 return r;
711 }
712
713 ll_addr->family = AF_INET;
714 ll_addr->in_addr.in = addr;
715 ll_addr->prefixlen = 16;
716 ll_addr->broadcast.s_addr = ll_addr->in_addr.in.s_addr | htonl(0xfffffffflu >> ll_addr->prefixlen);
717 ll_addr->scope = RT_SCOPE_LINK;
718
719 r = address_configure(ll_addr, link, &address_handler);
720 if (r < 0) {
721 log_warning_link(link,
722 "could not set addresses: %s", strerror(-r));
723 link_enter_failed(link);
724 return r;
725 }
726
727 link->addr_messages ++;
728 }
729 }
730
731 if (link->dhcp_lease) {
732 _cleanup_address_free_ Address *address = NULL;
733 struct in_addr addr;
734 struct in_addr netmask;
735 unsigned prefixlen;
736
737 r = sd_dhcp_lease_get_address(link->dhcp_lease, &addr);
738 if (r < 0) {
739 log_warning_link(link, "DHCP error: no address: %s",
740 strerror(-r));
741 return r;
742 }
743
744 if (!link->network->dhcp_critical) {
745 r = sd_dhcp_lease_get_lifetime(link->dhcp_lease,
746 &lifetime);
747 if (r < 0) {
748 log_warning_link(link, "DHCP error: no lifetime: %s",
749 strerror(-r));
750 return r;
751 }
752 }
753
754 r = sd_dhcp_lease_get_netmask(link->dhcp_lease, &netmask);
755 if (r < 0) {
756 log_warning_link(link, "DHCP error: no netmask: %s",
757 strerror(-r));
758 return r;
759 }
760
761 prefixlen = net_netmask_to_prefixlen(&netmask);
762
763 r = address_new_dynamic(&address);
764 if (r < 0) {
765 log_error_link(link, "Could not allocate address: %s",
766 strerror(-r));
767 return r;
768 }
769
770 address->family = AF_INET;
771 address->in_addr.in = addr;
772 address->cinfo.ifa_prefered = lifetime;
773 address->cinfo.ifa_valid = lifetime;
774 address->prefixlen = prefixlen;
775 address->broadcast.s_addr = addr.s_addr | ~netmask.s_addr;
776
777 /* use update rather than configure so that we will update the lifetime
778 of an existing address if it has already been configured */
779 r = address_update(address, link, &address_handler);
780 if (r < 0) {
781 log_warning_link(link,
782 "could not set addresses: %s", strerror(-r));
783 link_enter_failed(link);
784 return r;
785 }
786
787 link->addr_messages ++;
788 }
789
790 return 0;
791 }
792
793 static int address_update_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
794 _cleanup_link_unref_ Link *link = userdata;
795 int r;
796
797 assert(m);
798 assert(link);
799 assert(link->ifname);
800
801 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
802 return 1;
803
804 r = sd_rtnl_message_get_errno(m);
805 if (r < 0 && r != -ENOENT)
806 log_struct_link(LOG_WARNING, link,
807 "MESSAGE=%-*s: could not update address: %s",
808 IFNAMSIZ,
809 link->ifname, strerror(-r),
810 "ERRNO=%d", -r,
811 NULL);
812
813 return 1;
814 }
815
816 static int address_drop_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
817 _cleanup_link_unref_ Link *link = userdata;
818 int r;
819
820 assert(m);
821 assert(link);
822 assert(link->ifname);
823
824 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
825 return 1;
826
827 r = sd_rtnl_message_get_errno(m);
828 if (r < 0 && r != -EADDRNOTAVAIL)
829 log_struct_link(LOG_WARNING, link,
830 "MESSAGE=%-*s: could not drop address: %s",
831 IFNAMSIZ,
832 link->ifname, strerror(-r),
833 "ERRNO=%d", -r,
834 NULL);
835
836 return 1;
837 }
838
839 static int set_hostname_handler(sd_bus *bus, sd_bus_message *m, void *userdata, sd_bus_error *ret_error) {
840 _cleanup_link_unref_ Link *link = userdata;
841 int r;
842
843 assert(link);
844
845 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
846 return 1;
847
848 r = sd_bus_message_get_errno(m);
849 if (r < 0)
850 log_warning_link(link, "Could not set hostname: %s", strerror(-r));
851
852 return 1;
853 }
854
855 static int link_set_hostname(Link *link, const char *hostname) {
856 _cleanup_bus_message_unref_ sd_bus_message *m = NULL;
857 int r = 0;
858
859 assert(link);
860 assert(link->manager);
861 assert(hostname);
862
863 log_debug_link(link, "Setting transient hostname: '%s'", hostname);
864
865 if (!link->manager->bus) { /* TODO: replace by assert when we can rely on kdbus */
866 log_info_link(link, "Not connected to system bus, ignoring transient hostname.");
867 return 0;
868 }
869
870 r = sd_bus_message_new_method_call(
871 link->manager->bus,
872 &m,
873 "org.freedesktop.hostname1",
874 "/org/freedesktop/hostname1",
875 "org.freedesktop.hostname1",
876 "SetHostname");
877 if (r < 0)
878 return r;
879
880 r = sd_bus_message_append(m, "sb", hostname, false);
881 if (r < 0)
882 return r;
883
884 r = sd_bus_call_async(link->manager->bus, NULL, m, set_hostname_handler, link, 0);
885 if (r < 0) {
886 log_error_link(link, "Could not set transient hostname: %s", strerror(-r));
887 return r;
888 }
889
890 link_ref(link);
891
892 return 0;
893 }
894
895 static int set_mtu_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
896 _cleanup_link_unref_ Link *link = userdata;
897 int r;
898
899 assert(m);
900 assert(link);
901 assert(link->ifname);
902
903 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
904 return 1;
905
906 r = sd_rtnl_message_get_errno(m);
907 if (r < 0)
908 log_struct_link(LOG_WARNING, link,
909 "MESSAGE=%-*s: could not set MTU: %s",
910 IFNAMSIZ, link->ifname, strerror(-r),
911 "ERRNO=%d", -r,
912 NULL);
913
914 return 1;
915 }
916
917 static int link_set_mtu(Link *link, uint32_t mtu) {
918 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
919 int r;
920
921 assert(link);
922 assert(link->manager);
923 assert(link->manager->rtnl);
924
925 log_debug_link(link, "setting MTU: %" PRIu32, mtu);
926
927 r = sd_rtnl_message_new_link(link->manager->rtnl, &req,
928 RTM_SETLINK, link->ifindex);
929 if (r < 0) {
930 log_error_link(link, "Could not allocate RTM_SETLINK message");
931 return r;
932 }
933
934 r = sd_rtnl_message_append_u32(req, IFLA_MTU, mtu);
935 if (r < 0) {
936 log_error_link(link, "Could not append MTU: %s", strerror(-r));
937 return r;
938 }
939
940 r = sd_rtnl_call_async(link->manager->rtnl, req, set_mtu_handler, link, 0, NULL);
941 if (r < 0) {
942 log_error_link(link,
943 "Could not send rtnetlink message: %s", strerror(-r));
944 return r;
945 }
946
947 link_ref(link);
948
949 return 0;
950 }
951
952 static int dhcp_lease_lost(Link *link) {
953 _cleanup_address_free_ Address *address = NULL;
954 struct in_addr addr;
955 struct in_addr netmask;
956 struct in_addr gateway;
957 unsigned prefixlen;
958 unsigned i;
959 int r;
960
961 assert(link);
962 assert(link->dhcp_lease);
963
964 log_warning_link(link, "DHCP lease lost");
965
966 if (link->network->dhcp_routes) {
967 struct sd_dhcp_route *routes;
968 size_t routes_size;
969
970 r = sd_dhcp_lease_get_routes(link->dhcp_lease, &routes, &routes_size);
971 if (r >= 0) {
972 for (i = 0; i < routes_size; i++) {
973 _cleanup_route_free_ Route *route = NULL;
974
975 r = route_new_dynamic(&route);
976 if (r >= 0) {
977 route->family = AF_INET;
978 route->in_addr.in = routes[i].gw_addr;
979 route->dst_addr.in = routes[i].dst_addr;
980 route->dst_prefixlen = routes[i].dst_prefixlen;
981
982 route_drop(route, link, &route_drop_handler);
983 }
984 }
985 }
986 }
987
988 r = address_new_dynamic(&address);
989 if (r >= 0) {
990 r = sd_dhcp_lease_get_router(link->dhcp_lease, &gateway);
991 if (r >= 0) {
992 _cleanup_route_free_ Route *route_gw = NULL;
993 _cleanup_route_free_ Route *route = NULL;
994
995 r = route_new_dynamic(&route_gw);
996 if (r >= 0) {
997 route_gw->family = AF_INET;
998 route_gw->dst_addr.in = gateway;
999 route_gw->dst_prefixlen = 32;
1000 route_gw->scope = RT_SCOPE_LINK;
1001
1002 route_drop(route_gw, link, &route_drop_handler);
1003 }
1004
1005 r = route_new_dynamic(&route);
1006 if (r >= 0) {
1007 route->family = AF_INET;
1008 route->in_addr.in = gateway;
1009
1010 route_drop(route, link, &route_drop_handler);
1011 }
1012 }
1013
1014 sd_dhcp_lease_get_address(link->dhcp_lease, &addr);
1015 sd_dhcp_lease_get_netmask(link->dhcp_lease, &netmask);
1016 prefixlen = net_netmask_to_prefixlen(&netmask);
1017
1018 address->family = AF_INET;
1019 address->in_addr.in = addr;
1020 address->prefixlen = prefixlen;
1021
1022 address_drop(address, link, &address_drop_handler);
1023 }
1024
1025 if (link->network->dhcp_mtu) {
1026 uint16_t mtu;
1027
1028 r = sd_dhcp_lease_get_mtu(link->dhcp_lease, &mtu);
1029 if (r >= 0 && link->original_mtu != mtu) {
1030 r = link_set_mtu(link, link->original_mtu);
1031 if (r < 0) {
1032 log_warning_link(link, "DHCP error: could not reset MTU");
1033 link_enter_failed(link);
1034 return r;
1035 }
1036 }
1037 }
1038
1039 if (link->network->dhcp_hostname) {
1040 const char *hostname = NULL;
1041
1042 r = sd_dhcp_lease_get_hostname(link->dhcp_lease, &hostname);
1043 if (r >= 0 && hostname) {
1044 r = link_set_hostname(link, "");
1045 if (r < 0)
1046 log_error_link(link, "Failed to reset transient hostname");
1047 }
1048 }
1049
1050 link->dhcp_lease = sd_dhcp_lease_unref(link->dhcp_lease);
1051
1052 return 0;
1053 }
1054
1055 static int dhcp_lease_renew(sd_dhcp_client *client, Link *link) {
1056 sd_dhcp_lease *lease;
1057 int r;
1058
1059 r = sd_dhcp_client_get_lease(client, &lease);
1060 if (r < 0) {
1061 log_warning_link(link, "DHCP error: no lease %s",
1062 strerror(-r));
1063 return r;
1064 }
1065
1066 sd_dhcp_lease_unref(link->dhcp_lease);
1067 link->dhcp_lease = lease;
1068
1069 link_enter_set_addresses(link);
1070
1071 return 0;
1072 }
1073
1074 static int dhcp_lease_acquired(sd_dhcp_client *client, Link *link) {
1075 sd_dhcp_lease *lease;
1076 struct in_addr address;
1077 struct in_addr netmask;
1078 struct in_addr gateway;
1079 unsigned prefixlen;
1080 int r;
1081
1082 assert(client);
1083 assert(link);
1084
1085 r = sd_dhcp_client_get_lease(client, &lease);
1086 if (r < 0) {
1087 log_warning_link(link, "DHCP error: no lease: %s",
1088 strerror(-r));
1089 return r;
1090 }
1091
1092 r = sd_dhcp_lease_get_address(lease, &address);
1093 if (r < 0) {
1094 log_warning_link(link, "DHCP error: no address: %s",
1095 strerror(-r));
1096 return r;
1097 }
1098
1099 r = sd_dhcp_lease_get_netmask(lease, &netmask);
1100 if (r < 0) {
1101 log_warning_link(link, "DHCP error: no netmask: %s",
1102 strerror(-r));
1103 return r;
1104 }
1105
1106 prefixlen = net_netmask_to_prefixlen(&netmask);
1107
1108 r = sd_dhcp_lease_get_router(lease, &gateway);
1109 if (r < 0 && r != -ENOENT) {
1110 log_warning_link(link, "DHCP error: could not get gateway: %s",
1111 strerror(-r));
1112 return r;
1113 }
1114
1115 if (r >= 0)
1116 log_struct_link(LOG_INFO, link,
1117 "MESSAGE=%-*s: DHCPv4 address %u.%u.%u.%u/%u via %u.%u.%u.%u",
1118 IFNAMSIZ,
1119 link->ifname,
1120 ADDRESS_FMT_VAL(address),
1121 prefixlen,
1122 ADDRESS_FMT_VAL(gateway),
1123 "ADDRESS=%u.%u.%u.%u",
1124 ADDRESS_FMT_VAL(address),
1125 "PREFIXLEN=%u",
1126 prefixlen,
1127 "GATEWAY=%u.%u.%u.%u",
1128 ADDRESS_FMT_VAL(gateway),
1129 NULL);
1130 else
1131 log_struct_link(LOG_INFO, link,
1132 "MESSAGE=%-*s: DHCPv4 address %u.%u.%u.%u/%u",
1133 IFNAMSIZ,
1134 link->ifname,
1135 ADDRESS_FMT_VAL(address),
1136 prefixlen,
1137 "ADDRESS=%u.%u.%u.%u",
1138 ADDRESS_FMT_VAL(address),
1139 "PREFIXLEN=%u",
1140 prefixlen,
1141 NULL);
1142
1143 link->dhcp_lease = lease;
1144
1145 if (link->network->dhcp_mtu) {
1146 uint16_t mtu;
1147
1148 r = sd_dhcp_lease_get_mtu(lease, &mtu);
1149 if (r >= 0) {
1150 r = link_set_mtu(link, mtu);
1151 if (r < 0)
1152 log_error_link(link, "Failed to set MTU "
1153 "to %" PRIu16, mtu);
1154 }
1155 }
1156
1157 if (link->network->dhcp_hostname) {
1158 const char *hostname;
1159
1160 r = sd_dhcp_lease_get_hostname(lease, &hostname);
1161 if (r >= 0) {
1162 r = link_set_hostname(link, hostname);
1163 if (r < 0)
1164 log_error_link(link, "Failed to set transient hostname "
1165 "to '%s'", hostname);
1166 }
1167 }
1168
1169 link_enter_set_addresses(link);
1170
1171 return 0;
1172 }
1173
1174 static void dhcp_handler(sd_dhcp_client *client, int event, void *userdata) {
1175 Link *link = userdata;
1176 int r = 0;
1177
1178 assert(link);
1179 assert(link->network);
1180 assert(link->manager);
1181
1182 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1183 return;
1184
1185 switch (event) {
1186 case DHCP_EVENT_NO_LEASE:
1187 log_debug_link(link, "IP address in use.");
1188 break;
1189 case DHCP_EVENT_EXPIRED:
1190 case DHCP_EVENT_STOP:
1191 case DHCP_EVENT_IP_CHANGE:
1192 if (link->network->dhcp_critical) {
1193 log_error_link(link, "DHCPv4 connection considered system critical, "
1194 "ignoring request to reconfigure it.");
1195 return;
1196 }
1197
1198 if (link->dhcp_lease) {
1199 r = dhcp_lease_lost(link);
1200 if (r < 0) {
1201 link_enter_failed(link);
1202 return;
1203 }
1204 }
1205
1206 if (event == DHCP_EVENT_IP_CHANGE) {
1207 r = dhcp_lease_acquired(client, link);
1208 if (r < 0) {
1209 link_enter_failed(link);
1210 return;
1211 }
1212 }
1213
1214 if (event == DHCP_EVENT_EXPIRED && link->network->ipv4ll) {
1215 if (!sd_ipv4ll_is_running(link->ipv4ll))
1216 r = sd_ipv4ll_start(link->ipv4ll);
1217 else if (ipv4ll_is_bound(link->ipv4ll))
1218 r = ipv4ll_address_update(link, false);
1219 if (r < 0) {
1220 link_enter_failed(link);
1221 return;
1222 }
1223 }
1224
1225 break;
1226 case DHCP_EVENT_RENEW:
1227 r = dhcp_lease_renew(client, link);
1228 if (r < 0) {
1229 link_enter_failed(link);
1230 return;
1231 }
1232 break;
1233 case DHCP_EVENT_IP_ACQUIRE:
1234 r = dhcp_lease_acquired(client, link);
1235 if (r < 0) {
1236 link_enter_failed(link);
1237 return;
1238 }
1239 if (link->ipv4ll) {
1240 if (ipv4ll_is_bound(link->ipv4ll))
1241 r = ipv4ll_address_update(link, true);
1242 else
1243 r = sd_ipv4ll_stop(link->ipv4ll);
1244 if (r < 0) {
1245 link_enter_failed(link);
1246 return;
1247 }
1248 }
1249 break;
1250 default:
1251 if (event < 0)
1252 log_warning_link(link, "DHCP error: client failed: %s", strerror(-event));
1253 else
1254 log_warning_link(link, "DHCP unknown event: %d", event);
1255 break;
1256 }
1257
1258 return;
1259 }
1260
1261 static int ipv4ll_address_update(Link *link, bool deprecate) {
1262 int r;
1263 struct in_addr addr;
1264
1265 assert(link);
1266
1267 r = sd_ipv4ll_get_address(link->ipv4ll, &addr);
1268 if (r >= 0) {
1269 _cleanup_address_free_ Address *address = NULL;
1270
1271 log_debug_link(link, "IPv4 link-local %s %u.%u.%u.%u",
1272 deprecate ? "deprecate" : "approve",
1273 ADDRESS_FMT_VAL(addr));
1274
1275 r = address_new_dynamic(&address);
1276 if (r < 0) {
1277 log_error_link(link, "Could not allocate address: %s", strerror(-r));
1278 return r;
1279 }
1280
1281 address->family = AF_INET;
1282 address->in_addr.in = addr;
1283 address->prefixlen = 16;
1284 address->scope = RT_SCOPE_LINK;
1285 address->cinfo.ifa_prefered = deprecate ? 0 : CACHE_INFO_INFINITY_LIFE_TIME;
1286 address->broadcast.s_addr = address->in_addr.in.s_addr | htonl(0xfffffffflu >> address->prefixlen);
1287
1288 address_update(address, link, &address_update_handler);
1289 }
1290
1291 return 0;
1292
1293 }
1294
1295 static int ipv4ll_address_lost(Link *link) {
1296 int r;
1297 struct in_addr addr;
1298
1299 assert(link);
1300
1301 r = sd_ipv4ll_get_address(link->ipv4ll, &addr);
1302 if (r >= 0) {
1303 _cleanup_address_free_ Address *address = NULL;
1304 _cleanup_route_free_ Route *route = NULL;
1305
1306 log_debug_link(link, "IPv4 link-local release %u.%u.%u.%u",
1307 ADDRESS_FMT_VAL(addr));
1308
1309 r = address_new_dynamic(&address);
1310 if (r < 0) {
1311 log_error_link(link, "Could not allocate address: %s", strerror(-r));
1312 return r;
1313 }
1314
1315 address->family = AF_INET;
1316 address->in_addr.in = addr;
1317 address->prefixlen = 16;
1318 address->scope = RT_SCOPE_LINK;
1319
1320 address_drop(address, link, &address_drop_handler);
1321
1322 r = route_new_dynamic(&route);
1323 if (r < 0) {
1324 log_error_link(link, "Could not allocate route: %s",
1325 strerror(-r));
1326 return r;
1327 }
1328
1329 route->family = AF_INET;
1330 route->scope = RT_SCOPE_LINK;
1331 route->metrics = 99;
1332
1333 route_drop(route, link, &route_drop_handler);
1334 }
1335
1336 return 0;
1337 }
1338
1339 static bool ipv4ll_is_bound(sd_ipv4ll *ll) {
1340 int r;
1341 struct in_addr addr;
1342
1343 assert(ll);
1344
1345 r = sd_ipv4ll_get_address(ll, &addr);
1346 if (r < 0)
1347 return false;
1348 return true;
1349 }
1350
1351 static int ipv4ll_address_claimed(sd_ipv4ll *ll, Link *link) {
1352 struct in_addr address;
1353 int r;
1354
1355 assert(ll);
1356 assert(link);
1357
1358 r = sd_ipv4ll_get_address(ll, &address);
1359 if (r < 0)
1360 return r;
1361
1362 log_struct_link(LOG_INFO, link,
1363 "MESSAGE=%-*s: IPv4 link-local address %u.%u.%u.%u",
1364 IFNAMSIZ,
1365 link->ifname,
1366 ADDRESS_FMT_VAL(address),
1367 NULL);
1368
1369 link_enter_set_addresses(link);
1370
1371 return 0;
1372 }
1373
1374 static void ipv4ll_handler(sd_ipv4ll *ll, int event, void *userdata){
1375 Link *link = userdata;
1376 int r;
1377
1378 assert(link);
1379 assert(link->network);
1380 assert(link->manager);
1381
1382 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1383 return;
1384
1385 switch(event) {
1386 case IPV4LL_EVENT_STOP:
1387 case IPV4LL_EVENT_CONFLICT:
1388 r = ipv4ll_address_lost(link);
1389 if (r < 0) {
1390 link_enter_failed(link);
1391 return;
1392 }
1393 break;
1394 case IPV4LL_EVENT_BIND:
1395 r = ipv4ll_address_claimed(ll, link);
1396 if (r < 0) {
1397 link_enter_failed(link);
1398 return;
1399 }
1400 break;
1401 default:
1402 if (event < 0)
1403 log_warning_link(link, "IPv4 link-local error: %s", strerror(-event));
1404 else
1405 log_warning_link(link, "IPv4 link-local unknown event: %d", event);
1406 break;
1407 }
1408 }
1409
1410 static void dhcp6_handler(sd_dhcp6_client *client, int event, void *userdata) {
1411 Link *link = userdata;
1412
1413 assert(link);
1414 assert(link->network);
1415 assert(link->manager);
1416
1417 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1418 return;
1419
1420 switch(event) {
1421 case DHCP6_EVENT_STOP:
1422 case DHCP6_EVENT_RESEND_EXPIRE:
1423 case DHCP6_EVENT_RETRANS_MAX:
1424 case DHCP6_EVENT_IP_ACQUIRE:
1425 log_debug_link(link, "DHCPv6 event %d", event);
1426
1427 break;
1428
1429 default:
1430 if (event < 0)
1431 log_warning_link(link, "DHCPv6 error: %s",
1432 strerror(-event));
1433 else
1434 log_warning_link(link, "DHCPv6 unknown event: %d",
1435 event);
1436 return;
1437 }
1438 }
1439
1440 static void icmp6_router_handler(sd_icmp6_nd *nd, int event, void *userdata) {
1441 Link *link = userdata;
1442 int r;
1443
1444 assert(link);
1445 assert(link->network);
1446 assert(link->manager);
1447
1448 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1449 return;
1450
1451 switch(event) {
1452 case ICMP6_EVENT_ROUTER_ADVERTISMENT_NONE:
1453 case ICMP6_EVENT_ROUTER_ADVERTISMENT_OTHER:
1454 return;
1455
1456 case ICMP6_EVENT_ROUTER_ADVERTISMENT_TIMEOUT:
1457 case ICMP6_EVENT_ROUTER_ADVERTISMENT_MANAGED:
1458 break;
1459
1460 default:
1461 if (event < 0)
1462 log_warning_link(link, "ICMPv6 error: %s",
1463 strerror(-event));
1464 else
1465 log_warning_link(link, "ICMPv6 unknown event: %d",
1466 event);
1467
1468 return;
1469 }
1470
1471 if (link->dhcp6_client)
1472 return;
1473
1474 r = sd_dhcp6_client_new(&link->dhcp6_client);
1475 if (r < 0)
1476 return;
1477
1478 r = sd_dhcp6_client_attach_event(link->dhcp6_client, NULL, 0);
1479 if (r < 0) {
1480 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
1481 return;
1482 }
1483
1484 r = sd_dhcp6_client_set_mac(link->dhcp6_client, &link->mac);
1485 if (r < 0) {
1486 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
1487 return;
1488 }
1489
1490 r = sd_dhcp6_client_set_index(link->dhcp6_client, link->ifindex);
1491 if (r < 0) {
1492 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
1493 return;
1494 }
1495
1496 r = sd_dhcp6_client_set_callback(link->dhcp6_client, dhcp6_handler,
1497 link);
1498 if (r < 0) {
1499 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
1500 return;
1501 }
1502
1503 r = sd_dhcp6_client_start(link->dhcp6_client);
1504 if (r < 0)
1505 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
1506 }
1507
1508 static int link_acquire_conf(Link *link) {
1509 int r;
1510
1511 assert(link);
1512 assert(link->network);
1513 assert(link->manager);
1514 assert(link->manager->event);
1515
1516 if (link->network->ipv4ll) {
1517 assert(link->ipv4ll);
1518
1519 log_debug_link(link, "acquiring IPv4 link-local address");
1520
1521 r = sd_ipv4ll_start(link->ipv4ll);
1522 if (r < 0) {
1523 log_warning_link(link, "could not acquire IPv4 "
1524 "link-local address");
1525 return r;
1526 }
1527 }
1528
1529 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V4)) {
1530 assert(link->dhcp_client);
1531
1532 log_debug_link(link, "acquiring DHCPv4 lease");
1533
1534 r = sd_dhcp_client_start(link->dhcp_client);
1535 if (r < 0) {
1536 log_warning_link(link, "could not acquire DHCPv4 "
1537 "lease");
1538 return r;
1539 }
1540 }
1541
1542 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V6)) {
1543 assert(link->icmp6_router_discovery);
1544
1545 log_debug_link(link, "discovering IPv6 routers");
1546
1547 r = sd_icmp6_router_solicitation_start(link->icmp6_router_discovery);
1548 if (r < 0) {
1549 log_warning_link(link, "could not start IPv6 router discovery");
1550 return r;
1551 }
1552 }
1553
1554 return 0;
1555 }
1556
1557 bool link_has_carrier(unsigned flags, uint8_t operstate) {
1558 /* see Documentation/networking/operstates.txt in the kernel sources */
1559
1560 if (operstate == IF_OPER_UP)
1561 return true;
1562
1563 if (operstate == IF_OPER_UNKNOWN)
1564 /* operstate may not be implemented, so fall back to flags */
1565 if ((flags & IFF_LOWER_UP) && !(flags & IFF_DORMANT))
1566 return true;
1567
1568 return false;
1569 }
1570
1571 #define FLAG_STRING(string, flag, old, new) \
1572 (((old ^ new) & flag) \
1573 ? ((old & flag) ? (" -" string) : (" +" string)) \
1574 : "")
1575
1576 static int link_update_flags(Link *link, sd_rtnl_message *m) {
1577 unsigned flags, unknown_flags_added, unknown_flags_removed, unknown_flags;
1578 uint8_t operstate;
1579 bool carrier_gained = false, carrier_lost = false;
1580 int r;
1581
1582 assert(link);
1583
1584 r = sd_rtnl_message_link_get_flags(m, &flags);
1585 if (r < 0) {
1586 log_warning_link(link, "Could not get link flags");
1587 return r;
1588 }
1589
1590 r = sd_rtnl_message_read_u8(m, IFLA_OPERSTATE, &operstate);
1591 if (r < 0)
1592 /* if we got a message without operstate, take it to mean
1593 the state was unchanged */
1594 operstate = link->kernel_operstate;
1595
1596 if ((link->flags == flags) && (link->kernel_operstate == operstate))
1597 return 0;
1598
1599 if (link->flags != flags) {
1600 log_debug_link(link, "flags change:%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s",
1601 FLAG_STRING("LOOPBACK", IFF_LOOPBACK, link->flags, flags),
1602 FLAG_STRING("MASTER", IFF_MASTER, link->flags, flags),
1603 FLAG_STRING("SLAVE", IFF_SLAVE, link->flags, flags),
1604 FLAG_STRING("UP", IFF_UP, link->flags, flags),
1605 FLAG_STRING("DORMANT", IFF_DORMANT, link->flags, flags),
1606 FLAG_STRING("LOWER_UP", IFF_LOWER_UP, link->flags, flags),
1607 FLAG_STRING("RUNNING", IFF_RUNNING, link->flags, flags),
1608 FLAG_STRING("MULTICAST", IFF_MULTICAST, link->flags, flags),
1609 FLAG_STRING("BROADCAST", IFF_BROADCAST, link->flags, flags),
1610 FLAG_STRING("POINTOPOINT", IFF_POINTOPOINT, link->flags, flags),
1611 FLAG_STRING("PROMISC", IFF_PROMISC, link->flags, flags),
1612 FLAG_STRING("ALLMULTI", IFF_ALLMULTI, link->flags, flags),
1613 FLAG_STRING("PORTSEL", IFF_PORTSEL, link->flags, flags),
1614 FLAG_STRING("AUTOMEDIA", IFF_AUTOMEDIA, link->flags, flags),
1615 FLAG_STRING("DYNAMIC", IFF_DYNAMIC, link->flags, flags),
1616 FLAG_STRING("NOARP", IFF_NOARP, link->flags, flags),
1617 FLAG_STRING("NOTRAILERS", IFF_NOTRAILERS, link->flags, flags),
1618 FLAG_STRING("DEBUG", IFF_DEBUG, link->flags, flags),
1619 FLAG_STRING("ECHO", IFF_ECHO, link->flags, flags));
1620
1621 unknown_flags = ~(IFF_LOOPBACK | IFF_MASTER | IFF_SLAVE | IFF_UP |
1622 IFF_DORMANT | IFF_LOWER_UP | IFF_RUNNING |
1623 IFF_MULTICAST | IFF_BROADCAST | IFF_POINTOPOINT |
1624 IFF_PROMISC | IFF_ALLMULTI | IFF_PORTSEL |
1625 IFF_AUTOMEDIA | IFF_DYNAMIC | IFF_NOARP |
1626 IFF_NOTRAILERS | IFF_DEBUG | IFF_ECHO);
1627 unknown_flags_added = ((link->flags ^ flags) & flags & unknown_flags);
1628 unknown_flags_removed = ((link->flags ^ flags) & link->flags & unknown_flags);
1629
1630 /* link flags are currently at most 18 bits, let's align to printing 20 */
1631 if (unknown_flags_added)
1632 log_debug_link(link, "unknown link flags gained: %#.5x (ignoring)",
1633 unknown_flags_added);
1634
1635 if (unknown_flags_removed)
1636 log_debug_link(link, "unknown link flags lost: %#.5x (ignoring)",
1637 unknown_flags_removed);
1638 }
1639
1640 carrier_gained = !link_has_carrier(link->flags, link->kernel_operstate) &&
1641 link_has_carrier(flags, operstate);
1642 carrier_lost = link_has_carrier(link->flags, link->kernel_operstate) &&
1643 !link_has_carrier(flags, operstate);
1644
1645 link->flags = flags;
1646 link->kernel_operstate = operstate;
1647
1648 link_save(link);
1649
1650 if (link->state == LINK_STATE_FAILED ||
1651 link->state == LINK_STATE_UNMANAGED)
1652 return 0;
1653
1654 if (carrier_gained) {
1655 log_info_link(link, "gained carrier");
1656
1657 if (link->network) {
1658 r = link_acquire_conf(link);
1659 if (r < 0) {
1660 link_enter_failed(link);
1661 return r;
1662 }
1663 }
1664 } else if (carrier_lost) {
1665 log_info_link(link, "lost carrier");
1666
1667 r = link_stop_clients(link);
1668 if (r < 0) {
1669 link_enter_failed(link);
1670 return r;
1671 }
1672 }
1673
1674 return 0;
1675 }
1676
1677 static int link_up_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
1678 _cleanup_link_unref_ Link *link = userdata;
1679 int r;
1680
1681 assert(link);
1682
1683 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1684 return 1;
1685
1686 r = sd_rtnl_message_get_errno(m);
1687 if (r < 0) {
1688 /* we warn but don't fail the link, as it may
1689 be brought up later */
1690 log_struct_link(LOG_WARNING, link,
1691 "MESSAGE=%-*s: could not bring up interface: %s",
1692 IFNAMSIZ,
1693 link->ifname, strerror(-r),
1694 "ERRNO=%d", -r,
1695 NULL);
1696 }
1697
1698 return 1;
1699 }
1700
1701 static int link_up(Link *link) {
1702 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
1703 int r;
1704
1705 assert(link);
1706 assert(link->manager);
1707 assert(link->manager->rtnl);
1708
1709 log_debug_link(link, "bringing link up");
1710
1711 r = sd_rtnl_message_new_link(link->manager->rtnl, &req,
1712 RTM_SETLINK, link->ifindex);
1713 if (r < 0) {
1714 log_error_link(link, "Could not allocate RTM_SETLINK message");
1715 return r;
1716 }
1717
1718 r = sd_rtnl_message_link_set_flags(req, IFF_UP, IFF_UP);
1719 if (r < 0) {
1720 log_error_link(link, "Could not set link flags: %s", strerror(-r));
1721 return r;
1722 }
1723
1724 r = sd_rtnl_call_async(link->manager->rtnl, req, link_up_handler, link, 0, NULL);
1725 if (r < 0) {
1726 log_error_link(link,
1727 "Could not send rtnetlink message: %s", strerror(-r));
1728 return r;
1729 }
1730
1731 link_ref(link);
1732
1733 return 0;
1734 }
1735
1736 static int link_joined(Link *link) {
1737 int r;
1738
1739 assert(link);
1740 assert(link->state == LINK_STATE_ENSLAVING);
1741 assert(link->network);
1742
1743 log_debug_link(link, "joined netdev");
1744
1745 if (!(link->flags & IFF_UP)) {
1746 r = link_up(link);
1747 if (r < 0) {
1748 link_enter_failed(link);
1749 return r;
1750 }
1751 }
1752
1753 return link_enter_set_addresses(link);
1754 }
1755
1756 static int netdev_join_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
1757 _cleanup_link_unref_ Link *link = userdata;
1758 int r;
1759
1760 assert(link);
1761 assert(IN_SET(link->state, LINK_STATE_ENSLAVING, LINK_STATE_FAILED,
1762 LINK_STATE_LINGER));
1763 assert(link->network);
1764
1765 link->enslaving --;
1766
1767 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1768 return 1;
1769
1770 r = sd_rtnl_message_get_errno(m);
1771 if (r < 0 && r != -EEXIST) {
1772 log_struct_link(LOG_ERR, link,
1773 "MESSAGE=%-*s: could not join netdev: %s",
1774 IFNAMSIZ,
1775 link->ifname, strerror(-r),
1776 "ERRNO=%d", -r,
1777 NULL);
1778 link_enter_failed(link);
1779 return 1;
1780 }
1781
1782 if (link->enslaving <= 0)
1783 link_joined(link);
1784
1785 return 1;
1786 }
1787
1788 static int link_enter_join_netdev(Link *link) {
1789 NetDev *vlan, *macvlan, *vxlan;
1790 Iterator i;
1791 int r;
1792
1793 assert(link);
1794 assert(link->network);
1795 assert(link->state == LINK_STATE_INITIALIZING);
1796
1797 link->state = LINK_STATE_ENSLAVING;
1798
1799 link_save(link);
1800
1801 if (!link->network->bridge &&
1802 !link->network->bond &&
1803 !link->network->tunnel &&
1804 hashmap_isempty(link->network->vlans) &&
1805 hashmap_isempty(link->network->macvlans) &&
1806 hashmap_isempty(link->network->vxlans))
1807 return link_joined(link);
1808
1809 if (link->network->bond) {
1810 log_struct_link(LOG_DEBUG, link,
1811 "MESSAGE=%-*s: enslaving by '%s'",
1812 IFNAMSIZ,
1813 link->ifname, link->network->bond->ifname,
1814 NETDEV(link->network->bond),
1815 NULL);
1816
1817 r = netdev_join(link->network->bond, link, &netdev_join_handler);
1818 if (r < 0) {
1819 log_struct_link(LOG_WARNING, link,
1820 "MESSAGE=%-*s: could not join netdev '%s': %s",
1821 IFNAMSIZ,
1822 link->ifname, link->network->bond->ifname, strerror(-r),
1823 NETDEV(link->network->bond),
1824 NULL);
1825 link_enter_failed(link);
1826 return r;
1827 }
1828
1829 link->enslaving ++;
1830 }
1831
1832 if (link->network->bridge) {
1833 log_struct_link(LOG_DEBUG, link,
1834 "MESSAGE=%-*s: enslaving by '%s'",
1835 IFNAMSIZ,
1836 link->ifname, link->network->bridge->ifname,
1837 NETDEV(link->network->bridge),
1838 NULL);
1839
1840 r = netdev_join(link->network->bridge, link, &netdev_join_handler);
1841 if (r < 0) {
1842 log_struct_link(LOG_WARNING, link,
1843 "MESSAGE=%-*s: could not join netdev '%s': %s",
1844 IFNAMSIZ,
1845 link->ifname, link->network->bridge->ifname, strerror(-r),
1846 NETDEV(link->network->bridge),
1847 NULL);
1848 link_enter_failed(link);
1849 return r;
1850 }
1851
1852 link->enslaving ++;
1853 }
1854
1855 if (link->network->tunnel) {
1856 log_struct_link(LOG_DEBUG, link,
1857 "MESSAGE=%-*s: enslaving by '%s'",
1858 IFNAMSIZ,
1859 link->ifname, link->network->tunnel->ifname,
1860 NETDEV(link->network->tunnel),
1861 NULL);
1862
1863 r = netdev_join(link->network->tunnel, link, &netdev_join_handler);
1864 if (r < 0) {
1865 log_struct_link(LOG_WARNING, link,
1866 "MESSAGE=%-*s: could not join netdev '%s': %s",
1867 IFNAMSIZ,
1868 link->ifname, link->network->tunnel->ifname, strerror(-r),
1869 NETDEV(link->network->tunnel),
1870 NULL);
1871 link_enter_failed(link);
1872 return r;
1873 }
1874
1875 link->enslaving ++;
1876 }
1877
1878 HASHMAP_FOREACH(vlan, link->network->vlans, i) {
1879 log_struct_link(LOG_DEBUG, link,
1880 "MESSAGE=%-*s: enslaving by '%s'",
1881 IFNAMSIZ,
1882 link->ifname, vlan->ifname, NETDEV(vlan), NULL);
1883
1884 r = netdev_join(vlan, link, &netdev_join_handler);
1885 if (r < 0) {
1886 log_struct_link(LOG_WARNING, link,
1887 "MESSAGE=%-*s: could not join netdev '%s': %s",
1888 IFNAMSIZ,
1889 link->ifname, vlan->ifname, strerror(-r),
1890 NETDEV(vlan), NULL);
1891 link_enter_failed(link);
1892 return r;
1893 }
1894
1895 link->enslaving ++;
1896 }
1897
1898 HASHMAP_FOREACH(macvlan, link->network->macvlans, i) {
1899 log_struct_link(LOG_DEBUG, link,
1900 "MESSAGE=%-*s: enslaving by '%s'",
1901 IFNAMSIZ,
1902 link->ifname, macvlan->ifname, NETDEV(macvlan), NULL);
1903
1904 r = netdev_join(macvlan, link, &netdev_join_handler);
1905 if (r < 0) {
1906 log_struct_link(LOG_WARNING, link,
1907 "MESSAGE=%-*s: could not join netdev '%s': %s",
1908 IFNAMSIZ,
1909 link->ifname, macvlan->ifname, strerror(-r),
1910 NETDEV(macvlan), NULL);
1911 link_enter_failed(link);
1912 return r;
1913 }
1914
1915 link->enslaving ++;
1916 }
1917
1918 HASHMAP_FOREACH(vxlan, link->network->vxlans, i) {
1919 log_struct_link(LOG_DEBUG, link,
1920 "MESSAGE=%*s: enslaving by '%s'",
1921 IFNAMSIZ,
1922 link->ifname, vxlan->ifname, NETDEV(vxlan), NULL);
1923
1924 r = netdev_join(vxlan, link, &netdev_join_handler);
1925 if (r < 0) {
1926 log_struct_link(LOG_WARNING, link,
1927 "MESSAGE=%*s: could not join netdev '%s': %s",
1928 IFNAMSIZ,
1929 link->ifname, vxlan->ifname, strerror(-r),
1930 NETDEV(vxlan), NULL);
1931 link_enter_failed(link);
1932 return r;
1933 }
1934
1935 link->enslaving ++;
1936 }
1937
1938 return 0;
1939 }
1940
1941 static int link_configure(Link *link) {
1942 int r;
1943
1944 assert(link);
1945 assert(link->state == LINK_STATE_INITIALIZING);
1946
1947 if (link->network->ipv4ll) {
1948 uint8_t seed[8];
1949
1950 r = sd_ipv4ll_new(&link->ipv4ll);
1951 if (r < 0)
1952 return r;
1953
1954 if (link->udev_device) {
1955 r = net_get_unique_predictable_data(link->udev_device, seed);
1956 if (r >= 0) {
1957 r = sd_ipv4ll_set_address_seed(link->ipv4ll, seed);
1958 if (r < 0)
1959 return r;
1960 }
1961 }
1962
1963 r = sd_ipv4ll_attach_event(link->ipv4ll, NULL, 0);
1964 if (r < 0)
1965 return r;
1966
1967 r = sd_ipv4ll_set_mac(link->ipv4ll, &link->mac);
1968 if (r < 0)
1969 return r;
1970
1971 r = sd_ipv4ll_set_index(link->ipv4ll, link->ifindex);
1972 if (r < 0)
1973 return r;
1974
1975 r = sd_ipv4ll_set_callback(link->ipv4ll, ipv4ll_handler, link);
1976 if (r < 0)
1977 return r;
1978 }
1979
1980 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V4)) {
1981 r = sd_dhcp_client_new(&link->dhcp_client);
1982 if (r < 0)
1983 return r;
1984
1985 r = sd_dhcp_client_attach_event(link->dhcp_client, NULL, 0);
1986 if (r < 0)
1987 return r;
1988
1989 r = sd_dhcp_client_set_mac(link->dhcp_client, &link->mac);
1990 if (r < 0)
1991 return r;
1992
1993 r = sd_dhcp_client_set_index(link->dhcp_client, link->ifindex);
1994 if (r < 0)
1995 return r;
1996
1997 r = sd_dhcp_client_set_callback(link->dhcp_client, dhcp_handler, link);
1998 if (r < 0)
1999 return r;
2000
2001 if (link->network->dhcp_mtu) {
2002 r = sd_dhcp_client_set_request_option(link->dhcp_client, 26);
2003 if (r < 0)
2004 return r;
2005 }
2006
2007 if (link->network->dhcp_routes) {
2008 r = sd_dhcp_client_set_request_option(link->dhcp_client, DHCP_OPTION_STATIC_ROUTE);
2009 if (r < 0)
2010 return r;
2011 r = sd_dhcp_client_set_request_option(link->dhcp_client, DHCP_OPTION_CLASSLESS_STATIC_ROUTE);
2012 if (r < 0)
2013 return r;
2014 }
2015
2016 if (link->network->dhcp_sendhost) {
2017 _cleanup_free_ char *hostname = gethostname_malloc();
2018 if (!hostname)
2019 return -ENOMEM;
2020
2021 if (!is_localhost(hostname)) {
2022 r = sd_dhcp_client_set_hostname(link->dhcp_client, hostname);
2023 if (r < 0)
2024 return r;
2025 }
2026 }
2027
2028 if (link->network->dhcp_vendor_class_identifier) {
2029 r = sd_dhcp_client_set_vendor_class_identifier(link->dhcp_client,
2030 link->network->dhcp_vendor_class_identifier);
2031 if (r < 0)
2032 return r;
2033 }
2034 }
2035
2036 if (link->network->dhcp_server) {
2037 r = sd_dhcp_server_new(&link->dhcp_server, link->ifindex);
2038 if (r < 0)
2039 return r;
2040
2041 r = sd_dhcp_server_attach_event(link->dhcp_server, NULL, 0);
2042 if (r < 0)
2043 return r;
2044 }
2045
2046 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V6)) {
2047 r = sd_icmp6_nd_new(&link->icmp6_router_discovery);
2048 if (r < 0)
2049 return r;
2050
2051 r = sd_icmp6_nd_attach_event(link->icmp6_router_discovery,
2052 NULL, 0);
2053 if (r < 0)
2054 return r;
2055
2056 r = sd_icmp6_nd_set_mac(link->icmp6_router_discovery,
2057 &link->mac);
2058 if (r < 0)
2059 return r;
2060
2061 r = sd_icmp6_nd_set_index(link->icmp6_router_discovery,
2062 link->ifindex);
2063 if (r < 0)
2064 return r;
2065
2066 r = sd_icmp6_nd_set_callback(link->icmp6_router_discovery,
2067 icmp6_router_handler, link);
2068 if (r < 0)
2069 return r;
2070 }
2071
2072 if (link_has_carrier(link->flags, link->kernel_operstate)) {
2073 r = link_acquire_conf(link);
2074 if (r < 0)
2075 return r;
2076 }
2077
2078 return link_enter_join_netdev(link);
2079 }
2080
2081 static int link_initialized_and_synced(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
2082 _cleanup_link_unref_ Link *link = userdata;
2083 Network *network;
2084 int r;
2085
2086 assert(link);
2087 assert(link->ifname);
2088 assert(link->manager);
2089
2090 if (link->state != LINK_STATE_INITIALIZING)
2091 return 1;
2092
2093 log_debug_link(link, "link state is up-to-date");
2094
2095 r = network_get(link->manager, link->udev_device, link->ifname, &link->mac, &network);
2096 if (r == -ENOENT) {
2097 link_enter_unmanaged(link);
2098 return 1;
2099 } else if (r < 0)
2100 return r;
2101
2102 r = network_apply(link->manager, network, link);
2103 if (r < 0)
2104 return r;
2105
2106 r = link_configure(link);
2107 if (r < 0)
2108 return r;
2109
2110 return 1;
2111 }
2112
2113 int link_initialized(Link *link, struct udev_device *device) {
2114 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
2115 int r;
2116
2117 assert(link);
2118 assert(link->manager);
2119 assert(link->manager->rtnl);
2120 assert(device);
2121
2122 if (link->state != LINK_STATE_INITIALIZING)
2123 return 0;
2124
2125 log_debug_link(link, "udev initialized link");
2126
2127 link->udev_device = udev_device_ref(device);
2128
2129 /* udev has initialized the link, but we don't know if we have yet processed
2130 the NEWLINK messages with the latest state. Do a GETLINK, when it returns
2131 we know that the pending NEWLINKs have already been processed and that we
2132 are up-to-date */
2133
2134 r = sd_rtnl_message_new_link(link->manager->rtnl, &req, RTM_GETLINK, link->ifindex);
2135 if (r < 0)
2136 return r;
2137
2138 r = sd_rtnl_call_async(link->manager->rtnl, req, link_initialized_and_synced, link, 0, NULL);
2139 if (r < 0)
2140 return r;
2141
2142 link_ref(link);
2143
2144 return 0;
2145 }
2146
2147 int link_rtnl_process_address(sd_rtnl *rtnl, sd_rtnl_message *message, void *userdata) {
2148 Manager *m = userdata;
2149 Link *link = NULL;
2150 uint16_t type;
2151 _cleanup_address_free_ Address *address = NULL;
2152 Address *ad;
2153 char buf[INET6_ADDRSTRLEN];
2154 bool address_dropped = false;
2155 int r, ifindex;
2156
2157 assert(rtnl);
2158 assert(message);
2159 assert(m);
2160
2161 r = sd_rtnl_message_get_type(message, &type);
2162 if (r < 0) {
2163 log_warning("rtnl: could not get message type");
2164 return 0;
2165 }
2166
2167 r = sd_rtnl_message_addr_get_ifindex(message, &ifindex);
2168 if (r < 0 || ifindex <= 0) {
2169 log_warning("rtnl: received address message without valid ifindex, ignoring");
2170 return 0;
2171 } else {
2172 r = link_get(m, ifindex, &link);
2173 if (r < 0 || !link) {
2174 log_warning("rtnl: received address for a nonexistent link, ignoring");
2175 return 0;
2176 }
2177 }
2178
2179 r = address_new_dynamic(&address);
2180 if (r < 0)
2181 return r;
2182
2183 r = sd_rtnl_message_addr_get_family(message, &address->family);
2184 if (r < 0 || !IN_SET(address->family, AF_INET, AF_INET6)) {
2185 log_warning_link(link, "rtnl: received address with invalid family, ignoring");
2186 return 0;
2187 }
2188
2189 r = sd_rtnl_message_addr_get_prefixlen(message, &address->prefixlen);
2190 if (r < 0) {
2191 log_warning_link(link, "rtnl: received address with invalid prefixlen, ignoring");
2192 return 0;
2193 }
2194
2195 r = sd_rtnl_message_addr_get_scope(message, &address->scope);
2196 if (r < 0) {
2197 log_warning_link(link, "rtnl: received address with invalid scope, ignoring");
2198 return 0;
2199 }
2200
2201 switch (address->family) {
2202 case AF_INET:
2203 r = sd_rtnl_message_read_in_addr(message, IFA_LOCAL, &address->in_addr.in);
2204 if (r < 0) {
2205 log_warning_link(link, "rtnl: received address without valid address, ignoring");
2206 return 0;
2207 }
2208
2209 break;
2210
2211 case AF_INET6:
2212 r = sd_rtnl_message_read_in6_addr(message, IFA_ADDRESS, &address->in_addr.in6);
2213 if (r < 0) {
2214 log_warning_link(link, "rtnl: received address without valid address, ignoring");
2215 return 0;
2216 }
2217
2218 break;
2219
2220 default:
2221 assert_not_reached("invalid address family");
2222 }
2223
2224 if (!inet_ntop(address->family, &address->in_addr, buf, INET6_ADDRSTRLEN)) {
2225 log_warning_link(link, "could not print address");
2226 return 0;
2227 }
2228
2229 LIST_FOREACH(addresses, ad, link->addresses) {
2230 if (address_equal(ad, address)) {
2231 LIST_REMOVE(addresses, link->addresses, ad);
2232
2233 address_free(ad);
2234
2235 address_dropped = true;
2236
2237 break;
2238 }
2239 }
2240
2241 switch (type) {
2242 case RTM_NEWADDR:
2243 if (!address_dropped)
2244 log_debug_link(link, "added address: %s/%u", buf,
2245 address->prefixlen);
2246 else
2247 log_debug_link(link, "updated address: %s/%u", buf,
2248 address->prefixlen);
2249
2250 LIST_PREPEND(addresses, link->addresses, address);
2251 address = NULL;
2252
2253 link_save(link);
2254
2255 break;
2256 case RTM_DELADDR:
2257 if (address_dropped) {
2258 log_debug_link(link, "removed address: %s/%u", buf,
2259 address->prefixlen);
2260
2261 link_save(link);
2262 } else
2263 log_warning_link(link, "removing non-existent address: %s/%u",
2264 buf, address->prefixlen);
2265
2266 break;
2267 default:
2268 assert_not_reached("Received invalid RTNL message type");
2269 }
2270
2271 return 1;
2272 }
2273
2274 int link_add(Manager *m, sd_rtnl_message *message, Link **ret) {
2275 Link *link;
2276 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
2277 _cleanup_udev_device_unref_ struct udev_device *device = NULL;
2278 char ifindex_str[2 + DECIMAL_STR_MAX(int)];
2279 int r;
2280
2281 assert(m);
2282 assert(m->rtnl);
2283 assert(message);
2284 assert(ret);
2285
2286 r = link_new(m, message, ret);
2287 if (r < 0)
2288 return r;
2289
2290 link = *ret;
2291
2292 log_debug_link(link, "link %"PRIu64" added", link->ifindex);
2293
2294 r = sd_rtnl_message_new_addr(m->rtnl, &req, RTM_GETADDR, link->ifindex, 0);
2295 if (r < 0)
2296 return r;
2297
2298 r = sd_rtnl_call_async(m->rtnl, req, link_get_address_handler, link, 0, NULL);
2299 if (r < 0)
2300 return r;
2301
2302 link_ref(link);
2303
2304 if (detect_container(NULL) <= 0) {
2305 /* not in a container, udev will be around */
2306 sprintf(ifindex_str, "n%"PRIu64, link->ifindex);
2307 device = udev_device_new_from_device_id(m->udev, ifindex_str);
2308 if (!device) {
2309 log_warning_link(link, "could not find udev device");
2310 return -errno;
2311 }
2312
2313 if (udev_device_get_is_initialized(device) <= 0) {
2314 /* not yet ready */
2315 log_debug_link(link, "udev initializing link...");
2316 return 0;
2317 }
2318
2319 r = link_initialized(link, device);
2320 if (r < 0)
2321 return r;
2322 } else {
2323 /* we are calling a callback directly, so must take a ref */
2324 link_ref(link);
2325
2326 r = link_initialized_and_synced(m->rtnl, NULL, link);
2327 if (r < 0)
2328 return r;
2329 }
2330
2331 return 0;
2332 }
2333
2334 int link_update(Link *link, sd_rtnl_message *m) {
2335 struct ether_addr mac;
2336 char *ifname;
2337 int r;
2338
2339 assert(link);
2340 assert(link->ifname);
2341 assert(m);
2342
2343 if (link->state == LINK_STATE_LINGER) {
2344 link_ref(link);
2345 log_info_link(link, "link readded");
2346 link->state = LINK_STATE_ENSLAVING;
2347 }
2348
2349 r = sd_rtnl_message_read_string(m, IFLA_IFNAME, &ifname);
2350 if (r >= 0 && !streq(ifname, link->ifname)) {
2351 log_info_link(link, "renamed to %s", ifname);
2352
2353 free(link->ifname);
2354 link->ifname = strdup(ifname);
2355 if (!link->ifname)
2356 return -ENOMEM;
2357 }
2358
2359 if (!link->original_mtu) {
2360 r = sd_rtnl_message_read_u16(m, IFLA_MTU, &link->original_mtu);
2361 if (r >= 0)
2362 log_debug_link(link, "saved original MTU: %"
2363 PRIu16, link->original_mtu);
2364 }
2365
2366 /* The kernel may broadcast NEWLINK messages without the MAC address
2367 set, simply ignore them. */
2368 r = sd_rtnl_message_read_ether_addr(m, IFLA_ADDRESS, &mac);
2369 if (r >= 0) {
2370 if (memcmp(link->mac.ether_addr_octet, mac.ether_addr_octet, ETH_ALEN)) {
2371
2372 memcpy(link->mac.ether_addr_octet, mac.ether_addr_octet, ETH_ALEN);
2373
2374 log_debug_link(link, "MAC address: "
2375 "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx",
2376 mac.ether_addr_octet[0],
2377 mac.ether_addr_octet[1],
2378 mac.ether_addr_octet[2],
2379 mac.ether_addr_octet[3],
2380 mac.ether_addr_octet[4],
2381 mac.ether_addr_octet[5]);
2382
2383 if (link->ipv4ll) {
2384 r = sd_ipv4ll_set_mac(link->ipv4ll, &link->mac);
2385 if (r < 0) {
2386 log_warning_link(link, "Could not update MAC "
2387 "address in IPv4LL client: %s",
2388 strerror(-r));
2389 return r;
2390 }
2391 }
2392
2393 if (link->dhcp_client) {
2394 r = sd_dhcp_client_set_mac(link->dhcp_client, &link->mac);
2395 if (r < 0) {
2396 log_warning_link(link, "Could not update MAC "
2397 "address in DHCP client: %s",
2398 strerror(-r));
2399 return r;
2400 }
2401 }
2402
2403 if (link->dhcp6_client) {
2404 r = sd_dhcp6_client_set_mac(link->dhcp6_client,
2405 &link->mac);
2406 if (r < 0) {
2407 log_warning_link(link, "Could not update MAC address in DHCPv6 client: %s",
2408 strerror(-r));
2409 return r;
2410 }
2411 }
2412 }
2413 }
2414
2415 return link_update_flags(link, m);
2416 }
2417
2418 static void serialize_addresses(FILE *f, const char *key, Address *address) {
2419 Address *ad;
2420
2421 assert(f);
2422 assert(key);
2423
2424 if (!address)
2425 return;
2426
2427 fprintf(f, "%s=", key);
2428
2429 LIST_FOREACH(addresses, ad, address) {
2430 char buf[INET6_ADDRSTRLEN];
2431
2432 if (inet_ntop(ad->family, &ad->in_addr, buf, INET6_ADDRSTRLEN))
2433 fprintf(f, "%s%s", buf, (ad->addresses_next) ? " ": "");
2434 }
2435
2436 fputs("\n", f);
2437 }
2438
2439 static void link_update_operstate(Link *link) {
2440
2441 assert(link);
2442
2443 if (link->kernel_operstate == IF_OPER_DORMANT)
2444 link->operstate = LINK_OPERSTATE_DORMANT;
2445 else if (link_has_carrier(link->flags, link->kernel_operstate)) {
2446 Address *address;
2447 uint8_t scope = RT_SCOPE_NOWHERE;
2448
2449 /* if we have carrier, check what addresses we have */
2450 LIST_FOREACH(addresses, address, link->addresses) {
2451 if (address->scope < scope)
2452 scope = address->scope;
2453 }
2454
2455 if (scope < RT_SCOPE_SITE)
2456 /* universally accessible addresses found */
2457 link->operstate = LINK_OPERSTATE_ROUTABLE;
2458 else if (scope < RT_SCOPE_HOST)
2459 /* only link or site local addresses found */
2460 link->operstate = LINK_OPERSTATE_DEGRADED;
2461 else
2462 /* no useful addresses found */
2463 link->operstate = LINK_OPERSTATE_CARRIER;
2464 } else
2465 link->operstate = LINK_OPERSTATE_UNKNOWN;
2466 }
2467
2468 int link_save(Link *link) {
2469 _cleanup_free_ char *temp_path = NULL;
2470 _cleanup_fclose_ FILE *f = NULL;
2471 const char *admin_state, *oper_state;
2472 int r;
2473
2474 assert(link);
2475 assert(link->state_file);
2476 assert(link->lease_file);
2477 assert(link->manager);
2478
2479 link_update_operstate(link);
2480
2481 r = manager_save(link->manager);
2482 if (r < 0)
2483 return r;
2484
2485 if (link->state == LINK_STATE_LINGER) {
2486 unlink(link->state_file);
2487 return 0;
2488 }
2489
2490 admin_state = link_state_to_string(link->state);
2491 assert(admin_state);
2492
2493 oper_state = link_operstate_to_string(link->operstate);
2494 assert(oper_state);
2495
2496 r = fopen_temporary(link->state_file, &f, &temp_path);
2497 if (r < 0)
2498 goto finish;
2499
2500 fchmod(fileno(f), 0644);
2501
2502 fprintf(f,
2503 "# This is private data. Do not parse.\n"
2504 "ADMIN_STATE=%s\n"
2505 "OPER_STATE=%s\n"
2506 "FLAGS=%u\n",
2507 admin_state, oper_state, link->flags);
2508
2509 if (link->network) {
2510 serialize_addresses(f, "DNS", link->network->dns);
2511 serialize_addresses(f, "NTP", link->network->ntp);
2512 }
2513
2514 if (link->dhcp_lease) {
2515 assert(link->network);
2516
2517 r = dhcp_lease_save(link->dhcp_lease, link->lease_file);
2518 if (r < 0)
2519 goto finish;
2520
2521 fprintf(f,
2522 "DHCP_LEASE=%s\n"
2523 "DHCP_USE_DNS=%s\n"
2524 "DHCP_USE_NTP=%s\n",
2525 link->lease_file,
2526 yes_no(link->network->dhcp_dns),
2527 yes_no(link->network->dhcp_ntp));
2528 } else
2529 unlink(link->lease_file);
2530
2531 fflush(f);
2532
2533 if (ferror(f) || rename(temp_path, link->state_file) < 0) {
2534 r = -errno;
2535 unlink(link->state_file);
2536 unlink(temp_path);
2537 }
2538
2539 finish:
2540 if (r < 0)
2541 log_error_link(link, "Failed to save link data to %s: %s", link->state_file, strerror(-r));
2542
2543 return r;
2544 }
2545
2546 static const char* const link_state_table[_LINK_STATE_MAX] = {
2547 [LINK_STATE_INITIALIZING] = "initializing",
2548 [LINK_STATE_ENSLAVING] = "configuring",
2549 [LINK_STATE_SETTING_ADDRESSES] = "configuring",
2550 [LINK_STATE_SETTING_ROUTES] = "configuring",
2551 [LINK_STATE_CONFIGURED] = "configured",
2552 [LINK_STATE_UNMANAGED] = "unmanaged",
2553 [LINK_STATE_FAILED] = "failed",
2554 [LINK_STATE_LINGER] = "linger",
2555 };
2556
2557 DEFINE_STRING_TABLE_LOOKUP(link_state, LinkState);
2558
2559 static const char* const link_operstate_table[_LINK_OPERSTATE_MAX] = {
2560 [LINK_OPERSTATE_UNKNOWN] = "unknown",
2561 [LINK_OPERSTATE_DORMANT] = "dormant",
2562 [LINK_OPERSTATE_CARRIER] = "carrier",
2563 [LINK_OPERSTATE_DEGRADED] = "degraded",
2564 [LINK_OPERSTATE_ROUTABLE] = "routable",
2565 };
2566
2567 DEFINE_STRING_TABLE_LOOKUP(link_operstate, LinkOperationalState);
2568
2569 static const char* const dhcp_support_table[_DHCP_SUPPORT_MAX] = {
2570 [DHCP_SUPPORT_NONE] = "none",
2571 [DHCP_SUPPORT_BOTH] = "both",
2572 [DHCP_SUPPORT_V4] = "v4",
2573 [DHCP_SUPPORT_V6] = "v6",
2574 };
2575
2576 DEFINE_STRING_TABLE_LOOKUP(dhcp_support, DHCPSupport);
2577
2578 int config_parse_dhcp(
2579 const char* unit,
2580 const char *filename,
2581 unsigned line,
2582 const char *section,
2583 unsigned section_line,
2584 const char *lvalue,
2585 int ltype,
2586 const char *rvalue,
2587 void *data,
2588 void *userdata) {
2589
2590 DHCPSupport *dhcp = data;
2591 int k;
2592
2593 assert(filename);
2594 assert(lvalue);
2595 assert(rvalue);
2596 assert(data);
2597
2598 /* Our enum shall be a superset of booleans, hence first try
2599 * to parse as boolean, and then as enum */
2600
2601 k = parse_boolean(rvalue);
2602 if (k > 0)
2603 *dhcp = DHCP_SUPPORT_BOTH;
2604 else if (k == 0)
2605 *dhcp = DHCP_SUPPORT_NONE;
2606 else {
2607 DHCPSupport s;
2608
2609 s = dhcp_support_from_string(rvalue);
2610 if (s < 0){
2611 log_syntax(unit, LOG_ERR, filename, line, -s, "Failed to parse DHCP option, ignoring: %s", rvalue);
2612 return 0;
2613 }
2614
2615 *dhcp = s;
2616 }
2617
2618 return 0;
2619 }