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>
26 #include "networkd-link.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 "dhcp-lease-internal.h"
38 static bool link_dhcp6_enabled(Link *link) {
39 if (link->flags & IFF_LOOPBACK)
45 return IN_SET(link->network->dhcp, DHCP_SUPPORT_V6, DHCP_SUPPORT_BOTH);
48 static bool link_dhcp4_enabled(Link *link) {
49 if (link->flags & IFF_LOOPBACK)
55 return IN_SET(link->network->dhcp, DHCP_SUPPORT_V4, DHCP_SUPPORT_BOTH);
58 static bool link_dhcp4_server_enabled(Link *link) {
59 if (link->flags & IFF_LOOPBACK)
65 return link->network->dhcp_server;
68 static bool link_ipv4ll_enabled(Link *link) {
69 if (link->flags & IFF_LOOPBACK)
75 return link->network->ipv4ll;
78 #define FLAG_STRING(string, flag, old, new) \
79 (((old ^ new) & flag) \
80 ? ((old & flag) ? (" -" string) : (" +" string)) \
83 static int link_update_flags(Link *link, sd_rtnl_message *m) {
84 unsigned flags, unknown_flags_added, unknown_flags_removed, unknown_flags;
90 r = sd_rtnl_message_link_get_flags(m, &flags);
92 log_link_warning(link, "Could not get link flags");
96 r = sd_rtnl_message_read_u8(m, IFLA_OPERSTATE, &operstate);
98 /* if we got a message without operstate, take it to mean
99 the state was unchanged */
100 operstate = link->kernel_operstate;
102 if ((link->flags == flags) && (link->kernel_operstate == operstate))
105 if (link->flags != flags) {
106 log_link_debug(link, "flags change:%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s",
107 FLAG_STRING("LOOPBACK", IFF_LOOPBACK, link->flags, flags),
108 FLAG_STRING("MASTER", IFF_MASTER, link->flags, flags),
109 FLAG_STRING("SLAVE", IFF_SLAVE, link->flags, flags),
110 FLAG_STRING("UP", IFF_UP, link->flags, flags),
111 FLAG_STRING("DORMANT", IFF_DORMANT, link->flags, flags),
112 FLAG_STRING("LOWER_UP", IFF_LOWER_UP, link->flags, flags),
113 FLAG_STRING("RUNNING", IFF_RUNNING, link->flags, flags),
114 FLAG_STRING("MULTICAST", IFF_MULTICAST, link->flags, flags),
115 FLAG_STRING("BROADCAST", IFF_BROADCAST, link->flags, flags),
116 FLAG_STRING("POINTOPOINT", IFF_POINTOPOINT, link->flags, flags),
117 FLAG_STRING("PROMISC", IFF_PROMISC, link->flags, flags),
118 FLAG_STRING("ALLMULTI", IFF_ALLMULTI, link->flags, flags),
119 FLAG_STRING("PORTSEL", IFF_PORTSEL, link->flags, flags),
120 FLAG_STRING("AUTOMEDIA", IFF_AUTOMEDIA, link->flags, flags),
121 FLAG_STRING("DYNAMIC", IFF_DYNAMIC, link->flags, flags),
122 FLAG_STRING("NOARP", IFF_NOARP, link->flags, flags),
123 FLAG_STRING("NOTRAILERS", IFF_NOTRAILERS, link->flags, flags),
124 FLAG_STRING("DEBUG", IFF_DEBUG, link->flags, flags),
125 FLAG_STRING("ECHO", IFF_ECHO, link->flags, flags));
127 unknown_flags = ~(IFF_LOOPBACK | IFF_MASTER | IFF_SLAVE | IFF_UP |
128 IFF_DORMANT | IFF_LOWER_UP | IFF_RUNNING |
129 IFF_MULTICAST | IFF_BROADCAST | IFF_POINTOPOINT |
130 IFF_PROMISC | IFF_ALLMULTI | IFF_PORTSEL |
131 IFF_AUTOMEDIA | IFF_DYNAMIC | IFF_NOARP |
132 IFF_NOTRAILERS | IFF_DEBUG | IFF_ECHO);
133 unknown_flags_added = ((link->flags ^ flags) & flags & unknown_flags);
134 unknown_flags_removed = ((link->flags ^ flags) & link->flags & unknown_flags);
136 /* link flags are currently at most 18 bits, let's align to
138 if (unknown_flags_added)
140 "unknown link flags gained: %#.5x (ignoring)",
141 unknown_flags_added);
143 if (unknown_flags_removed)
145 "unknown link flags lost: %#.5x (ignoring)",
146 unknown_flags_removed);
150 link->kernel_operstate = operstate;
157 static int link_new(Manager *manager, sd_rtnl_message *message, Link **ret) {
158 _cleanup_link_unref_ Link *link = NULL;
167 r = sd_rtnl_message_get_type(message, &type);
170 else if (type != RTM_NEWLINK)
173 r = sd_rtnl_message_link_get_ifindex(message, &ifindex);
176 else if (ifindex <= 0)
179 r = sd_rtnl_message_read_string(message, IFLA_IFNAME, &ifname);
183 link = new0(Link, 1);
188 link->manager = manager;
189 link->state = LINK_STATE_PENDING;
190 link->ifindex = ifindex;
191 link->ifname = strdup(ifname);
195 r = sd_rtnl_message_read_ether_addr(message, IFLA_ADDRESS, &link->mac);
197 log_link_debug(link, "MAC address not found for new device, continuing without");
199 r = asprintf(&link->state_file, "/run/systemd/netif/links/%d",
204 r = asprintf(&link->lease_file, "/run/systemd/netif/leases/%d",
209 r = hashmap_ensure_allocated(&manager->links, NULL);
213 r = hashmap_put(manager->links, INT_TO_PTR(link->ifindex), link);
217 r = link_update_flags(link, message);
227 static void link_free(Link *link) {
233 while ((address = link->addresses)) {
234 LIST_REMOVE(addresses, link->addresses, address);
235 address_free(address);
238 while ((address = link->pool_addresses)) {
239 LIST_REMOVE(addresses, link->pool_addresses, address);
240 address_free(address);
243 sd_dhcp_client_unref(link->dhcp_client);
244 sd_dhcp_lease_unref(link->dhcp_lease);
246 unlink(link->lease_file);
247 free(link->lease_file);
249 sd_ipv4ll_unref(link->ipv4ll);
250 sd_dhcp6_client_unref(link->dhcp6_client);
251 sd_icmp6_nd_unref(link->icmp6_router_discovery);
254 hashmap_remove(link->manager->links, INT_TO_PTR(link->ifindex));
258 unlink(link->state_file);
259 free(link->state_file);
261 udev_device_unref(link->udev_device);
266 Link *link_unref(Link *link) {
267 if (link && (-- link->n_ref <= 0))
273 Link *link_ref(Link *link) {
275 assert_se(++ link->n_ref >= 2);
280 int link_get(Manager *m, int ifindex, Link **ret) {
287 link = hashmap_get(m->links, INT_TO_PTR(ifindex));
296 void link_drop(Link *link) {
297 if (!link || link->state == LINK_STATE_LINGER)
300 link->state = LINK_STATE_LINGER;
302 log_link_debug(link, "link removed");
309 static void link_enter_unmanaged(Link *link) {
312 log_link_debug(link, "unmanaged");
314 link->state = LINK_STATE_UNMANAGED;
319 static int link_stop_clients(Link *link) {
323 assert(link->manager);
324 assert(link->manager->event);
329 if (link->dhcp_client) {
330 k = sd_dhcp_client_stop(link->dhcp_client);
332 log_link_warning(link, "Could not stop DHCPv4 client: %s",
339 k = sd_ipv4ll_stop(link->ipv4ll);
341 log_link_warning(link, "Could not stop IPv4 link-local: %s",
347 if(link->icmp6_router_discovery) {
349 if (link->dhcp6_client) {
350 k = sd_dhcp6_client_stop(link->dhcp6_client);
352 log_link_warning(link, "Could not stop DHCPv6 client: %s",
358 k = sd_icmp6_nd_stop(link->icmp6_router_discovery);
360 log_link_warning(link,
361 "Could not stop ICMPv6 router discovery: %s",
370 void link_enter_failed(Link *link) {
373 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
376 log_link_warning(link, "failed");
378 link->state = LINK_STATE_FAILED;
380 link_stop_clients(link);
385 static Address* link_find_dhcp_server_address(Link *link) {
389 assert(link->network);
391 /* The the first statically configured address if there is any */
392 LIST_FOREACH(addresses, address, link->network->static_addresses) {
394 if (address->family != AF_INET)
397 if (in_addr_is_null(address->family, &address->in_addr))
403 /* If that didn't work, find a suitable address we got from the pool */
404 LIST_FOREACH(addresses, address, link->pool_addresses) {
405 if (address->family != AF_INET)
414 static int link_enter_configured(Link *link) {
418 assert(link->network);
419 assert(link->state == LINK_STATE_SETTING_ROUTES);
421 if (link_dhcp4_server_enabled(link) &&
422 !sd_dhcp_server_is_running(link->dhcp_server)) {
423 struct in_addr pool_start;
426 address = link_find_dhcp_server_address(link);
428 log_link_warning(link,
429 "Failed to find suitable address for DHCPv4 server instance.");
430 link_enter_failed(link);
434 log_link_debug(link, "offering DHCPv4 leases");
436 r = sd_dhcp_server_set_address(link->dhcp_server,
437 &address->in_addr.in,
442 /* offer 32 addresses starting from the address following the server address */
443 pool_start.s_addr = htobe32(be32toh(address->in_addr.in.s_addr) + 1);
444 r = sd_dhcp_server_set_lease_pool(link->dhcp_server,
450 r = sd_dhcp_server_set_router(link->dhcp_server,
451 &main_address->in_addr.in);
455 r = sd_dhcp_server_set_prefixlen(link->dhcp_server,
456 main_address->prefixlen);
461 r = sd_dhcp_server_start(link->dhcp_server);
463 log_link_warning(link, "could not start DHCPv4 server "
464 "instance: %s", strerror(-r));
466 link_enter_failed(link);
472 log_link_info(link, "link configured");
474 link->state = LINK_STATE_CONFIGURED;
481 void link_client_handler(Link *link) {
483 assert(link->network);
485 if (!link->static_configured)
488 if (link_ipv4ll_enabled(link))
489 if (!link->ipv4ll_address ||
493 if (link_dhcp4_enabled(link) && !link->dhcp4_configured)
496 if (link->state != LINK_STATE_CONFIGURED)
497 link_enter_configured(link);
502 static int route_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
503 _cleanup_link_unref_ Link *link = userdata;
506 assert(link->link_messages > 0);
507 assert(IN_SET(link->state, LINK_STATE_SETTING_ADDRESSES,
508 LINK_STATE_SETTING_ROUTES, LINK_STATE_FAILED,
511 link->link_messages --;
513 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
516 r = sd_rtnl_message_get_errno(m);
517 if (r < 0 && r != -EEXIST)
518 log_link_warning_errno(link, -r, "%-*s: could not set route: %m", IFNAMSIZ, link->ifname);
520 if (link->link_messages == 0) {
521 log_link_debug(link, "routes set");
522 link->static_configured = true;
523 link_client_handler(link);
529 static int link_enter_set_routes(Link *link) {
534 assert(link->network);
535 assert(link->state == LINK_STATE_SETTING_ADDRESSES);
537 link->state = LINK_STATE_SETTING_ROUTES;
539 LIST_FOREACH(routes, rt, link->network->static_routes) {
540 r = route_configure(rt, link, &route_handler);
542 log_link_warning(link,
543 "could not set routes: %s",
545 link_enter_failed(link);
549 link->link_messages ++;
552 if (link->link_messages == 0) {
553 link->static_configured = true;
554 link_client_handler(link);
556 log_link_debug(link, "setting routes");
561 int link_route_drop_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
562 _cleanup_link_unref_ Link *link = userdata;
567 assert(link->ifname);
569 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
572 r = sd_rtnl_message_get_errno(m);
573 if (r < 0 && r != -ESRCH)
574 log_link_warning_errno(link, -r, "%-*s: could not drop route: %m", IFNAMSIZ, link->ifname);
579 int link_get_address_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
580 _cleanup_link_unref_ Link *link = userdata;
586 assert(link->manager);
588 for (; m; m = sd_rtnl_message_next(m)) {
589 r = sd_rtnl_message_get_errno(m);
591 log_link_debug(link, "getting address failed: %s",
596 r = link_rtnl_process_address(rtnl, m, link->manager);
598 log_link_warning(link, "could not process address: %s",
605 static int address_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
606 _cleanup_link_unref_ Link *link = userdata;
612 assert(link->ifname);
613 assert(link->link_messages > 0);
614 assert(IN_SET(link->state, LINK_STATE_SETTING_ADDRESSES,
615 LINK_STATE_FAILED, LINK_STATE_LINGER));
617 link->link_messages --;
619 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
622 r = sd_rtnl_message_get_errno(m);
623 if (r < 0 && r != -EEXIST)
624 log_link_warning_errno(link, -r, "%-*s: could not set address: %m", IFNAMSIZ, link->ifname);
626 /* calling handler directly so take a ref */
628 link_get_address_handler(rtnl, m, link);
631 if (link->link_messages == 0) {
632 log_link_debug(link, "addresses set");
633 link_enter_set_routes(link);
639 static int link_enter_set_addresses(Link *link) {
644 assert(link->network);
645 assert(link->state != _LINK_STATE_INVALID);
647 link->state = LINK_STATE_SETTING_ADDRESSES;
649 LIST_FOREACH(addresses, ad, link->network->static_addresses) {
650 r = address_configure(ad, link, &address_handler);
652 log_link_warning(link,
653 "could not set addresses: %s",
655 link_enter_failed(link);
659 link->link_messages ++;
662 if (link->link_messages == 0) {
663 link_enter_set_routes(link);
665 log_link_debug(link, "setting addresses");
670 int link_address_drop_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
671 _cleanup_link_unref_ Link *link = userdata;
676 assert(link->ifname);
678 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
681 r = sd_rtnl_message_get_errno(m);
682 if (r < 0 && r != -EADDRNOTAVAIL)
683 log_link_warning_errno(link, -r, "%-*s: could not drop address: %m", IFNAMSIZ, link->ifname);
688 static int set_hostname_handler(sd_bus *bus, sd_bus_message *m, void *userdata,
689 sd_bus_error *ret_error) {
690 _cleanup_link_unref_ Link *link = userdata;
695 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
698 r = sd_bus_message_get_errno(m);
700 log_link_warning(link, "Could not set hostname: %s",
706 int link_set_hostname(Link *link, const char *hostname) {
707 _cleanup_bus_message_unref_ sd_bus_message *m = NULL;
711 assert(link->manager);
714 log_link_debug(link, "Setting transient hostname: '%s'", hostname);
716 if (!link->manager->bus) {
717 /* TODO: replace by assert when we can rely on kdbus */
719 "Not connected to system bus, ignoring transient hostname.");
723 r = sd_bus_message_new_method_call(
726 "org.freedesktop.hostname1",
727 "/org/freedesktop/hostname1",
728 "org.freedesktop.hostname1",
733 r = sd_bus_message_append(m, "sb", hostname, false);
737 r = sd_bus_call_async(link->manager->bus, NULL, m, set_hostname_handler,
740 log_link_error(link, "Could not set transient hostname: %s",
750 static int set_mtu_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
751 _cleanup_link_unref_ Link *link = userdata;
756 assert(link->ifname);
758 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
761 r = sd_rtnl_message_get_errno(m);
763 log_link_warning_errno(link, -r, "%-*s: could not set MTU: %m", IFNAMSIZ, link->ifname);
768 int link_set_mtu(Link *link, uint32_t mtu) {
769 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
773 assert(link->manager);
774 assert(link->manager->rtnl);
776 log_link_debug(link, "setting MTU: %" PRIu32, mtu);
778 r = sd_rtnl_message_new_link(link->manager->rtnl, &req,
779 RTM_SETLINK, link->ifindex);
781 log_link_error(link, "Could not allocate RTM_SETLINK message");
785 r = sd_rtnl_message_append_u32(req, IFLA_MTU, mtu);
787 log_link_error(link, "Could not append MTU: %s", strerror(-r));
791 r = sd_rtnl_call_async(link->manager->rtnl, req, set_mtu_handler, link,
795 "Could not send rtnetlink message: %s",
805 static void dhcp6_handler(sd_dhcp6_client *client, int event, void *userdata) {
806 Link *link = userdata;
809 assert(link->network);
810 assert(link->manager);
812 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
816 case DHCP6_EVENT_STOP:
817 case DHCP6_EVENT_RESEND_EXPIRE:
818 case DHCP6_EVENT_RETRANS_MAX:
819 case DHCP6_EVENT_IP_ACQUIRE:
820 log_link_debug(link, "DHCPv6 event %d", event);
826 log_link_warning(link, "DHCPv6 error: %s",
829 log_link_warning(link, "DHCPv6 unknown event: %d",
835 static void icmp6_router_handler(sd_icmp6_nd *nd, int event, void *userdata) {
836 Link *link = userdata;
840 assert(link->network);
841 assert(link->manager);
843 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
847 case ICMP6_EVENT_ROUTER_ADVERTISMENT_NONE:
848 case ICMP6_EVENT_ROUTER_ADVERTISMENT_OTHER:
851 case ICMP6_EVENT_ROUTER_ADVERTISMENT_TIMEOUT:
852 case ICMP6_EVENT_ROUTER_ADVERTISMENT_MANAGED:
857 log_link_warning(link, "ICMPv6 error: %s",
860 log_link_warning(link, "ICMPv6 unknown event: %d",
866 if (link->dhcp6_client)
869 r = sd_dhcp6_client_new(&link->dhcp6_client);
873 r = sd_dhcp6_client_attach_event(link->dhcp6_client, NULL, 0);
875 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
879 r = sd_dhcp6_client_set_mac(link->dhcp6_client,
880 (const uint8_t *) &link->mac,
881 sizeof (link->mac), ARPHRD_ETHER);
883 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
887 r = sd_dhcp6_client_set_index(link->dhcp6_client, link->ifindex);
889 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
893 r = sd_dhcp6_client_set_callback(link->dhcp6_client, dhcp6_handler,
896 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
900 r = sd_dhcp6_client_start(link->dhcp6_client);
902 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
905 static int link_acquire_conf(Link *link) {
909 assert(link->network);
910 assert(link->manager);
911 assert(link->manager->event);
913 if (link_ipv4ll_enabled(link)) {
914 assert(link->ipv4ll);
916 log_link_debug(link, "acquiring IPv4 link-local address");
918 r = sd_ipv4ll_start(link->ipv4ll);
920 log_link_warning(link, "could not acquire IPv4 "
921 "link-local address");
926 if (link_dhcp4_enabled(link)) {
927 assert(link->dhcp_client);
929 log_link_debug(link, "acquiring DHCPv4 lease");
931 r = sd_dhcp_client_start(link->dhcp_client);
933 log_link_warning(link, "could not acquire DHCPv4 "
939 if (link_dhcp6_enabled(link)) {
940 assert(link->icmp6_router_discovery);
942 log_link_debug(link, "discovering IPv6 routers");
944 r = sd_icmp6_router_solicitation_start(link->icmp6_router_discovery);
946 log_link_warning(link,
947 "could not start IPv6 router discovery");
955 bool link_has_carrier(Link *link) {
956 /* see Documentation/networking/operstates.txt in the kernel sources */
958 if (link->kernel_operstate == IF_OPER_UP)
961 if (link->kernel_operstate == IF_OPER_UNKNOWN)
962 /* operstate may not be implemented, so fall back to flags */
963 if ((link->flags & IFF_LOWER_UP) && !(link->flags & IFF_DORMANT))
969 static int link_up_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
970 _cleanup_link_unref_ Link *link = userdata;
975 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
978 r = sd_rtnl_message_get_errno(m);
980 /* we warn but don't fail the link, as it may
981 be brought up later */
982 log_link_warning_errno(link, -r, "%-*s: could not bring up interface: %m", IFNAMSIZ, link->ifname);
988 static int link_up(Link *link) {
989 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
993 assert(link->manager);
994 assert(link->manager->rtnl);
996 log_link_debug(link, "bringing link up");
998 r = sd_rtnl_message_new_link(link->manager->rtnl, &req,
999 RTM_SETLINK, link->ifindex);
1001 log_link_error(link, "Could not allocate RTM_SETLINK message");
1005 r = sd_rtnl_message_link_set_flags(req, IFF_UP, IFF_UP);
1007 log_link_error(link, "Could not set link flags: %s",
1012 r = sd_rtnl_call_async(link->manager->rtnl, req, link_up_handler, link,
1015 log_link_error(link,
1016 "Could not send rtnetlink message: %s",
1026 static int link_joined(Link *link) {
1030 assert(link->network);
1032 if (!(link->flags & IFF_UP)) {
1035 link_enter_failed(link);
1040 return link_enter_set_addresses(link);
1043 static int netdev_join_handler(sd_rtnl *rtnl, sd_rtnl_message *m,
1045 _cleanup_link_unref_ Link *link = userdata;
1049 assert(link->network);
1053 if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1056 r = sd_rtnl_message_get_errno(m);
1057 if (r < 0 && r != -EEXIST) {
1058 log_link_error_errno(link, -r, "%-*s: could not join netdev: %m", IFNAMSIZ, link->ifname);
1059 link_enter_failed(link);
1062 log_link_debug(link, "joined netdev");
1064 if (link->enslaving <= 0)
1070 static int link_enter_join_netdev(Link *link) {
1076 assert(link->network);
1077 assert(link->state == LINK_STATE_PENDING);
1079 link->state = LINK_STATE_ENSLAVING;
1083 if (!link->network->bridge &&
1084 !link->network->bond &&
1085 hashmap_isempty(link->network->stacked_netdevs))
1086 return link_joined(link);
1088 if (link->network->bond) {
1089 log_link_struct(link, LOG_DEBUG,
1090 "MESSAGE=%-*s: enslaving by '%s'",
1092 link->ifname, link->network->bond->ifname,
1093 NETDEVIF(link->network->bond),
1096 r = netdev_join(link->network->bond, link, &netdev_join_handler);
1098 log_link_struct(link, LOG_WARNING,
1099 "MESSAGE=%-*s: could not join netdev '%s': %s",
1101 link->ifname, link->network->bond->ifname,
1103 NETDEVIF(link->network->bond),
1105 link_enter_failed(link);
1112 if (link->network->bridge) {
1113 log_link_struct(link, LOG_DEBUG,
1114 "MESSAGE=%-*s: enslaving by '%s'",
1116 link->ifname, link->network->bridge->ifname,
1117 NETDEVIF(link->network->bridge),
1120 r = netdev_join(link->network->bridge, link,
1121 &netdev_join_handler);
1123 log_link_struct(link, LOG_WARNING,
1124 "MESSAGE=%-*s: could not join netdev '%s': %s",
1126 link->ifname, link->network->bridge->ifname,
1128 NETDEVIF(link->network->bridge),
1130 link_enter_failed(link);
1137 HASHMAP_FOREACH(netdev, link->network->stacked_netdevs, i) {
1138 log_link_struct(link, LOG_DEBUG,
1139 "MESSAGE=%-*s: enslaving by '%s'",
1141 link->ifname, netdev->ifname, NETDEVIF(netdev),
1144 r = netdev_join(netdev, link, &netdev_join_handler);
1146 log_link_struct(link, LOG_WARNING,
1147 "MESSAGE=%-*s: could not join netdev '%s': %s",
1149 link->ifname, netdev->ifname,
1151 NETDEVIF(netdev), NULL);
1152 link_enter_failed(link);
1162 static int link_configure(Link *link) {
1166 assert(link->network);
1167 assert(link->state == LINK_STATE_PENDING);
1169 if (link_ipv4ll_enabled(link)) {
1170 r = ipv4ll_configure(link);
1175 if (link_dhcp4_enabled(link)) {
1176 r = dhcp4_configure(link);
1181 if (link_dhcp4_server_enabled(link)) {
1182 r = sd_dhcp_server_new(&link->dhcp_server, link->ifindex);
1186 r = sd_dhcp_server_attach_event(link->dhcp_server, NULL, 0);
1191 if (link_dhcp6_enabled(link)) {
1192 r = sd_icmp6_nd_new(&link->icmp6_router_discovery);
1196 r = sd_icmp6_nd_attach_event(link->icmp6_router_discovery,
1201 r = sd_icmp6_nd_set_mac(link->icmp6_router_discovery,
1206 r = sd_icmp6_nd_set_index(link->icmp6_router_discovery,
1211 r = sd_icmp6_nd_set_callback(link->icmp6_router_discovery,
1212 icmp6_router_handler, link);
1217 if (link_has_carrier(link)) {
1218 r = link_acquire_conf(link);
1223 return link_enter_join_netdev(link);
1226 static int link_initialized_and_synced(sd_rtnl *rtnl, sd_rtnl_message *m,
1228 _cleanup_link_unref_ Link *link = userdata;
1233 assert(link->ifname);
1234 assert(link->manager);
1236 if (link->state != LINK_STATE_PENDING)
1239 log_link_debug(link, "link state is up-to-date");
1241 r = network_get(link->manager, link->udev_device, link->ifname,
1242 &link->mac, &network);
1244 link_enter_unmanaged(link);
1249 if (link->flags & IFF_LOOPBACK) {
1250 if (network->ipv4ll)
1251 log_link_debug(link, "ignoring IPv4LL for loopback link");
1253 if (network->dhcp != DHCP_SUPPORT_NONE)
1254 log_link_debug(link, "ignoring DHCP clients for loopback link");
1256 if (network->dhcp_server)
1257 log_link_debug(link, "ignoring DHCP server for loopback link");
1260 r = network_apply(link->manager, network, link);
1264 r = link_configure(link);
1271 int link_initialized(Link *link, struct udev_device *device) {
1272 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
1276 assert(link->manager);
1277 assert(link->manager->rtnl);
1280 if (link->state != LINK_STATE_PENDING)
1283 if (link->udev_device)
1286 log_link_debug(link, "udev initialized link");
1288 link->udev_device = udev_device_ref(device);
1290 /* udev has initialized the link, but we don't know if we have yet
1291 * processed the NEWLINK messages with the latest state. Do a GETLINK,
1292 * when it returns we know that the pending NEWLINKs have already been
1293 * processed and that we are up-to-date */
1295 r = sd_rtnl_message_new_link(link->manager->rtnl, &req, RTM_GETLINK,
1300 r = sd_rtnl_call_async(link->manager->rtnl, req,
1301 link_initialized_and_synced, link, 0, NULL);
1310 int link_rtnl_process_address(sd_rtnl *rtnl, sd_rtnl_message *message,
1312 Manager *m = userdata;
1315 _cleanup_address_free_ Address *address = NULL;
1317 char buf[INET6_ADDRSTRLEN];
1318 char valid_buf[FORMAT_TIMESPAN_MAX];
1319 const char *valid_str = NULL;
1320 bool address_dropped = false;
1327 r = sd_rtnl_message_get_type(message, &type);
1329 log_warning("rtnl: could not get message type");
1333 r = sd_rtnl_message_addr_get_ifindex(message, &ifindex);
1334 if (r < 0 || ifindex <= 0) {
1335 log_warning("rtnl: received address message without valid ifindex, ignoring");
1338 r = link_get(m, ifindex, &link);
1339 if (r < 0 || !link) {
1340 log_warning("rtnl: received address for a nonexistent link (%d), ignoring", ifindex);
1345 r = address_new_dynamic(&address);
1349 r = sd_rtnl_message_addr_get_family(message, &address->family);
1350 if (r < 0 || !IN_SET(address->family, AF_INET, AF_INET6)) {
1351 log_link_warning(link,
1352 "rtnl: received address with invalid family, ignoring");
1356 r = sd_rtnl_message_addr_get_prefixlen(message, &address->prefixlen);
1358 log_link_warning(link,
1359 "rtnl: received address with invalid prefixlen, ignoring");
1363 r = sd_rtnl_message_addr_get_scope(message, &address->scope);
1365 log_link_warning(link,
1366 "rtnl: received address with invalid scope, ignoring");
1370 r = sd_rtnl_message_addr_get_flags(message, &address->flags);
1372 log_link_warning(link,
1373 "rtnl: received address with invalid flags, ignoring");
1377 switch (address->family) {
1379 r = sd_rtnl_message_read_in_addr(message, IFA_LOCAL,
1380 &address->in_addr.in);
1382 log_link_warning(link,
1383 "rtnl: received address without valid address, ignoring");
1390 r = sd_rtnl_message_read_in6_addr(message, IFA_ADDRESS,
1391 &address->in_addr.in6);
1393 log_link_warning(link,
1394 "rtnl: received address without valid address, ignoring");
1401 assert_not_reached("invalid address family");
1404 if (!inet_ntop(address->family, &address->in_addr, buf,
1405 INET6_ADDRSTRLEN)) {
1406 log_link_warning(link, "could not print address");
1410 r = sd_rtnl_message_read_cache_info(message, IFA_CACHEINFO,
1413 if (address->cinfo.ifa_valid == CACHE_INFO_INFINITY_LIFE_TIME)
1416 valid_str = format_timespan(valid_buf, FORMAT_TIMESPAN_MAX,
1417 address->cinfo.ifa_valid * USEC_PER_SEC,
1421 LIST_FOREACH(addresses, ad, link->addresses) {
1422 if (address_equal(ad, address)) {
1423 LIST_REMOVE(addresses, link->addresses, ad);
1427 address_dropped = true;
1435 if (!address_dropped)
1436 log_link_debug(link, "added address: %s/%u (valid for %s)",
1437 buf, address->prefixlen, valid_str);
1439 log_link_debug(link, "updated address: %s/%u (valid for %s)",
1440 buf, address->prefixlen, valid_str);
1442 LIST_PREPEND(addresses, link->addresses, address);
1449 if (address_dropped) {
1450 log_link_debug(link, "removed address: %s/%u (valid for %s)",
1451 buf, address->prefixlen, valid_str);
1455 log_link_warning(link,
1456 "removing non-existent address: %s/%u (valid for %s)",
1457 buf, address->prefixlen, valid_str);
1461 assert_not_reached("Received invalid RTNL message type");
1467 int link_add(Manager *m, sd_rtnl_message *message, Link **ret) {
1469 _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
1470 _cleanup_udev_device_unref_ struct udev_device *device = NULL;
1471 char ifindex_str[2 + DECIMAL_STR_MAX(int)];
1479 r = link_new(m, message, ret);
1485 log_link_debug(link, "link %d added", link->ifindex);
1487 r = sd_rtnl_message_new_addr(m->rtnl, &req, RTM_GETADDR, link->ifindex,
1492 r = sd_rtnl_call_async(m->rtnl, req, link_get_address_handler, link, 0,
1499 if (detect_container(NULL) <= 0) {
1500 /* not in a container, udev will be around */
1501 sprintf(ifindex_str, "n%d", link->ifindex);
1502 device = udev_device_new_from_device_id(m->udev, ifindex_str);
1504 log_link_warning(link,
1505 "could not find udev device: %m");
1509 if (udev_device_get_is_initialized(device) <= 0) {
1511 log_link_debug(link, "link pending udev initialization...");
1515 r = link_initialized(link, device);
1519 /* we are calling a callback directly, so must take a ref */
1522 r = link_initialized_and_synced(m->rtnl, NULL, link);
1530 int link_update(Link *link, sd_rtnl_message *m) {
1531 struct ether_addr mac;
1534 bool had_carrier, carrier_gained, carrier_lost;
1538 assert(link->ifname);
1541 if (link->state == LINK_STATE_LINGER) {
1543 log_link_info(link, "link readded");
1544 link->state = LINK_STATE_ENSLAVING;
1547 r = sd_rtnl_message_read_string(m, IFLA_IFNAME, &ifname);
1548 if (r >= 0 && !streq(ifname, link->ifname)) {
1549 log_link_info(link, "renamed to %s", ifname);
1552 link->ifname = strdup(ifname);
1557 r = sd_rtnl_message_read_u32(m, IFLA_MTU, &mtu);
1558 if (r >= 0 && mtu > 0) {
1560 if (!link->original_mtu) {
1561 link->original_mtu = mtu;
1562 log_link_debug(link, "saved original MTU: %"
1563 PRIu32, link->original_mtu);
1566 if (link->dhcp_client) {
1567 r = sd_dhcp_client_set_mtu(link->dhcp_client,
1570 log_link_warning(link,
1571 "Could not update MTU in DHCP client: %s",
1578 /* The kernel may broadcast NEWLINK messages without the MAC address
1579 set, simply ignore them. */
1580 r = sd_rtnl_message_read_ether_addr(m, IFLA_ADDRESS, &mac);
1582 if (memcmp(link->mac.ether_addr_octet, mac.ether_addr_octet,
1585 memcpy(link->mac.ether_addr_octet, mac.ether_addr_octet,
1588 log_link_debug(link, "MAC address: "
1589 "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx",
1590 mac.ether_addr_octet[0],
1591 mac.ether_addr_octet[1],
1592 mac.ether_addr_octet[2],
1593 mac.ether_addr_octet[3],
1594 mac.ether_addr_octet[4],
1595 mac.ether_addr_octet[5]);
1598 r = sd_ipv4ll_set_mac(link->ipv4ll, &link->mac);
1600 log_link_warning(link,
1601 "Could not update MAC address in IPv4LL client: %s",
1607 if (link->dhcp_client) {
1608 r = sd_dhcp_client_set_mac(link->dhcp_client,
1609 (const uint8_t *) &link->mac,
1613 log_link_warning(link,
1614 "Could not update MAC address in DHCP client: %s",
1620 if (link->dhcp6_client) {
1621 r = sd_dhcp6_client_set_mac(link->dhcp6_client,
1622 (const uint8_t *) &link->mac,
1626 log_link_warning(link,
1627 "Could not update MAC address in DHCPv6 client: %s",
1635 had_carrier = link_has_carrier(link);
1637 r = link_update_flags(link, m);
1641 carrier_gained = !had_carrier && link_has_carrier(link);
1642 carrier_lost = had_carrier && !link_has_carrier(link);
1644 if (carrier_gained) {
1645 log_link_info(link, "gained carrier");
1647 if (link->network) {
1648 r = link_acquire_conf(link);
1650 link_enter_failed(link);
1654 } else if (carrier_lost) {
1655 log_link_info(link, "lost carrier");
1657 r = link_stop_clients(link);
1659 link_enter_failed(link);
1667 static void link_update_operstate(Link *link) {
1671 if (link->kernel_operstate == IF_OPER_DORMANT)
1672 link->operstate = LINK_OPERSTATE_DORMANT;
1673 else if (link_has_carrier(link)) {
1675 uint8_t scope = RT_SCOPE_NOWHERE;
1677 /* if we have carrier, check what addresses we have */
1678 LIST_FOREACH(addresses, address, link->addresses) {
1679 if (address->flags & (IFA_F_TENTATIVE | IFA_F_DEPRECATED))
1682 if (address->scope < scope)
1683 scope = address->scope;
1686 if (scope < RT_SCOPE_SITE)
1687 /* universally accessible addresses found */
1688 link->operstate = LINK_OPERSTATE_ROUTABLE;
1689 else if (scope < RT_SCOPE_HOST)
1690 /* only link or site local addresses found */
1691 link->operstate = LINK_OPERSTATE_DEGRADED;
1693 /* no useful addresses found */
1694 link->operstate = LINK_OPERSTATE_CARRIER;
1695 } else if (link->flags & IFF_UP)
1696 link->operstate = LINK_OPERSTATE_NO_CARRIER;
1698 link->operstate = LINK_OPERSTATE_OFF;
1701 int link_save(Link *link) {
1702 _cleanup_free_ char *temp_path = NULL;
1703 _cleanup_fclose_ FILE *f = NULL;
1704 const char *admin_state, *oper_state;
1708 assert(link->state_file);
1709 assert(link->lease_file);
1710 assert(link->manager);
1712 link_update_operstate(link);
1714 r = manager_save(link->manager);
1718 if (link->state == LINK_STATE_LINGER) {
1719 unlink(link->state_file);
1723 admin_state = link_state_to_string(link->state);
1724 assert(admin_state);
1726 oper_state = link_operstate_to_string(link->operstate);
1729 r = fopen_temporary(link->state_file, &f, &temp_path);
1733 fchmod(fileno(f), 0644);
1736 "# This is private data. Do not parse.\n"
1739 admin_state, oper_state);
1741 if (link->network) {
1742 char **address, **domain;
1745 fprintf(f, "NETWORK_FILE=%s\n", link->network->filename);
1749 STRV_FOREACH(address, link->network->dns) {
1756 if (link->network->dhcp_dns &&
1758 const struct in_addr *addresses;
1760 r = sd_dhcp_lease_get_dns(link->dhcp_lease, &addresses);
1764 serialize_in_addrs(f, addresses, r);
1772 STRV_FOREACH(address, link->network->ntp) {
1779 if (link->network->dhcp_ntp &&
1781 const struct in_addr *addresses;
1783 r = sd_dhcp_lease_get_ntp(link->dhcp_lease, &addresses);
1787 serialize_in_addrs(f, addresses, r);
1793 fprintf(f, "DOMAINS=");
1795 STRV_FOREACH(domain, link->network->domains) {
1802 if (link->network->dhcp_domains &&
1804 const char *domainname;
1806 r = sd_dhcp_lease_get_domainname(link->dhcp_lease, &domainname);
1810 fputs(domainname, f);
1816 fprintf(f, "WILDCARD_DOMAIN=%s\n",
1817 yes_no(link->network->wildcard_domain));
1819 fprintf(f, "LLMNR=%s\n",
1820 llmnr_support_to_string(link->network->llmnr));
1823 if (link->dhcp_lease) {
1824 assert(link->network);
1826 r = sd_dhcp_lease_save(link->dhcp_lease, link->lease_file);
1834 unlink(link->lease_file);
1836 r = fflush_and_check(f);
1840 if (rename(temp_path, link->state_file) < 0) {
1847 log_link_error(link, "Failed to save link data to %s: %s", link->state_file, strerror(-r));
1848 unlink(link->state_file);
1853 static const char* const link_state_table[_LINK_STATE_MAX] = {
1854 [LINK_STATE_PENDING] = "pending",
1855 [LINK_STATE_ENSLAVING] = "configuring",
1856 [LINK_STATE_SETTING_ADDRESSES] = "configuring",
1857 [LINK_STATE_SETTING_ROUTES] = "configuring",
1858 [LINK_STATE_CONFIGURED] = "configured",
1859 [LINK_STATE_UNMANAGED] = "unmanaged",
1860 [LINK_STATE_FAILED] = "failed",
1861 [LINK_STATE_LINGER] = "linger",
1864 DEFINE_STRING_TABLE_LOOKUP(link_state, LinkState);
1866 static const char* const link_operstate_table[_LINK_OPERSTATE_MAX] = {
1867 [LINK_OPERSTATE_OFF] = "off",
1868 [LINK_OPERSTATE_NO_CARRIER] = "no-carrier",
1869 [LINK_OPERSTATE_DORMANT] = "dormant",
1870 [LINK_OPERSTATE_CARRIER] = "carrier",
1871 [LINK_OPERSTATE_DEGRADED] = "degraded",
1872 [LINK_OPERSTATE_ROUTABLE] = "routable",
1875 DEFINE_STRING_TABLE_LOOKUP(link_operstate, LinkOperationalState);