1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
4 This file is part of systemd.
6 Copyright 2013 Tom Gundersen <teg@jklm.no>
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.
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.
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/>.
22 #include <netinet/ether.h>
27 #include "networkd-netdev.h"
28 #include "libudev-private.h"
29 #include "udev-util.h"
33 #include "network-internal.h"
34 #include "conf-parser.h"
36 #include "network-util.h"
37 #include "dhcp-lease-internal.h"
39 static int ipv4ll_address_update(Link *link, bool deprecate);
40 static bool ipv4ll_is_bound(sd_ipv4ll *ll);
42 static int link_new(Manager *manager, sd_rtnl_message *message, Link **ret) {
43 _cleanup_link_unref_ Link *link = NULL;
49 assert(manager->links);
53 r = sd_rtnl_message_get_type(message, &type);
56 else if (type != RTM_NEWLINK)
59 r = sd_rtnl_message_link_get_ifindex(message, &ifindex);
62 else if (ifindex <= 0)
65 r = sd_rtnl_message_read_string(message, IFLA_IFNAME, &ifname);
74 link->manager = manager;
75 link->state = LINK_STATE_INITIALIZING;
76 link->ifindex = ifindex;
77 link->ifname = strdup(ifname);
81 r = sd_rtnl_message_read_ether_addr(message, IFLA_ADDRESS, &link->mac);
83 log_debug_link(link, "MAC address not found for new device, continuing without");
85 r = asprintf(&link->state_file, "/run/systemd/netif/links/%"PRIu64,
90 r = asprintf(&link->lease_file, "/run/systemd/netif/leases/%"PRIu64,
95 r = hashmap_put(manager->links, &link->ifindex, link);
105 static void link_free(Link *link) {
111 while ((address = link->addresses)) {
112 LIST_REMOVE(addresses, link->addresses, address);
113 address_free(address);
116 while ((address = link->pool_addresses)) {
117 LIST_REMOVE(addresses, link->pool_addresses, address);
118 address_free(address);
121 sd_dhcp_client_unref(link->dhcp_client);
122 sd_dhcp_lease_unref(link->dhcp_lease);
124 unlink(link->lease_file);
125 free(link->lease_file);
127 sd_ipv4ll_unref(link->ipv4ll);
128 sd_dhcp6_client_unref(link->dhcp6_client);
129 sd_icmp6_nd_unref(link->icmp6_router_discovery);
132 hashmap_remove(link->manager->links, &link->ifindex);
136 unlink(link->state_file);
137 free(link->state_file);
139 udev_device_unref(link->udev_device);
144 Link *link_unref(Link *link) {
145 if (link && (-- link->n_ref <= 0))
151 Link *link_ref(Link *link) {
153 assert_se(++ link->n_ref >= 2);
158 int link_get(Manager *m, int ifindex, Link **ret) {
167 ifindex_64 = ifindex;
168 link = hashmap_get(m->links, &ifindex_64);
177 void link_drop(Link *link) {
178 if (!link || link->state == LINK_STATE_LINGER)
181 link->state = LINK_STATE_LINGER;
183 log_debug_link(link, "link removed");
190 static void link_enter_unmanaged(Link *link) {
193 log_debug_link(link, "unmanaged");
195 link->state = LINK_STATE_UNMANAGED;
200 static int link_stop_clients(Link *link) {
204 assert(link->manager);
205 assert(link->manager->event);
210 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V6)) {
211 assert(link->dhcp_client);
213 k = sd_dhcp_client_stop(link->dhcp_client);
215 log_warning_link(link, "Could not stop DHCPv4 client: %s", strerror(-r));
220 if (link->network->ipv4ll) {
221 assert(link->ipv4ll);
223 k = sd_ipv4ll_stop(link->ipv4ll);
225 log_warning_link(link, "Could not stop IPv4 link-local: %s", strerror(-r));
230 if (link->network->dhcp_server) {
231 assert(link->dhcp_server);
233 k = sd_dhcp_server_stop(link->dhcp_server);
235 log_warning_link(link, "Could not stop DHCPv4 server: %s", strerror(-r));
240 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V6)) {
241 assert(link->icmp6_router_discovery);
243 if (link->dhcp6_client) {
244 k = sd_dhcp6_client_stop(link->dhcp6_client);
246 log_warning_link(link, "Could not stop DHCPv6 client: %s", strerror(-r));
251 k = sd_icmp6_nd_stop(link->icmp6_router_discovery);
253 log_warning_link(link, "Could not stop ICMPv6 router discovery: %s", strerror(-r));
261 static void link_enter_failed(Link *link) {
264 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
267 log_warning_link(link, "failed");
269 link->state = LINK_STATE_FAILED;
271 link_stop_clients(link);
276 static Address* link_find_dhcp_server_address(Link *link) {
280 assert(link->network);
282 /* The the first statically configured address if there is any */
283 LIST_FOREACH(addresses, address, link->network->static_addresses) {
285 if (address->family != AF_INET)
288 if (in_addr_null(address->family, &address->in_addr))
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)
305 static int link_enter_configured(Link *link) {
309 assert(link->network);
310 assert(link->state == LINK_STATE_SETTING_ROUTES);
312 if (link->network->dhcp_server &&
313 !sd_dhcp_server_is_running(link->dhcp_server)) {
314 struct in_addr pool_start;
317 address = link_find_dhcp_server_address(link);
319 log_warning_link(link, "Failed to find suitable address for DHCPv4 server instance.");
320 link_enter_failed(link);
324 log_debug_link(link, "offering DHCPv4 leases");
326 r = sd_dhcp_server_set_address(link->dhcp_server, &address->in_addr.in);
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,
338 r = sd_dhcp_server_set_router(link->dhcp_server,
339 &main_address->in_addr.in);
343 r = sd_dhcp_server_set_prefixlen(link->dhcp_server,
344 main_address->prefixlen);
349 r = sd_dhcp_server_start(link->dhcp_server);
351 log_warning_link(link, "could not start DHCPv4 server "
352 "instance: %s", strerror(-r));
354 link_enter_failed(link);
360 log_info_link(link, "link configured");
362 link->state = LINK_STATE_CONFIGURED;
369 static int route_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
370 _cleanup_link_unref_ Link *link = userdata;
373 assert(link->route_messages > 0);
374 assert(IN_SET(link->state, LINK_STATE_SETTING_ADDRESSES,
375 LINK_STATE_SETTING_ROUTES, LINK_STATE_FAILED,
378 link->route_messages --;
380 if (IN_SET(LINK_STATE_FAILED, LINK_STATE_LINGER))
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",
388 link->ifname, strerror(-r),
392 /* we might have received an old reply after moving back to SETTING_ADDRESSES,
394 if (link->route_messages == 0 && link->state == LINK_STATE_SETTING_ROUTES) {
395 log_debug_link(link, "routes set");
396 link_enter_configured(link);
402 static int link_set_dhcp_routes(Link *link) {
403 struct sd_dhcp_route *static_routes;
408 n = sd_dhcp_lease_get_routes(link->dhcp_lease, &static_routes);
411 log_warning_link(link, "DHCP error: could not get routes: %s", strerror(-n));
415 for (i = 0; i < n; i++) {
416 _cleanup_route_free_ Route *route = NULL;
418 r = route_new_dynamic(&route, RTPROT_DHCP);
420 log_error_link(link, "Could not allocate route: %s",
425 route->family = AF_INET;
426 route->in_addr.in = static_routes[i].gw_addr;
427 route->dst_addr.in = static_routes[i].dst_addr;
428 route->dst_prefixlen = static_routes[i].dst_prefixlen;
429 route->metrics = DHCP_ROUTE_METRIC;
431 r = route_configure(route, link, &route_handler);
433 log_warning_link(link,
434 "could not set host route: %s", strerror(-r));
438 link->route_messages ++;
444 static int link_enter_set_routes(Link *link) {
449 assert(link->network);
450 assert(link->state == LINK_STATE_SETTING_ADDRESSES);
452 link->state = LINK_STATE_SETTING_ROUTES;
454 if (!link->network->static_routes && !link->dhcp_lease &&
455 (!link->ipv4ll || ipv4ll_is_bound(link->ipv4ll) == false))
456 return link_enter_configured(link);
458 log_debug_link(link, "setting routes");
460 LIST_FOREACH(routes, rt, link->network->static_routes) {
461 r = route_configure(rt, link, &route_handler);
463 log_warning_link(link,
464 "could not set routes: %s", strerror(-r));
465 link_enter_failed(link);
469 link->route_messages ++;
472 if (link->ipv4ll && !link->dhcp_lease) {
473 _cleanup_route_free_ Route *route = NULL;
476 r = route_new_dynamic(&route, RTPROT_STATIC);
478 log_error_link(link, "Could not allocate route: %s",
483 route->family = AF_INET;
484 route->scope = RT_SCOPE_LINK;
485 route->metrics = IPV4LL_ROUTE_METRIC;
487 r = route_configure(route, link, &route_handler);
489 log_warning_link(link,
490 "could not set routes: %s", strerror(-r));
491 link_enter_failed(link);
495 link->route_messages ++;
499 if (link->dhcp_lease) {
500 _cleanup_route_free_ Route *route = NULL;
501 _cleanup_route_free_ Route *route_gw = NULL;
502 struct in_addr gateway;
504 r = sd_dhcp_lease_get_router(link->dhcp_lease, &gateway);
505 if (r < 0 && r != -ENOENT) {
506 log_warning_link(link, "DHCP error: could not get gateway: %s",
512 r = route_new_dynamic(&route, RTPROT_DHCP);
514 log_error_link(link, "Could not allocate route: %s",
519 r = route_new_dynamic(&route_gw, RTPROT_DHCP);
521 log_error_link(link, "Could not allocate route: %s",
526 /* The dhcp netmask may mask out the gateway. Add an explicit
527 * route for the gw host so that we can route no matter the
528 * netmask or existing kernel route tables. */
529 route_gw->family = AF_INET;
530 route_gw->dst_addr.in = gateway;
531 route_gw->dst_prefixlen = 32;
532 route_gw->scope = RT_SCOPE_LINK;
533 route_gw->metrics = DHCP_ROUTE_METRIC;
535 r = route_configure(route_gw, link, &route_handler);
537 log_warning_link(link,
538 "could not set host route: %s", strerror(-r));
542 link->route_messages ++;
544 route->family = AF_INET;
545 route->in_addr.in = gateway;
546 route->metrics = DHCP_ROUTE_METRIC;
548 r = route_configure(route, link, &route_handler);
550 log_warning_link(link,
551 "could not set routes: %s", strerror(-r));
552 link_enter_failed(link);
556 link->route_messages ++;
559 if (link->network->dhcp_routes)
560 link_set_dhcp_routes(link);
563 if (link->route_messages == 0) {
564 link_enter_configured(link);
570 static int route_drop_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
571 _cleanup_link_unref_ Link *link = userdata;
576 assert(link->ifname);
578 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
581 r = sd_rtnl_message_get_errno(m);
582 if (r < 0 && r != -ESRCH)
583 log_struct_link(LOG_WARNING, link,
584 "MESSAGE=%-*s: could not drop route: %s",
586 link->ifname, strerror(-r),
593 static int link_get_address_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
594 _cleanup_link_unref_ Link *link = userdata;
600 assert(link->manager);
602 for (; m; m = sd_rtnl_message_next(m)) {
603 r = sd_rtnl_message_get_errno(m);
605 log_debug_link(link, "getting address failed: %s", strerror(-r));
609 r = link_rtnl_process_address(rtnl, m, link->manager);
611 log_warning_link(link, "could not process address: %s", strerror(-r));
617 static int address_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
618 _cleanup_link_unref_ Link *link = userdata;
624 assert(link->ifname);
625 assert(link->addr_messages > 0);
626 assert(IN_SET(link->state, LINK_STATE_SETTING_ADDRESSES,
627 LINK_STATE_FAILED, LINK_STATE_LINGER));
629 link->addr_messages --;
631 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
634 r = sd_rtnl_message_get_errno(m);
635 if (r < 0 && r != -EEXIST)
636 log_struct_link(LOG_WARNING, link,
637 "MESSAGE=%-*s: could not set address: %s",
639 link->ifname, strerror(-r),
643 /* calling handler directly so take a ref */
645 link_get_address_handler(rtnl, m, link);
648 if (link->addr_messages == 0) {
649 log_debug_link(link, "addresses set");
650 link_enter_set_routes(link);
656 static int link_enter_set_addresses(Link *link) {
659 uint32_t lifetime = CACHE_INFO_INFINITY_LIFE_TIME;
662 assert(link->network);
663 assert(link->state != _LINK_STATE_INVALID);
665 link->state = LINK_STATE_SETTING_ADDRESSES;
667 if (!link->network->static_addresses && !link->dhcp_lease &&
668 (!link->ipv4ll || ipv4ll_is_bound(link->ipv4ll) == false))
669 return link_enter_set_routes(link);
671 log_debug_link(link, "setting addresses");
673 LIST_FOREACH(addresses, ad, link->network->static_addresses) {
674 r = address_configure(ad, link, &address_handler);
676 log_warning_link(link,
677 "could not set addresses: %s", strerror(-r));
678 link_enter_failed(link);
682 link->addr_messages ++;
685 if (link->ipv4ll && !link->dhcp_lease) {
686 _cleanup_address_free_ Address *ll_addr = NULL;
689 r = sd_ipv4ll_get_address(link->ipv4ll, &addr);
690 if (r < 0 && r != -ENOENT) {
691 log_warning_link(link, "IPV4LL error: no address: %s",
697 r = address_new_dynamic(&ll_addr);
699 log_error_link(link, "Could not allocate address: %s", strerror(-r));
703 ll_addr->family = AF_INET;
704 ll_addr->in_addr.in = addr;
705 ll_addr->prefixlen = 16;
706 ll_addr->broadcast.s_addr = ll_addr->in_addr.in.s_addr | htonl(0xfffffffflu >> ll_addr->prefixlen);
707 ll_addr->scope = RT_SCOPE_LINK;
709 r = address_configure(ll_addr, link, &address_handler);
711 log_warning_link(link,
712 "could not set addresses: %s", strerror(-r));
713 link_enter_failed(link);
717 link->addr_messages ++;
721 if (link->dhcp_lease) {
722 _cleanup_address_free_ Address *address = NULL;
724 struct in_addr netmask;
727 r = sd_dhcp_lease_get_address(link->dhcp_lease, &addr);
729 log_warning_link(link, "DHCP error: no address: %s",
734 if (!link->network->dhcp_critical) {
735 r = sd_dhcp_lease_get_lifetime(link->dhcp_lease,
738 log_warning_link(link, "DHCP error: no lifetime: %s",
744 r = sd_dhcp_lease_get_netmask(link->dhcp_lease, &netmask);
746 log_warning_link(link, "DHCP error: no netmask: %s",
751 prefixlen = net_netmask_to_prefixlen(&netmask);
753 r = address_new_dynamic(&address);
755 log_error_link(link, "Could not allocate address: %s",
760 address->family = AF_INET;
761 address->in_addr.in = addr;
762 address->cinfo.ifa_prefered = lifetime;
763 address->cinfo.ifa_valid = lifetime;
764 address->prefixlen = prefixlen;
765 address->broadcast.s_addr = addr.s_addr | ~netmask.s_addr;
767 /* use update rather than configure so that we will update the lifetime
768 of an existing address if it has already been configured */
769 r = address_update(address, link, &address_handler);
771 log_warning_link(link,
772 "could not set addresses: %s", strerror(-r));
773 link_enter_failed(link);
777 link->addr_messages ++;
783 static int address_update_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
784 _cleanup_link_unref_ Link *link = userdata;
789 assert(link->ifname);
791 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
794 r = sd_rtnl_message_get_errno(m);
795 if (r < 0 && r != -ENOENT)
796 log_struct_link(LOG_WARNING, link,
797 "MESSAGE=%-*s: could not update address: %s",
799 link->ifname, strerror(-r),
806 static int address_drop_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
807 _cleanup_link_unref_ Link *link = userdata;
812 assert(link->ifname);
814 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
817 r = sd_rtnl_message_get_errno(m);
818 if (r < 0 && r != -EADDRNOTAVAIL)
819 log_struct_link(LOG_WARNING, link,
820 "MESSAGE=%-*s: could not drop address: %s",
822 link->ifname, strerror(-r),
829 static int set_hostname_handler(sd_bus *bus, sd_bus_message *m, void *userdata, sd_bus_error *ret_error) {
830 _cleanup_link_unref_ Link *link = userdata;
835 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
838 r = sd_bus_message_get_errno(m);
840 log_warning_link(link, "Could not set hostname: %s", strerror(-r));
845 static int link_set_hostname(Link *link, const char *hostname) {
846 _cleanup_bus_message_unref_ sd_bus_message *m = NULL;
850 assert(link->manager);
853 log_debug_link(link, "Setting transient hostname: '%s'", hostname);
855 if (!link->manager->bus) { /* TODO: replace by assert when we can rely on kdbus */
856 log_info_link(link, "Not connected to system bus, ignoring transient hostname.");
860 r = sd_bus_message_new_method_call(
863 "org.freedesktop.hostname1",
864 "/org/freedesktop/hostname1",
865 "org.freedesktop.hostname1",
870 r = sd_bus_message_append(m, "sb", hostname, false);
874 r = sd_bus_call_async(link->manager->bus, NULL, m, set_hostname_handler, link, 0);
876 log_error_link(link, "Could not set transient hostname: %s", strerror(-r));
885 static int set_mtu_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
886 _cleanup_link_unref_ Link *link = userdata;
891 assert(link->ifname);
893 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
896 r = sd_rtnl_message_get_errno(m);
898 log_struct_link(LOG_WARNING, link,
899 "MESSAGE=%-*s: could not set MTU: %s",
900 IFNAMSIZ, link->ifname, strerror(-r),
907 static int link_set_mtu(Link *link, uint32_t mtu) {
908 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
912 assert(link->manager);
913 assert(link->manager->rtnl);
915 log_debug_link(link, "setting MTU: %" PRIu32, mtu);
917 r = sd_rtnl_message_new_link(link->manager->rtnl, &req,
918 RTM_SETLINK, link->ifindex);
920 log_error_link(link, "Could not allocate RTM_SETLINK message");
924 r = sd_rtnl_message_append_u32(req, IFLA_MTU, mtu);
926 log_error_link(link, "Could not append MTU: %s", strerror(-r));
930 r = sd_rtnl_call_async(link->manager->rtnl, req, set_mtu_handler, link, 0, NULL);
933 "Could not send rtnetlink message: %s", strerror(-r));
942 static int dhcp_lease_lost(Link *link) {
943 _cleanup_address_free_ Address *address = NULL;
945 struct in_addr netmask;
946 struct in_addr gateway;
951 assert(link->dhcp_lease);
953 log_warning_link(link, "DHCP lease lost");
955 if (link->network->dhcp_routes) {
956 struct sd_dhcp_route *routes;
959 n = sd_dhcp_lease_get_routes(link->dhcp_lease, &routes);
961 for (i = 0; i < n; i++) {
962 _cleanup_route_free_ Route *route = NULL;
964 r = route_new_dynamic(&route, RTPROT_UNSPEC);
966 route->family = AF_INET;
967 route->in_addr.in = routes[i].gw_addr;
968 route->dst_addr.in = routes[i].dst_addr;
969 route->dst_prefixlen = routes[i].dst_prefixlen;
971 route_drop(route, link, &route_drop_handler);
977 r = address_new_dynamic(&address);
979 r = sd_dhcp_lease_get_router(link->dhcp_lease, &gateway);
981 _cleanup_route_free_ Route *route_gw = NULL;
982 _cleanup_route_free_ Route *route = NULL;
984 r = route_new_dynamic(&route_gw, RTPROT_UNSPEC);
986 route_gw->family = AF_INET;
987 route_gw->dst_addr.in = gateway;
988 route_gw->dst_prefixlen = 32;
989 route_gw->scope = RT_SCOPE_LINK;
991 route_drop(route_gw, link, &route_drop_handler);
994 r = route_new_dynamic(&route, RTPROT_UNSPEC);
996 route->family = AF_INET;
997 route->in_addr.in = gateway;
999 route_drop(route, link, &route_drop_handler);
1003 sd_dhcp_lease_get_address(link->dhcp_lease, &addr);
1004 sd_dhcp_lease_get_netmask(link->dhcp_lease, &netmask);
1005 prefixlen = net_netmask_to_prefixlen(&netmask);
1007 address->family = AF_INET;
1008 address->in_addr.in = addr;
1009 address->prefixlen = prefixlen;
1011 address_drop(address, link, &address_drop_handler);
1014 if (link->network->dhcp_mtu) {
1017 r = sd_dhcp_lease_get_mtu(link->dhcp_lease, &mtu);
1018 if (r >= 0 && link->original_mtu != mtu) {
1019 r = link_set_mtu(link, link->original_mtu);
1021 log_warning_link(link, "DHCP error: could not reset MTU");
1022 link_enter_failed(link);
1028 if (link->network->dhcp_hostname) {
1029 const char *hostname = NULL;
1031 r = sd_dhcp_lease_get_hostname(link->dhcp_lease, &hostname);
1032 if (r >= 0 && hostname) {
1033 r = link_set_hostname(link, "");
1035 log_error_link(link, "Failed to reset transient hostname");
1039 link->dhcp_lease = sd_dhcp_lease_unref(link->dhcp_lease);
1044 static int dhcp_lease_renew(sd_dhcp_client *client, Link *link) {
1045 sd_dhcp_lease *lease;
1048 r = sd_dhcp_client_get_lease(client, &lease);
1050 log_warning_link(link, "DHCP error: no lease %s",
1055 sd_dhcp_lease_unref(link->dhcp_lease);
1056 link->dhcp_lease = lease;
1058 link_enter_set_addresses(link);
1063 static int dhcp_lease_acquired(sd_dhcp_client *client, Link *link) {
1064 sd_dhcp_lease *lease;
1065 struct in_addr address;
1066 struct in_addr netmask;
1067 struct in_addr gateway;
1074 r = sd_dhcp_client_get_lease(client, &lease);
1076 log_warning_link(link, "DHCP error: no lease: %s",
1081 r = sd_dhcp_lease_get_address(lease, &address);
1083 log_warning_link(link, "DHCP error: no address: %s",
1088 r = sd_dhcp_lease_get_netmask(lease, &netmask);
1090 log_warning_link(link, "DHCP error: no netmask: %s",
1095 prefixlen = net_netmask_to_prefixlen(&netmask);
1097 r = sd_dhcp_lease_get_router(lease, &gateway);
1098 if (r < 0 && r != -ENOENT) {
1099 log_warning_link(link, "DHCP error: could not get gateway: %s",
1105 log_struct_link(LOG_INFO, link,
1106 "MESSAGE=%-*s: DHCPv4 address %u.%u.%u.%u/%u via %u.%u.%u.%u",
1109 ADDRESS_FMT_VAL(address),
1111 ADDRESS_FMT_VAL(gateway),
1112 "ADDRESS=%u.%u.%u.%u",
1113 ADDRESS_FMT_VAL(address),
1116 "GATEWAY=%u.%u.%u.%u",
1117 ADDRESS_FMT_VAL(gateway),
1120 log_struct_link(LOG_INFO, link,
1121 "MESSAGE=%-*s: DHCPv4 address %u.%u.%u.%u/%u",
1124 ADDRESS_FMT_VAL(address),
1126 "ADDRESS=%u.%u.%u.%u",
1127 ADDRESS_FMT_VAL(address),
1132 link->dhcp_lease = lease;
1134 if (link->network->dhcp_mtu) {
1137 r = sd_dhcp_lease_get_mtu(lease, &mtu);
1139 r = link_set_mtu(link, mtu);
1141 log_error_link(link, "Failed to set MTU "
1142 "to %" PRIu16, mtu);
1146 if (link->network->dhcp_hostname) {
1147 const char *hostname;
1149 r = sd_dhcp_lease_get_hostname(lease, &hostname);
1151 r = link_set_hostname(link, hostname);
1153 log_error_link(link, "Failed to set transient hostname "
1154 "to '%s'", hostname);
1158 link_enter_set_addresses(link);
1163 static void dhcp_handler(sd_dhcp_client *client, int event, void *userdata) {
1164 Link *link = userdata;
1168 assert(link->network);
1169 assert(link->manager);
1171 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1175 case DHCP_EVENT_NO_LEASE:
1176 log_debug_link(link, "IP address in use.");
1178 case DHCP_EVENT_EXPIRED:
1179 case DHCP_EVENT_STOP:
1180 case DHCP_EVENT_IP_CHANGE:
1181 if (link->network->dhcp_critical) {
1182 log_error_link(link, "DHCPv4 connection considered system critical, "
1183 "ignoring request to reconfigure it.");
1187 if (link->dhcp_lease) {
1188 r = dhcp_lease_lost(link);
1190 link_enter_failed(link);
1195 if (event == DHCP_EVENT_IP_CHANGE) {
1196 r = dhcp_lease_acquired(client, link);
1198 link_enter_failed(link);
1203 if (event == DHCP_EVENT_EXPIRED && link->network->ipv4ll) {
1204 if (!sd_ipv4ll_is_running(link->ipv4ll))
1205 r = sd_ipv4ll_start(link->ipv4ll);
1206 else if (ipv4ll_is_bound(link->ipv4ll))
1207 r = ipv4ll_address_update(link, false);
1209 link_enter_failed(link);
1215 case DHCP_EVENT_RENEW:
1216 r = dhcp_lease_renew(client, link);
1218 link_enter_failed(link);
1222 case DHCP_EVENT_IP_ACQUIRE:
1223 r = dhcp_lease_acquired(client, link);
1225 link_enter_failed(link);
1229 if (ipv4ll_is_bound(link->ipv4ll))
1230 r = ipv4ll_address_update(link, true);
1232 r = sd_ipv4ll_stop(link->ipv4ll);
1234 link_enter_failed(link);
1241 log_warning_link(link, "DHCP error: client failed: %s", strerror(-event));
1243 log_warning_link(link, "DHCP unknown event: %d", event);
1250 static int ipv4ll_address_update(Link *link, bool deprecate) {
1252 struct in_addr addr;
1256 r = sd_ipv4ll_get_address(link->ipv4ll, &addr);
1258 _cleanup_address_free_ Address *address = NULL;
1260 log_debug_link(link, "IPv4 link-local %s %u.%u.%u.%u",
1261 deprecate ? "deprecate" : "approve",
1262 ADDRESS_FMT_VAL(addr));
1264 r = address_new_dynamic(&address);
1266 log_error_link(link, "Could not allocate address: %s", strerror(-r));
1270 address->family = AF_INET;
1271 address->in_addr.in = addr;
1272 address->prefixlen = 16;
1273 address->scope = RT_SCOPE_LINK;
1274 address->cinfo.ifa_prefered = deprecate ? 0 : CACHE_INFO_INFINITY_LIFE_TIME;
1275 address->broadcast.s_addr = address->in_addr.in.s_addr | htonl(0xfffffffflu >> address->prefixlen);
1277 address_update(address, link, &address_update_handler);
1284 static int ipv4ll_address_lost(Link *link) {
1286 struct in_addr addr;
1290 r = sd_ipv4ll_get_address(link->ipv4ll, &addr);
1292 _cleanup_address_free_ Address *address = NULL;
1293 _cleanup_route_free_ Route *route = NULL;
1295 log_debug_link(link, "IPv4 link-local release %u.%u.%u.%u",
1296 ADDRESS_FMT_VAL(addr));
1298 r = address_new_dynamic(&address);
1300 log_error_link(link, "Could not allocate address: %s", strerror(-r));
1304 address->family = AF_INET;
1305 address->in_addr.in = addr;
1306 address->prefixlen = 16;
1307 address->scope = RT_SCOPE_LINK;
1309 address_drop(address, link, &address_drop_handler);
1311 r = route_new_dynamic(&route, RTPROT_UNSPEC);
1313 log_error_link(link, "Could not allocate route: %s",
1318 route->family = AF_INET;
1319 route->scope = RT_SCOPE_LINK;
1320 route->metrics = 99;
1322 route_drop(route, link, &route_drop_handler);
1328 static bool ipv4ll_is_bound(sd_ipv4ll *ll) {
1330 struct in_addr addr;
1334 r = sd_ipv4ll_get_address(ll, &addr);
1340 static int ipv4ll_address_claimed(sd_ipv4ll *ll, Link *link) {
1341 struct in_addr address;
1347 r = sd_ipv4ll_get_address(ll, &address);
1351 log_struct_link(LOG_INFO, link,
1352 "MESSAGE=%-*s: IPv4 link-local address %u.%u.%u.%u",
1355 ADDRESS_FMT_VAL(address),
1358 link_enter_set_addresses(link);
1363 static void ipv4ll_handler(sd_ipv4ll *ll, int event, void *userdata){
1364 Link *link = userdata;
1368 assert(link->network);
1369 assert(link->manager);
1371 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1375 case IPV4LL_EVENT_STOP:
1376 case IPV4LL_EVENT_CONFLICT:
1377 r = ipv4ll_address_lost(link);
1379 link_enter_failed(link);
1383 case IPV4LL_EVENT_BIND:
1384 r = ipv4ll_address_claimed(ll, link);
1386 link_enter_failed(link);
1392 log_warning_link(link, "IPv4 link-local error: %s", strerror(-event));
1394 log_warning_link(link, "IPv4 link-local unknown event: %d", event);
1399 static void dhcp6_handler(sd_dhcp6_client *client, int event, void *userdata) {
1400 Link *link = userdata;
1403 assert(link->network);
1404 assert(link->manager);
1406 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1410 case DHCP6_EVENT_STOP:
1411 case DHCP6_EVENT_RESEND_EXPIRE:
1412 case DHCP6_EVENT_RETRANS_MAX:
1413 case DHCP6_EVENT_IP_ACQUIRE:
1414 log_debug_link(link, "DHCPv6 event %d", event);
1420 log_warning_link(link, "DHCPv6 error: %s",
1423 log_warning_link(link, "DHCPv6 unknown event: %d",
1429 static void icmp6_router_handler(sd_icmp6_nd *nd, int event, void *userdata) {
1430 Link *link = userdata;
1434 assert(link->network);
1435 assert(link->manager);
1437 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1441 case ICMP6_EVENT_ROUTER_ADVERTISMENT_NONE:
1442 case ICMP6_EVENT_ROUTER_ADVERTISMENT_OTHER:
1445 case ICMP6_EVENT_ROUTER_ADVERTISMENT_TIMEOUT:
1446 case ICMP6_EVENT_ROUTER_ADVERTISMENT_MANAGED:
1451 log_warning_link(link, "ICMPv6 error: %s",
1454 log_warning_link(link, "ICMPv6 unknown event: %d",
1460 if (link->dhcp6_client)
1463 r = sd_dhcp6_client_new(&link->dhcp6_client);
1467 r = sd_dhcp6_client_attach_event(link->dhcp6_client, NULL, 0);
1469 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
1473 r = sd_dhcp6_client_set_mac(link->dhcp6_client, &link->mac);
1475 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
1479 r = sd_dhcp6_client_set_index(link->dhcp6_client, link->ifindex);
1481 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
1485 r = sd_dhcp6_client_set_callback(link->dhcp6_client, dhcp6_handler,
1488 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
1492 r = sd_dhcp6_client_start(link->dhcp6_client);
1494 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
1497 static int link_acquire_conf(Link *link) {
1501 assert(link->network);
1502 assert(link->manager);
1503 assert(link->manager->event);
1505 if (link->network->ipv4ll) {
1506 assert(link->ipv4ll);
1508 log_debug_link(link, "acquiring IPv4 link-local address");
1510 r = sd_ipv4ll_start(link->ipv4ll);
1512 log_warning_link(link, "could not acquire IPv4 "
1513 "link-local address");
1518 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V4)) {
1519 assert(link->dhcp_client);
1521 log_debug_link(link, "acquiring DHCPv4 lease");
1523 r = sd_dhcp_client_start(link->dhcp_client);
1525 log_warning_link(link, "could not acquire DHCPv4 "
1531 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V6)) {
1532 assert(link->icmp6_router_discovery);
1534 log_debug_link(link, "discovering IPv6 routers");
1536 r = sd_icmp6_router_solicitation_start(link->icmp6_router_discovery);
1538 log_warning_link(link, "could not start IPv6 router discovery");
1546 bool link_has_carrier(unsigned flags, uint8_t operstate) {
1547 /* see Documentation/networking/operstates.txt in the kernel sources */
1549 if (operstate == IF_OPER_UP)
1552 if (operstate == IF_OPER_UNKNOWN)
1553 /* operstate may not be implemented, so fall back to flags */
1554 if ((flags & IFF_LOWER_UP) && !(flags & IFF_DORMANT))
1560 #define FLAG_STRING(string, flag, old, new) \
1561 (((old ^ new) & flag) \
1562 ? ((old & flag) ? (" -" string) : (" +" string)) \
1565 static int link_update_flags(Link *link, sd_rtnl_message *m) {
1566 unsigned flags, unknown_flags_added, unknown_flags_removed, unknown_flags;
1568 bool carrier_gained = false, carrier_lost = false;
1573 r = sd_rtnl_message_link_get_flags(m, &flags);
1575 log_warning_link(link, "Could not get link flags");
1579 r = sd_rtnl_message_read_u8(m, IFLA_OPERSTATE, &operstate);
1581 /* if we got a message without operstate, take it to mean
1582 the state was unchanged */
1583 operstate = link->kernel_operstate;
1585 if ((link->flags == flags) && (link->kernel_operstate == operstate))
1588 if (link->flags != flags) {
1589 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",
1590 FLAG_STRING("LOOPBACK", IFF_LOOPBACK, link->flags, flags),
1591 FLAG_STRING("MASTER", IFF_MASTER, link->flags, flags),
1592 FLAG_STRING("SLAVE", IFF_SLAVE, link->flags, flags),
1593 FLAG_STRING("UP", IFF_UP, link->flags, flags),
1594 FLAG_STRING("DORMANT", IFF_DORMANT, link->flags, flags),
1595 FLAG_STRING("LOWER_UP", IFF_LOWER_UP, link->flags, flags),
1596 FLAG_STRING("RUNNING", IFF_RUNNING, link->flags, flags),
1597 FLAG_STRING("MULTICAST", IFF_MULTICAST, link->flags, flags),
1598 FLAG_STRING("BROADCAST", IFF_BROADCAST, link->flags, flags),
1599 FLAG_STRING("POINTOPOINT", IFF_POINTOPOINT, link->flags, flags),
1600 FLAG_STRING("PROMISC", IFF_PROMISC, link->flags, flags),
1601 FLAG_STRING("ALLMULTI", IFF_ALLMULTI, link->flags, flags),
1602 FLAG_STRING("PORTSEL", IFF_PORTSEL, link->flags, flags),
1603 FLAG_STRING("AUTOMEDIA", IFF_AUTOMEDIA, link->flags, flags),
1604 FLAG_STRING("DYNAMIC", IFF_DYNAMIC, link->flags, flags),
1605 FLAG_STRING("NOARP", IFF_NOARP, link->flags, flags),
1606 FLAG_STRING("NOTRAILERS", IFF_NOTRAILERS, link->flags, flags),
1607 FLAG_STRING("DEBUG", IFF_DEBUG, link->flags, flags),
1608 FLAG_STRING("ECHO", IFF_ECHO, link->flags, flags));
1610 unknown_flags = ~(IFF_LOOPBACK | IFF_MASTER | IFF_SLAVE | IFF_UP |
1611 IFF_DORMANT | IFF_LOWER_UP | IFF_RUNNING |
1612 IFF_MULTICAST | IFF_BROADCAST | IFF_POINTOPOINT |
1613 IFF_PROMISC | IFF_ALLMULTI | IFF_PORTSEL |
1614 IFF_AUTOMEDIA | IFF_DYNAMIC | IFF_NOARP |
1615 IFF_NOTRAILERS | IFF_DEBUG | IFF_ECHO);
1616 unknown_flags_added = ((link->flags ^ flags) & flags & unknown_flags);
1617 unknown_flags_removed = ((link->flags ^ flags) & link->flags & unknown_flags);
1619 /* link flags are currently at most 18 bits, let's align to printing 20 */
1620 if (unknown_flags_added)
1621 log_debug_link(link, "unknown link flags gained: %#.5x (ignoring)",
1622 unknown_flags_added);
1624 if (unknown_flags_removed)
1625 log_debug_link(link, "unknown link flags lost: %#.5x (ignoring)",
1626 unknown_flags_removed);
1629 carrier_gained = !link_has_carrier(link->flags, link->kernel_operstate) &&
1630 link_has_carrier(flags, operstate);
1631 carrier_lost = link_has_carrier(link->flags, link->kernel_operstate) &&
1632 !link_has_carrier(flags, operstate);
1634 link->flags = flags;
1635 link->kernel_operstate = operstate;
1639 if (link->state == LINK_STATE_FAILED ||
1640 link->state == LINK_STATE_UNMANAGED)
1643 if (carrier_gained) {
1644 log_info_link(link, "gained carrier");
1646 if (link->network) {
1647 r = link_acquire_conf(link);
1649 link_enter_failed(link);
1653 } else if (carrier_lost) {
1654 log_info_link(link, "lost carrier");
1656 r = link_stop_clients(link);
1658 link_enter_failed(link);
1666 static int link_up_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
1667 _cleanup_link_unref_ Link *link = userdata;
1672 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1675 r = sd_rtnl_message_get_errno(m);
1677 /* we warn but don't fail the link, as it may
1678 be brought up later */
1679 log_struct_link(LOG_WARNING, link,
1680 "MESSAGE=%-*s: could not bring up interface: %s",
1682 link->ifname, strerror(-r),
1690 static int link_up(Link *link) {
1691 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
1695 assert(link->manager);
1696 assert(link->manager->rtnl);
1698 log_debug_link(link, "bringing link up");
1700 r = sd_rtnl_message_new_link(link->manager->rtnl, &req,
1701 RTM_SETLINK, link->ifindex);
1703 log_error_link(link, "Could not allocate RTM_SETLINK message");
1707 r = sd_rtnl_message_link_set_flags(req, IFF_UP, IFF_UP);
1709 log_error_link(link, "Could not set link flags: %s", strerror(-r));
1713 r = sd_rtnl_call_async(link->manager->rtnl, req, link_up_handler, link, 0, NULL);
1715 log_error_link(link,
1716 "Could not send rtnetlink message: %s", strerror(-r));
1725 static int link_joined(Link *link) {
1729 assert(link->state == LINK_STATE_ENSLAVING);
1730 assert(link->network);
1732 log_debug_link(link, "joined netdev");
1734 if (!(link->flags & IFF_UP)) {
1737 link_enter_failed(link);
1742 return link_enter_set_addresses(link);
1745 static int netdev_join_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
1746 _cleanup_link_unref_ Link *link = userdata;
1750 assert(IN_SET(link->state, LINK_STATE_ENSLAVING, LINK_STATE_FAILED,
1751 LINK_STATE_LINGER));
1752 assert(link->network);
1756 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1759 r = sd_rtnl_message_get_errno(m);
1760 if (r < 0 && r != -EEXIST) {
1761 log_struct_link(LOG_ERR, link,
1762 "MESSAGE=%-*s: could not join netdev: %s",
1764 link->ifname, strerror(-r),
1767 link_enter_failed(link);
1771 if (link->enslaving <= 0)
1777 static int link_enter_join_netdev(Link *link) {
1778 NetDev *vlan, *macvlan, *vxlan;
1783 assert(link->network);
1784 assert(link->state == LINK_STATE_INITIALIZING);
1786 link->state = LINK_STATE_ENSLAVING;
1790 if (!link->network->bridge &&
1791 !link->network->bond &&
1792 !link->network->tunnel &&
1793 hashmap_isempty(link->network->vlans) &&
1794 hashmap_isempty(link->network->macvlans) &&
1795 hashmap_isempty(link->network->vxlans))
1796 return link_joined(link);
1798 if (link->network->bond) {
1799 log_struct_link(LOG_DEBUG, link,
1800 "MESSAGE=%-*s: enslaving by '%s'",
1802 link->ifname, link->network->bond->ifname,
1803 NETDEVIF(link->network->bond),
1806 r = netdev_join(link->network->bond, link, &netdev_join_handler);
1808 log_struct_link(LOG_WARNING, link,
1809 "MESSAGE=%-*s: could not join netdev '%s': %s",
1811 link->ifname, link->network->bond->ifname, strerror(-r),
1812 NETDEVIF(link->network->bond),
1814 link_enter_failed(link);
1821 if (link->network->bridge) {
1822 log_struct_link(LOG_DEBUG, link,
1823 "MESSAGE=%-*s: enslaving by '%s'",
1825 link->ifname, link->network->bridge->ifname,
1826 NETDEVIF(link->network->bridge),
1829 r = netdev_join(link->network->bridge, link, &netdev_join_handler);
1831 log_struct_link(LOG_WARNING, link,
1832 "MESSAGE=%-*s: could not join netdev '%s': %s",
1834 link->ifname, link->network->bridge->ifname, strerror(-r),
1835 NETDEVIF(link->network->bridge),
1837 link_enter_failed(link);
1844 if (link->network->tunnel) {
1845 log_struct_link(LOG_DEBUG, link,
1846 "MESSAGE=%-*s: enslaving by '%s'",
1848 link->ifname, link->network->tunnel->ifname,
1849 NETDEVIF(link->network->tunnel),
1852 r = netdev_join(link->network->tunnel, link, &netdev_join_handler);
1854 log_struct_link(LOG_WARNING, link,
1855 "MESSAGE=%-*s: could not join netdev '%s': %s",
1857 link->ifname, link->network->tunnel->ifname, strerror(-r),
1858 NETDEVIF(link->network->tunnel),
1860 link_enter_failed(link);
1867 HASHMAP_FOREACH(vlan, link->network->vlans, i) {
1868 log_struct_link(LOG_DEBUG, link,
1869 "MESSAGE=%-*s: enslaving by '%s'",
1871 link->ifname, vlan->ifname, NETDEVIF(vlan), NULL);
1873 r = netdev_join(vlan, link, &netdev_join_handler);
1875 log_struct_link(LOG_WARNING, link,
1876 "MESSAGE=%-*s: could not join netdev '%s': %s",
1878 link->ifname, vlan->ifname, strerror(-r),
1879 NETDEVIF(vlan), NULL);
1880 link_enter_failed(link);
1887 HASHMAP_FOREACH(macvlan, link->network->macvlans, i) {
1888 log_struct_link(LOG_DEBUG, link,
1889 "MESSAGE=%-*s: enslaving by '%s'",
1891 link->ifname, macvlan->ifname, NETDEVIF(macvlan), NULL);
1893 r = netdev_join(macvlan, link, &netdev_join_handler);
1895 log_struct_link(LOG_WARNING, link,
1896 "MESSAGE=%-*s: could not join netdev '%s': %s",
1898 link->ifname, macvlan->ifname, strerror(-r),
1899 NETDEVIF(macvlan), NULL);
1900 link_enter_failed(link);
1907 HASHMAP_FOREACH(vxlan, link->network->vxlans, i) {
1908 log_struct_link(LOG_DEBUG, link,
1909 "MESSAGE=%*s: enslaving by '%s'",
1911 link->ifname, vxlan->ifname, NETDEVIF(vxlan), NULL);
1913 r = netdev_join(vxlan, link, &netdev_join_handler);
1915 log_struct_link(LOG_WARNING, link,
1916 "MESSAGE=%*s: could not join netdev '%s': %s",
1918 link->ifname, vxlan->ifname, strerror(-r),
1919 NETDEVIF(vxlan), NULL);
1920 link_enter_failed(link);
1930 static int link_configure(Link *link) {
1934 assert(link->state == LINK_STATE_INITIALIZING);
1936 if (link->network->ipv4ll) {
1939 r = sd_ipv4ll_new(&link->ipv4ll);
1943 if (link->udev_device) {
1944 r = net_get_unique_predictable_data(link->udev_device, seed);
1946 r = sd_ipv4ll_set_address_seed(link->ipv4ll, seed);
1952 r = sd_ipv4ll_attach_event(link->ipv4ll, NULL, 0);
1956 r = sd_ipv4ll_set_mac(link->ipv4ll, &link->mac);
1960 r = sd_ipv4ll_set_index(link->ipv4ll, link->ifindex);
1964 r = sd_ipv4ll_set_callback(link->ipv4ll, ipv4ll_handler, link);
1969 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V4)) {
1970 r = sd_dhcp_client_new(&link->dhcp_client);
1974 r = sd_dhcp_client_attach_event(link->dhcp_client, NULL, 0);
1978 r = sd_dhcp_client_set_mac(link->dhcp_client, &link->mac);
1982 r = sd_dhcp_client_set_index(link->dhcp_client, link->ifindex);
1986 r = sd_dhcp_client_set_callback(link->dhcp_client, dhcp_handler, link);
1990 r = sd_dhcp_client_set_request_broadcast(link->dhcp_client, link->network->dhcp_broadcast);
1994 if (link->network->dhcp_mtu) {
1995 r = sd_dhcp_client_set_request_option(link->dhcp_client, 26);
2000 if (link->network->dhcp_routes) {
2001 r = sd_dhcp_client_set_request_option(link->dhcp_client, DHCP_OPTION_STATIC_ROUTE);
2004 r = sd_dhcp_client_set_request_option(link->dhcp_client, DHCP_OPTION_CLASSLESS_STATIC_ROUTE);
2009 if (link->network->dhcp_sendhost) {
2010 _cleanup_free_ char *hostname = gethostname_malloc();
2014 if (!is_localhost(hostname)) {
2015 r = sd_dhcp_client_set_hostname(link->dhcp_client, hostname);
2021 if (link->network->dhcp_vendor_class_identifier) {
2022 r = sd_dhcp_client_set_vendor_class_identifier(link->dhcp_client,
2023 link->network->dhcp_vendor_class_identifier);
2029 if (link->network->dhcp_server) {
2030 r = sd_dhcp_server_new(&link->dhcp_server, link->ifindex);
2034 r = sd_dhcp_server_attach_event(link->dhcp_server, NULL, 0);
2039 if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V6)) {
2040 r = sd_icmp6_nd_new(&link->icmp6_router_discovery);
2044 r = sd_icmp6_nd_attach_event(link->icmp6_router_discovery,
2049 r = sd_icmp6_nd_set_mac(link->icmp6_router_discovery,
2054 r = sd_icmp6_nd_set_index(link->icmp6_router_discovery,
2059 r = sd_icmp6_nd_set_callback(link->icmp6_router_discovery,
2060 icmp6_router_handler, link);
2065 if (link_has_carrier(link->flags, link->kernel_operstate)) {
2066 r = link_acquire_conf(link);
2071 return link_enter_join_netdev(link);
2074 static int link_initialized_and_synced(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
2075 _cleanup_link_unref_ Link *link = userdata;
2080 assert(link->ifname);
2081 assert(link->manager);
2083 if (link->state != LINK_STATE_INITIALIZING)
2086 log_debug_link(link, "link state is up-to-date");
2088 r = network_get(link->manager, link->udev_device, link->ifname, &link->mac, &network);
2090 link_enter_unmanaged(link);
2095 r = network_apply(link->manager, network, link);
2099 r = link_configure(link);
2106 int link_initialized(Link *link, struct udev_device *device) {
2107 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
2111 assert(link->manager);
2112 assert(link->manager->rtnl);
2115 if (link->state != LINK_STATE_INITIALIZING)
2118 if (link->udev_device)
2121 log_debug_link(link, "udev initialized link");
2123 link->udev_device = udev_device_ref(device);
2125 /* udev has initialized the link, but we don't know if we have yet processed
2126 the NEWLINK messages with the latest state. Do a GETLINK, when it returns
2127 we know that the pending NEWLINKs have already been processed and that we
2130 r = sd_rtnl_message_new_link(link->manager->rtnl, &req, RTM_GETLINK, link->ifindex);
2134 r = sd_rtnl_call_async(link->manager->rtnl, req, link_initialized_and_synced, link, 0, NULL);
2143 int link_rtnl_process_address(sd_rtnl *rtnl, sd_rtnl_message *message, void *userdata) {
2144 Manager *m = userdata;
2147 _cleanup_address_free_ Address *address = NULL;
2149 char buf[INET6_ADDRSTRLEN];
2150 bool address_dropped = false;
2157 r = sd_rtnl_message_get_type(message, &type);
2159 log_warning("rtnl: could not get message type");
2163 r = sd_rtnl_message_addr_get_ifindex(message, &ifindex);
2164 if (r < 0 || ifindex <= 0) {
2165 log_warning("rtnl: received address message without valid ifindex, ignoring");
2168 r = link_get(m, ifindex, &link);
2169 if (r < 0 || !link) {
2170 log_warning("rtnl: received address for a nonexistent link, ignoring");
2175 r = address_new_dynamic(&address);
2179 r = sd_rtnl_message_addr_get_family(message, &address->family);
2180 if (r < 0 || !IN_SET(address->family, AF_INET, AF_INET6)) {
2181 log_warning_link(link, "rtnl: received address with invalid family, ignoring");
2185 r = sd_rtnl_message_addr_get_prefixlen(message, &address->prefixlen);
2187 log_warning_link(link, "rtnl: received address with invalid prefixlen, ignoring");
2191 r = sd_rtnl_message_addr_get_scope(message, &address->scope);
2193 log_warning_link(link, "rtnl: received address with invalid scope, ignoring");
2197 switch (address->family) {
2199 r = sd_rtnl_message_read_in_addr(message, IFA_LOCAL, &address->in_addr.in);
2201 log_warning_link(link, "rtnl: received address without valid address, ignoring");
2208 r = sd_rtnl_message_read_in6_addr(message, IFA_ADDRESS, &address->in_addr.in6);
2210 log_warning_link(link, "rtnl: received address without valid address, ignoring");
2217 assert_not_reached("invalid address family");
2220 if (!inet_ntop(address->family, &address->in_addr, buf, INET6_ADDRSTRLEN)) {
2221 log_warning_link(link, "could not print address");
2225 LIST_FOREACH(addresses, ad, link->addresses) {
2226 if (address_equal(ad, address)) {
2227 LIST_REMOVE(addresses, link->addresses, ad);
2231 address_dropped = true;
2239 if (!address_dropped)
2240 log_debug_link(link, "added address: %s/%u", buf,
2241 address->prefixlen);
2243 log_debug_link(link, "updated address: %s/%u", buf,
2244 address->prefixlen);
2246 LIST_PREPEND(addresses, link->addresses, address);
2253 if (address_dropped) {
2254 log_debug_link(link, "removed address: %s/%u", buf,
2255 address->prefixlen);
2259 log_warning_link(link, "removing non-existent address: %s/%u",
2260 buf, address->prefixlen);
2264 assert_not_reached("Received invalid RTNL message type");
2270 int link_add(Manager *m, sd_rtnl_message *message, Link **ret) {
2272 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
2273 _cleanup_udev_device_unref_ struct udev_device *device = NULL;
2274 char ifindex_str[2 + DECIMAL_STR_MAX(int)];
2282 r = link_new(m, message, ret);
2288 log_debug_link(link, "link %"PRIu64" added", link->ifindex);
2290 r = sd_rtnl_message_new_addr(m->rtnl, &req, RTM_GETADDR, link->ifindex, 0);
2294 r = sd_rtnl_call_async(m->rtnl, req, link_get_address_handler, link, 0, NULL);
2300 if (detect_container(NULL) <= 0) {
2301 /* not in a container, udev will be around */
2302 sprintf(ifindex_str, "n%"PRIu64, link->ifindex);
2303 device = udev_device_new_from_device_id(m->udev, ifindex_str);
2305 log_warning_link(link, "could not find udev device");
2309 if (udev_device_get_is_initialized(device) <= 0) {
2311 log_debug_link(link, "udev initializing link...");
2315 r = link_initialized(link, device);
2319 /* we are calling a callback directly, so must take a ref */
2322 r = link_initialized_and_synced(m->rtnl, NULL, link);
2330 int link_update(Link *link, sd_rtnl_message *m) {
2331 struct ether_addr mac;
2336 assert(link->ifname);
2339 if (link->state == LINK_STATE_LINGER) {
2341 log_info_link(link, "link readded");
2342 link->state = LINK_STATE_ENSLAVING;
2345 r = sd_rtnl_message_read_string(m, IFLA_IFNAME, &ifname);
2346 if (r >= 0 && !streq(ifname, link->ifname)) {
2347 log_info_link(link, "renamed to %s", ifname);
2350 link->ifname = strdup(ifname);
2355 if (!link->original_mtu) {
2356 r = sd_rtnl_message_read_u16(m, IFLA_MTU, &link->original_mtu);
2358 log_debug_link(link, "saved original MTU: %"
2359 PRIu16, link->original_mtu);
2362 /* The kernel may broadcast NEWLINK messages without the MAC address
2363 set, simply ignore them. */
2364 r = sd_rtnl_message_read_ether_addr(m, IFLA_ADDRESS, &mac);
2366 if (memcmp(link->mac.ether_addr_octet, mac.ether_addr_octet, ETH_ALEN)) {
2368 memcpy(link->mac.ether_addr_octet, mac.ether_addr_octet, ETH_ALEN);
2370 log_debug_link(link, "MAC address: "
2371 "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx",
2372 mac.ether_addr_octet[0],
2373 mac.ether_addr_octet[1],
2374 mac.ether_addr_octet[2],
2375 mac.ether_addr_octet[3],
2376 mac.ether_addr_octet[4],
2377 mac.ether_addr_octet[5]);
2380 r = sd_ipv4ll_set_mac(link->ipv4ll, &link->mac);
2382 log_warning_link(link, "Could not update MAC "
2383 "address in IPv4LL client: %s",
2389 if (link->dhcp_client) {
2390 r = sd_dhcp_client_set_mac(link->dhcp_client, &link->mac);
2392 log_warning_link(link, "Could not update MAC "
2393 "address in DHCP client: %s",
2399 if (link->dhcp6_client) {
2400 r = sd_dhcp6_client_set_mac(link->dhcp6_client,
2403 log_warning_link(link, "Could not update MAC address in DHCPv6 client: %s",
2411 return link_update_flags(link, m);
2414 static void link_update_operstate(Link *link) {
2418 if (link->kernel_operstate == IF_OPER_DORMANT)
2419 link->operstate = LINK_OPERSTATE_DORMANT;
2420 else if (link_has_carrier(link->flags, link->kernel_operstate)) {
2422 uint8_t scope = RT_SCOPE_NOWHERE;
2424 /* if we have carrier, check what addresses we have */
2425 LIST_FOREACH(addresses, address, link->addresses) {
2426 if (address->scope < scope)
2427 scope = address->scope;
2430 if (scope < RT_SCOPE_SITE)
2431 /* universally accessible addresses found */
2432 link->operstate = LINK_OPERSTATE_ROUTABLE;
2433 else if (scope < RT_SCOPE_HOST)
2434 /* only link or site local addresses found */
2435 link->operstate = LINK_OPERSTATE_DEGRADED;
2437 /* no useful addresses found */
2438 link->operstate = LINK_OPERSTATE_CARRIER;
2440 link->operstate = LINK_OPERSTATE_UNKNOWN;
2443 int link_save(Link *link) {
2444 _cleanup_free_ char *temp_path = NULL;
2445 _cleanup_fclose_ FILE *f = NULL;
2446 const char *admin_state, *oper_state;
2450 assert(link->state_file);
2451 assert(link->lease_file);
2452 assert(link->manager);
2454 link_update_operstate(link);
2456 r = manager_save(link->manager);
2460 if (link->state == LINK_STATE_LINGER) {
2461 unlink(link->state_file);
2465 admin_state = link_state_to_string(link->state);
2466 assert(admin_state);
2468 oper_state = link_operstate_to_string(link->operstate);
2471 r = fopen_temporary(link->state_file, &f, &temp_path);
2475 fchmod(fileno(f), 0644);
2478 "# This is private data. Do not parse.\n"
2481 admin_state, oper_state);
2483 if (link->network) {
2488 if (link->network->dhcp_dns &&
2490 const struct in_addr *addresses;
2492 r = sd_dhcp_lease_get_dns(link->dhcp_lease, &addresses);
2494 serialize_in_addrs(f, addresses, r);
2495 if (link->network->dns)
2500 STRV_FOREACH(address, link->network->dns)
2501 fprintf(f, "%s%s", *address,
2502 (address + 1 ? " " : ""));
2508 if (link->network->dhcp_ntp &&
2510 const struct in_addr *addresses;
2512 r = sd_dhcp_lease_get_ntp(link->dhcp_lease, &addresses);
2514 serialize_in_addrs(f, addresses, r);
2515 if (link->network->ntp)
2520 STRV_FOREACH(address, link->network->ntp)
2521 fprintf(f, "%s%s", *address,
2522 (address + 1 ? " " : ""));
2527 if (link->dhcp_lease) {
2528 assert(link->network);
2530 r = dhcp_lease_save(link->dhcp_lease, link->lease_file);
2538 unlink(link->lease_file);
2542 if (ferror(f) || rename(temp_path, link->state_file) < 0) {
2544 unlink(link->state_file);
2550 log_error_link(link, "Failed to save link data to %s: %s", link->state_file, strerror(-r));
2555 static const char* const link_state_table[_LINK_STATE_MAX] = {
2556 [LINK_STATE_INITIALIZING] = "initializing",
2557 [LINK_STATE_ENSLAVING] = "configuring",
2558 [LINK_STATE_SETTING_ADDRESSES] = "configuring",
2559 [LINK_STATE_SETTING_ROUTES] = "configuring",
2560 [LINK_STATE_CONFIGURED] = "configured",
2561 [LINK_STATE_UNMANAGED] = "unmanaged",
2562 [LINK_STATE_FAILED] = "failed",
2563 [LINK_STATE_LINGER] = "linger",
2566 DEFINE_STRING_TABLE_LOOKUP(link_state, LinkState);
2568 static const char* const link_operstate_table[_LINK_OPERSTATE_MAX] = {
2569 [LINK_OPERSTATE_UNKNOWN] = "unknown",
2570 [LINK_OPERSTATE_DORMANT] = "dormant",
2571 [LINK_OPERSTATE_CARRIER] = "carrier",
2572 [LINK_OPERSTATE_DEGRADED] = "degraded",
2573 [LINK_OPERSTATE_ROUTABLE] = "routable",
2576 DEFINE_STRING_TABLE_LOOKUP(link_operstate, LinkOperationalState);
2578 static const char* const dhcp_support_table[_DHCP_SUPPORT_MAX] = {
2579 [DHCP_SUPPORT_NONE] = "none",
2580 [DHCP_SUPPORT_BOTH] = "both",
2581 [DHCP_SUPPORT_V4] = "v4",
2582 [DHCP_SUPPORT_V6] = "v6",
2585 DEFINE_STRING_TABLE_LOOKUP(dhcp_support, DHCPSupport);
2587 int config_parse_dhcp(
2589 const char *filename,
2591 const char *section,
2592 unsigned section_line,
2599 DHCPSupport *dhcp = data;
2607 /* Our enum shall be a superset of booleans, hence first try
2608 * to parse as boolean, and then as enum */
2610 k = parse_boolean(rvalue);
2612 *dhcp = DHCP_SUPPORT_BOTH;
2614 *dhcp = DHCP_SUPPORT_NONE;
2618 s = dhcp_support_from_string(rvalue);
2620 log_syntax(unit, LOG_ERR, filename, line, -s, "Failed to parse DHCP option, ignoring: %s", rvalue);