chiark / gitweb /
sd-network: rename state INITALIZING to PENDING and expose as any other state
[elogind.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-link.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 "dhcp-lease-internal.h"
37
38 static int link_new(Manager *manager, sd_rtnl_message *message, Link **ret) {
39         _cleanup_link_unref_ Link *link = NULL;
40         uint16_t type;
41         const char *ifname;
42         int r, ifindex;
43
44         assert(manager);
45         assert(message);
46         assert(ret);
47
48         r = sd_rtnl_message_get_type(message, &type);
49         if (r < 0)
50                 return r;
51         else if (type != RTM_NEWLINK)
52                 return -EINVAL;
53
54         r = sd_rtnl_message_link_get_ifindex(message, &ifindex);
55         if (r < 0)
56                 return r;
57         else if (ifindex <= 0)
58                 return -EINVAL;
59
60         r = sd_rtnl_message_read_string(message, IFLA_IFNAME, &ifname);
61         if (r < 0)
62                 return r;
63
64         link = new0(Link, 1);
65         if (!link)
66                 return -ENOMEM;
67
68         link->n_ref = 1;
69         link->manager = manager;
70         link->state = LINK_STATE_PENDING;
71         link->ifindex = ifindex;
72         link->ifname = strdup(ifname);
73         if (!link->ifname)
74                 return -ENOMEM;
75
76         r = sd_rtnl_message_read_ether_addr(message, IFLA_ADDRESS, &link->mac);
77         if (r < 0)
78                 log_debug_link(link, "MAC address not found for new device, continuing without");
79
80         r = asprintf(&link->state_file, "/run/systemd/netif/links/%d",
81                      link->ifindex);
82         if (r < 0)
83                 return -ENOMEM;
84
85         r = asprintf(&link->lease_file, "/run/systemd/netif/leases/%d",
86                      link->ifindex);
87         if (r < 0)
88                 return -ENOMEM;
89
90         r = hashmap_ensure_allocated(&manager->links, NULL, NULL);
91         if (r < 0)
92                 return r;
93
94         r = hashmap_put(manager->links, INT_TO_PTR(link->ifindex), link);
95         if (r < 0)
96                 return r;
97
98         *ret = link;
99         link = NULL;
100
101         return 0;
102 }
103
104 static void link_free(Link *link) {
105         Address *address;
106
107         if (!link)
108                 return;
109
110         while ((address = link->addresses)) {
111                 LIST_REMOVE(addresses, link->addresses, address);
112                 address_free(address);
113         }
114
115         while ((address = link->pool_addresses)) {
116                 LIST_REMOVE(addresses, link->pool_addresses, address);
117                 address_free(address);
118         }
119
120         sd_dhcp_client_unref(link->dhcp_client);
121         sd_dhcp_lease_unref(link->dhcp_lease);
122
123         unlink(link->lease_file);
124         free(link->lease_file);
125
126         sd_ipv4ll_unref(link->ipv4ll);
127         sd_dhcp6_client_unref(link->dhcp6_client);
128         sd_icmp6_nd_unref(link->icmp6_router_discovery);
129
130         if (link->manager)
131                 hashmap_remove(link->manager->links, INT_TO_PTR(link->ifindex));
132
133         free(link->ifname);
134
135         unlink(link->state_file);
136         free(link->state_file);
137
138         udev_device_unref(link->udev_device);
139
140         free(link);
141 }
142
143 Link *link_unref(Link *link) {
144         if (link && (-- link->n_ref <= 0))
145                 link_free(link);
146
147         return NULL;
148 }
149
150 Link *link_ref(Link *link) {
151         if (link)
152                 assert_se(++ link->n_ref >= 2);
153
154         return link;
155 }
156
157 int link_get(Manager *m, int ifindex, Link **ret) {
158         Link *link;
159
160         assert(m);
161         assert(ifindex);
162         assert(ret);
163
164         link = hashmap_get(m->links, INT_TO_PTR(ifindex));
165         if (!link)
166                 return -ENODEV;
167
168         *ret = link;
169
170         return 0;
171 }
172
173 void link_drop(Link *link) {
174         if (!link || link->state == LINK_STATE_LINGER)
175                 return;
176
177         link->state = LINK_STATE_LINGER;
178
179         log_debug_link(link, "link removed");
180
181         link_unref(link);
182
183         return;
184 }
185
186 static void link_enter_unmanaged(Link *link) {
187         assert(link);
188
189         log_debug_link(link, "unmanaged");
190
191         link->state = LINK_STATE_UNMANAGED;
192
193         link_save(link);
194 }
195
196 static int link_stop_clients(Link *link) {
197         int r = 0, k;
198
199         assert(link);
200         assert(link->manager);
201         assert(link->manager->event);
202
203         if (!link->network)
204                 return 0;
205
206         if (link->dhcp_client) {
207                 k = sd_dhcp_client_stop(link->dhcp_client);
208                 if (k < 0) {
209                         log_warning_link(link, "Could not stop DHCPv4 client: %s",
210                                          strerror(-r));
211                         r = k;
212                 }
213         }
214
215         if (link->ipv4ll) {
216                 k = sd_ipv4ll_stop(link->ipv4ll);
217                 if (k < 0) {
218                         log_warning_link(link, "Could not stop IPv4 link-local: %s",
219                                          strerror(-r));
220                         r = k;
221                 }
222         }
223
224         if (link->dhcp_server) {
225                 k = sd_dhcp_server_stop(link->dhcp_server);
226                 if (k < 0) {
227                         log_warning_link(link, "Could not stop DHCPv4 server: %s",
228                                          strerror(-r));
229                         r = k;
230                 }
231         }
232
233         if(link->icmp6_router_discovery) {
234
235                 if (link->dhcp6_client) {
236                         k = sd_dhcp6_client_stop(link->dhcp6_client);
237                         if (k < 0) {
238                                 log_warning_link(link, "Could not stop DHCPv6 client: %s",
239                                                  strerror(-r));
240                                 r = k;
241                         }
242                 }
243
244                 k = sd_icmp6_nd_stop(link->icmp6_router_discovery);
245                 if (k < 0) {
246                         log_warning_link(link,
247                                          "Could not stop ICMPv6 router discovery: %s",
248                                          strerror(-r));
249                         r = k;
250                 }
251         }
252
253         return r;
254 }
255
256 void link_enter_failed(Link *link) {
257         assert(link);
258
259         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
260                 return;
261
262         log_warning_link(link, "failed");
263
264         link->state = LINK_STATE_FAILED;
265
266         link_stop_clients(link);
267
268         link_save(link);
269 }
270
271 static Address* link_find_dhcp_server_address(Link *link) {
272         Address *address;
273
274         assert(link);
275         assert(link->network);
276
277         /* The the first statically configured address if there is any */
278         LIST_FOREACH(addresses, address, link->network->static_addresses) {
279
280                 if (address->family != AF_INET)
281                         continue;
282
283                 if (in_addr_is_null(address->family, &address->in_addr))
284                         continue;
285
286                 return address;
287         }
288
289         /* If that didn't work, find a suitable address we got from the pool */
290         LIST_FOREACH(addresses, address, link->pool_addresses) {
291                 if (address->family != AF_INET)
292                         continue;
293
294                 return address;
295         }
296
297         return NULL;
298 }
299
300 static int link_enter_configured(Link *link) {
301         int r;
302
303         assert(link);
304         assert(link->network);
305         assert(link->state == LINK_STATE_SETTING_ROUTES);
306
307         if (link->network->dhcp_server &&
308             !sd_dhcp_server_is_running(link->dhcp_server)) {
309                 struct in_addr pool_start;
310                 Address *address;
311
312                 address = link_find_dhcp_server_address(link);
313                 if (!address) {
314                         log_warning_link(link,
315                                          "Failed to find suitable address for DHCPv4 server instance.");
316                         link_enter_failed(link);
317                         return 0;
318                 }
319
320                 log_debug_link(link, "offering DHCPv4 leases");
321
322                 r = sd_dhcp_server_set_address(link->dhcp_server,
323                                                &address->in_addr.in,
324                                                address->prefixlen);
325                 if (r < 0)
326                         return r;
327
328                 /* offer 32 addresses starting from the address following the server address */
329                 pool_start.s_addr = htobe32(be32toh(address->in_addr.in.s_addr) + 1);
330                 r = sd_dhcp_server_set_lease_pool(link->dhcp_server,
331                                                   &pool_start, 32);
332                 if (r < 0)
333                         return r;
334
335                 /* TODO:
336                 r = sd_dhcp_server_set_router(link->dhcp_server,
337                                               &main_address->in_addr.in);
338                 if (r < 0)
339                         return r;
340
341                 r = sd_dhcp_server_set_prefixlen(link->dhcp_server,
342                                                  main_address->prefixlen);
343                 if (r < 0)
344                         return r;
345                 */
346
347                 r = sd_dhcp_server_start(link->dhcp_server);
348                 if (r < 0) {
349                         log_warning_link(link, "could not start DHCPv4 server "
350                                          "instance: %s", strerror(-r));
351
352                         link_enter_failed(link);
353
354                         return 0;
355                 }
356         }
357
358         log_info_link(link, "link configured");
359
360         link->state = LINK_STATE_CONFIGURED;
361
362         link_save(link);
363
364         return 0;
365 }
366
367 void link_client_handler(Link *link) {
368         assert(link);
369         assert(link->network);
370
371         if (!link->static_configured)
372                 return;
373
374         if (link->network->ipv4ll)
375                 if (!link->ipv4ll_address ||
376                     !link->ipv4ll_route)
377                         return;
378
379         if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V4))
380                 if (!link->dhcp4_configured)
381                         return;
382
383         link_enter_configured(link);
384
385         return;
386 }
387
388 static int route_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
389         _cleanup_link_unref_ Link *link = userdata;
390         int r;
391
392         assert(link->link_messages > 0);
393         assert(IN_SET(link->state, LINK_STATE_SETTING_ADDRESSES,
394                       LINK_STATE_SETTING_ROUTES, LINK_STATE_FAILED,
395                       LINK_STATE_LINGER));
396
397         link->link_messages --;
398
399         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
400                 return 1;
401
402         r = sd_rtnl_message_get_errno(m);
403         if (r < 0 && r != -EEXIST)
404                 log_struct_link(LOG_WARNING, link,
405                                 "MESSAGE=%-*s: could not set route: %s",
406                                 IFNAMSIZ,
407                                 link->ifname, strerror(-r),
408                                 "ERRNO=%d", -r,
409                                 NULL);
410
411         if (link->link_messages == 0) {
412                 log_debug_link(link, "routes set");
413                 link->static_configured = true;
414                 link_client_handler(link);
415         }
416
417         return 1;
418 }
419
420 static int link_enter_set_routes(Link *link) {
421         Route *rt;
422         int r;
423
424         assert(link);
425         assert(link->network);
426         assert(link->state == LINK_STATE_SETTING_ADDRESSES);
427
428         link->state = LINK_STATE_SETTING_ROUTES;
429
430         LIST_FOREACH(routes, rt, link->network->static_routes) {
431                 r = route_configure(rt, link, &route_handler);
432                 if (r < 0) {
433                         log_warning_link(link,
434                                          "could not set routes: %s",
435                                          strerror(-r));
436                         link_enter_failed(link);
437                         return r;
438                 }
439
440                 link->link_messages ++;
441         }
442
443         if (link->link_messages == 0) {
444                 link->static_configured = true;
445                 link_client_handler(link);
446         } else
447                 log_debug_link(link, "setting routes");
448
449         return 0;
450 }
451
452 int link_route_drop_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
453         _cleanup_link_unref_ Link *link = userdata;
454         int r;
455
456         assert(m);
457         assert(link);
458         assert(link->ifname);
459
460         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
461                 return 1;
462
463         r = sd_rtnl_message_get_errno(m);
464         if (r < 0 && r != -ESRCH)
465                 log_struct_link(LOG_WARNING, link,
466                                 "MESSAGE=%-*s: could not drop route: %s",
467                                 IFNAMSIZ,
468                                 link->ifname, strerror(-r),
469                                 "ERRNO=%d", -r,
470                                 NULL);
471
472         return 1;
473 }
474
475 int link_get_address_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
476         _cleanup_link_unref_ Link *link = userdata;
477         int r;
478
479         assert(rtnl);
480         assert(m);
481         assert(link);
482         assert(link->manager);
483
484         for (; m; m = sd_rtnl_message_next(m)) {
485                 r = sd_rtnl_message_get_errno(m);
486                 if (r < 0) {
487                         log_debug_link(link, "getting address failed: %s",
488                                        strerror(-r));
489                         continue;
490                 }
491
492                 r = link_rtnl_process_address(rtnl, m, link->manager);
493                 if (r < 0)
494                         log_warning_link(link, "could not process address: %s",
495                                          strerror(-r));
496         }
497
498         return 1;
499 }
500
501 static int address_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
502         _cleanup_link_unref_ Link *link = userdata;
503         int r;
504
505         assert(rtnl);
506         assert(m);
507         assert(link);
508         assert(link->ifname);
509         assert(link->link_messages > 0);
510         assert(IN_SET(link->state, LINK_STATE_SETTING_ADDRESSES,
511                LINK_STATE_FAILED, LINK_STATE_LINGER));
512
513         link->link_messages --;
514
515         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
516                 return 1;
517
518         r = sd_rtnl_message_get_errno(m);
519         if (r < 0 && r != -EEXIST)
520                 log_struct_link(LOG_WARNING, link,
521                                 "MESSAGE=%-*s: could not set address: %s",
522                                 IFNAMSIZ,
523                                 link->ifname, strerror(-r),
524                                 "ERRNO=%d", -r,
525                                 NULL);
526         else if (r >= 0) {
527                 /* calling handler directly so take a ref */
528                 link_ref(link);
529                 link_get_address_handler(rtnl, m, link);
530         }
531
532         if (link->link_messages == 0) {
533                 log_debug_link(link, "addresses set");
534                 link_enter_set_routes(link);
535         }
536
537         return 1;
538 }
539
540 static int link_enter_set_addresses(Link *link) {
541         Address *ad;
542         int r;
543
544         assert(link);
545         assert(link->network);
546         assert(link->state != _LINK_STATE_INVALID);
547
548         link->state = LINK_STATE_SETTING_ADDRESSES;
549
550         LIST_FOREACH(addresses, ad, link->network->static_addresses) {
551                 r = address_configure(ad, link, &address_handler);
552                 if (r < 0) {
553                         log_warning_link(link,
554                                          "could not set addresses: %s",
555                                          strerror(-r));
556                         link_enter_failed(link);
557                         return r;
558                 }
559
560                 link->link_messages ++;
561         }
562
563         if (link->link_messages == 0) {
564                 link_enter_set_routes(link);
565         } else
566                 log_debug_link(link, "setting addresses");
567
568         return 0;
569 }
570
571 int link_address_drop_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
572         _cleanup_link_unref_ Link *link = userdata;
573         int r;
574
575         assert(m);
576         assert(link);
577         assert(link->ifname);
578
579         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
580                 return 1;
581
582         r = sd_rtnl_message_get_errno(m);
583         if (r < 0 && r != -EADDRNOTAVAIL)
584                 log_struct_link(LOG_WARNING, link,
585                                 "MESSAGE=%-*s: could not drop address: %s",
586                                 IFNAMSIZ,
587                                 link->ifname, strerror(-r),
588                                 "ERRNO=%d", -r,
589                                 NULL);
590
591         return 1;
592 }
593
594 static int set_hostname_handler(sd_bus *bus, sd_bus_message *m, void *userdata,
595                                 sd_bus_error *ret_error) {
596         _cleanup_link_unref_ Link *link = userdata;
597         int r;
598
599         assert(link);
600
601         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
602                 return 1;
603
604         r = sd_bus_message_get_errno(m);
605         if (r < 0)
606                 r = -r;
607         if (r > 0)
608                 log_warning_link(link, "Could not set hostname: %s",
609                                  strerror(r));
610
611         return 1;
612 }
613
614 int link_set_hostname(Link *link, const char *hostname) {
615         _cleanup_bus_message_unref_ sd_bus_message *m = NULL;
616         int r = 0;
617
618         assert(link);
619         assert(link->manager);
620         assert(hostname);
621
622         log_debug_link(link, "Setting transient hostname: '%s'", hostname);
623
624         if (!link->manager->bus) {
625                 /* TODO: replace by assert when we can rely on kdbus */
626                 log_info_link(link,
627                               "Not connected to system bus, ignoring transient hostname.");
628                 return 0;
629         }
630
631         r = sd_bus_message_new_method_call(
632                         link->manager->bus,
633                         &m,
634                         "org.freedesktop.hostname1",
635                         "/org/freedesktop/hostname1",
636                         "org.freedesktop.hostname1",
637                         "SetHostname");
638         if (r < 0)
639                 return r;
640
641         r = sd_bus_message_append(m, "sb", hostname, false);
642         if (r < 0)
643                 return r;
644
645         r = sd_bus_call_async(link->manager->bus, NULL, m, set_hostname_handler,
646                               link, 0);
647         if (r < 0) {
648                 log_error_link(link, "Could not set transient hostname: %s",
649                                strerror(-r));
650                 return r;
651         }
652
653         link_ref(link);
654
655         return 0;
656 }
657
658 static int set_mtu_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
659         _cleanup_link_unref_ Link *link = userdata;
660         int r;
661
662         assert(m);
663         assert(link);
664         assert(link->ifname);
665
666         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
667                 return 1;
668
669         r = sd_rtnl_message_get_errno(m);
670         if (r < 0)
671                 log_struct_link(LOG_WARNING, link,
672                                 "MESSAGE=%-*s: could not set MTU: %s",
673                                 IFNAMSIZ, link->ifname, strerror(-r),
674                                 "ERRNO=%d", -r,
675                                 NULL);
676
677         return 1;
678 }
679
680 int link_set_mtu(Link *link, uint32_t mtu) {
681         _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
682         int r;
683
684         assert(link);
685         assert(link->manager);
686         assert(link->manager->rtnl);
687
688         log_debug_link(link, "setting MTU: %" PRIu32, mtu);
689
690         r = sd_rtnl_message_new_link(link->manager->rtnl, &req,
691                                      RTM_SETLINK, link->ifindex);
692         if (r < 0) {
693                 log_error_link(link, "Could not allocate RTM_SETLINK message");
694                 return r;
695         }
696
697         r = sd_rtnl_message_append_u32(req, IFLA_MTU, mtu);
698         if (r < 0) {
699                 log_error_link(link, "Could not append MTU: %s", strerror(-r));
700                 return r;
701         }
702
703         r = sd_rtnl_call_async(link->manager->rtnl, req, set_mtu_handler, link,
704                                0, NULL);
705         if (r < 0) {
706                 log_error_link(link,
707                                "Could not send rtnetlink message: %s",
708                                strerror(-r));
709                 return r;
710         }
711
712         link_ref(link);
713
714         return 0;
715 }
716
717 static void dhcp6_handler(sd_dhcp6_client *client, int event, void *userdata) {
718         Link *link = userdata;
719
720         assert(link);
721         assert(link->network);
722         assert(link->manager);
723
724         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
725                 return;
726
727         switch(event) {
728         case DHCP6_EVENT_STOP:
729         case DHCP6_EVENT_RESEND_EXPIRE:
730         case DHCP6_EVENT_RETRANS_MAX:
731         case DHCP6_EVENT_IP_ACQUIRE:
732                 log_debug_link(link, "DHCPv6 event %d", event);
733
734                 break;
735
736         default:
737                 if (event < 0)
738                         log_warning_link(link, "DHCPv6 error: %s",
739                                          strerror(-event));
740                 else
741                         log_warning_link(link, "DHCPv6 unknown event: %d",
742                                          event);
743                 return;
744         }
745 }
746
747 static void icmp6_router_handler(sd_icmp6_nd *nd, int event, void *userdata) {
748         Link *link = userdata;
749         int r;
750
751         assert(link);
752         assert(link->network);
753         assert(link->manager);
754
755         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
756                 return;
757
758         switch(event) {
759         case ICMP6_EVENT_ROUTER_ADVERTISMENT_NONE:
760         case ICMP6_EVENT_ROUTER_ADVERTISMENT_OTHER:
761                 return;
762
763         case ICMP6_EVENT_ROUTER_ADVERTISMENT_TIMEOUT:
764         case ICMP6_EVENT_ROUTER_ADVERTISMENT_MANAGED:
765                 break;
766
767         default:
768                 if (event < 0)
769                         log_warning_link(link, "ICMPv6 error: %s",
770                                          strerror(-event));
771                 else
772                         log_warning_link(link, "ICMPv6 unknown event: %d",
773                                          event);
774
775                 return;
776         }
777
778         if (link->dhcp6_client)
779                 return;
780
781         r = sd_dhcp6_client_new(&link->dhcp6_client);
782         if (r < 0)
783                 return;
784
785         r = sd_dhcp6_client_attach_event(link->dhcp6_client, NULL, 0);
786         if (r < 0) {
787                 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
788                 return;
789         }
790
791         r = sd_dhcp6_client_set_mac(link->dhcp6_client, &link->mac);
792         if (r < 0) {
793                 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
794                 return;
795         }
796
797         r = sd_dhcp6_client_set_index(link->dhcp6_client, link->ifindex);
798         if (r < 0) {
799                 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
800                 return;
801         }
802
803         r = sd_dhcp6_client_set_callback(link->dhcp6_client, dhcp6_handler,
804                                          link);
805         if (r < 0) {
806                 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
807                 return;
808         }
809
810         r = sd_dhcp6_client_start(link->dhcp6_client);
811         if (r < 0)
812                 link->dhcp6_client = sd_dhcp6_client_unref(link->dhcp6_client);
813 }
814
815 static int link_acquire_conf(Link *link) {
816         int r;
817
818         assert(link);
819         assert(link->network);
820         assert(link->manager);
821         assert(link->manager->event);
822
823         if (link->network->ipv4ll) {
824                 assert(link->ipv4ll);
825
826                 log_debug_link(link, "acquiring IPv4 link-local address");
827
828                 r = sd_ipv4ll_start(link->ipv4ll);
829                 if (r < 0) {
830                         log_warning_link(link, "could not acquire IPv4 "
831                                          "link-local address");
832                         return r;
833                 }
834         }
835
836         if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V4)) {
837                 assert(link->dhcp_client);
838
839                 log_debug_link(link, "acquiring DHCPv4 lease");
840
841                 r = sd_dhcp_client_start(link->dhcp_client);
842                 if (r < 0) {
843                         log_warning_link(link, "could not acquire DHCPv4 "
844                                          "lease");
845                         return r;
846                 }
847         }
848
849         if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V6)) {
850                 assert(link->icmp6_router_discovery);
851
852                 log_debug_link(link, "discovering IPv6 routers");
853
854                 r = sd_icmp6_router_solicitation_start(link->icmp6_router_discovery);
855                 if (r < 0) {
856                         log_warning_link(link,
857                                          "could not start IPv6 router discovery");
858                         return r;
859                 }
860         }
861
862         return 0;
863 }
864
865 bool link_has_carrier(unsigned flags, uint8_t operstate) {
866         /* see Documentation/networking/operstates.txt in the kernel sources */
867
868         if (operstate == IF_OPER_UP)
869                 return true;
870
871         if (operstate == IF_OPER_UNKNOWN)
872                 /* operstate may not be implemented, so fall back to flags */
873                 if ((flags & IFF_LOWER_UP) && !(flags & IFF_DORMANT))
874                         return true;
875
876         return false;
877 }
878
879 #define FLAG_STRING(string, flag, old, new) \
880         (((old ^ new) & flag) \
881                 ? ((old & flag) ? (" -" string) : (" +" string)) \
882                 : "")
883
884 static int link_update_flags(Link *link, sd_rtnl_message *m) {
885         unsigned flags, unknown_flags_added, unknown_flags_removed, unknown_flags;
886         uint8_t operstate;
887         bool carrier_gained = false, carrier_lost = false;
888         int r;
889
890         assert(link);
891
892         r = sd_rtnl_message_link_get_flags(m, &flags);
893         if (r < 0) {
894                 log_warning_link(link, "Could not get link flags");
895                 return r;
896         }
897
898         r = sd_rtnl_message_read_u8(m, IFLA_OPERSTATE, &operstate);
899         if (r < 0)
900                 /* if we got a message without operstate, take it to mean
901                    the state was unchanged */
902                 operstate = link->kernel_operstate;
903
904         if ((link->flags == flags) && (link->kernel_operstate == operstate))
905                 return 0;
906
907         if (link->flags != flags) {
908                 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",
909                                FLAG_STRING("LOOPBACK", IFF_LOOPBACK, link->flags, flags),
910                                FLAG_STRING("MASTER", IFF_MASTER, link->flags, flags),
911                                FLAG_STRING("SLAVE", IFF_SLAVE, link->flags, flags),
912                                FLAG_STRING("UP", IFF_UP, link->flags, flags),
913                                FLAG_STRING("DORMANT", IFF_DORMANT, link->flags, flags),
914                                FLAG_STRING("LOWER_UP", IFF_LOWER_UP, link->flags, flags),
915                                FLAG_STRING("RUNNING", IFF_RUNNING, link->flags, flags),
916                                FLAG_STRING("MULTICAST", IFF_MULTICAST, link->flags, flags),
917                                FLAG_STRING("BROADCAST", IFF_BROADCAST, link->flags, flags),
918                                FLAG_STRING("POINTOPOINT", IFF_POINTOPOINT, link->flags, flags),
919                                FLAG_STRING("PROMISC", IFF_PROMISC, link->flags, flags),
920                                FLAG_STRING("ALLMULTI", IFF_ALLMULTI, link->flags, flags),
921                                FLAG_STRING("PORTSEL", IFF_PORTSEL, link->flags, flags),
922                                FLAG_STRING("AUTOMEDIA", IFF_AUTOMEDIA, link->flags, flags),
923                                FLAG_STRING("DYNAMIC", IFF_DYNAMIC, link->flags, flags),
924                                FLAG_STRING("NOARP", IFF_NOARP, link->flags, flags),
925                                FLAG_STRING("NOTRAILERS", IFF_NOTRAILERS, link->flags, flags),
926                                FLAG_STRING("DEBUG", IFF_DEBUG, link->flags, flags),
927                                FLAG_STRING("ECHO", IFF_ECHO, link->flags, flags));
928
929                 unknown_flags = ~(IFF_LOOPBACK | IFF_MASTER | IFF_SLAVE | IFF_UP |
930                                   IFF_DORMANT | IFF_LOWER_UP | IFF_RUNNING |
931                                   IFF_MULTICAST | IFF_BROADCAST | IFF_POINTOPOINT |
932                                   IFF_PROMISC | IFF_ALLMULTI | IFF_PORTSEL |
933                                   IFF_AUTOMEDIA | IFF_DYNAMIC | IFF_NOARP |
934                                   IFF_NOTRAILERS | IFF_DEBUG | IFF_ECHO);
935                 unknown_flags_added = ((link->flags ^ flags) & flags & unknown_flags);
936                 unknown_flags_removed = ((link->flags ^ flags) & link->flags & unknown_flags);
937
938                 /* link flags are currently at most 18 bits, let's align to
939                  * printing 20 */
940                 if (unknown_flags_added)
941                         log_debug_link(link,
942                                        "unknown link flags gained: %#.5x (ignoring)",
943                                        unknown_flags_added);
944
945                 if (unknown_flags_removed)
946                         log_debug_link(link,
947                                        "unknown link flags lost: %#.5x (ignoring)",
948                                        unknown_flags_removed);
949         }
950
951         carrier_gained = !link_has_carrier(link->flags, link->kernel_operstate) &&
952                        link_has_carrier(flags, operstate);
953         carrier_lost = link_has_carrier(link->flags, link->kernel_operstate) &&
954                          !link_has_carrier(flags, operstate);
955
956         link->flags = flags;
957         link->kernel_operstate = operstate;
958
959         link_save(link);
960
961         if (link->state == LINK_STATE_FAILED ||
962             link->state == LINK_STATE_UNMANAGED)
963                 return 0;
964
965         if (carrier_gained) {
966                 log_info_link(link, "gained carrier");
967
968                 if (link->network) {
969                         r = link_acquire_conf(link);
970                         if (r < 0) {
971                                 link_enter_failed(link);
972                                 return r;
973                         }
974                 }
975         } else if (carrier_lost) {
976                 log_info_link(link, "lost carrier");
977
978                 r = link_stop_clients(link);
979                 if (r < 0) {
980                         link_enter_failed(link);
981                         return r;
982                 }
983         }
984
985         return 0;
986 }
987
988 static int link_up_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
989         _cleanup_link_unref_ Link *link = userdata;
990         int r;
991
992         assert(link);
993
994         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
995                 return 1;
996
997         r = sd_rtnl_message_get_errno(m);
998         if (r < 0) {
999                 /* we warn but don't fail the link, as it may
1000                    be brought up later */
1001                 log_struct_link(LOG_WARNING, link,
1002                                 "MESSAGE=%-*s: could not bring up interface: %s",
1003                                 IFNAMSIZ,
1004                                 link->ifname, strerror(-r),
1005                                 "ERRNO=%d", -r,
1006                                 NULL);
1007         }
1008
1009         return 1;
1010 }
1011
1012 static int link_up(Link *link) {
1013         _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
1014         int r;
1015
1016         assert(link);
1017         assert(link->manager);
1018         assert(link->manager->rtnl);
1019
1020         log_debug_link(link, "bringing link up");
1021
1022         r = sd_rtnl_message_new_link(link->manager->rtnl, &req,
1023                                      RTM_SETLINK, link->ifindex);
1024         if (r < 0) {
1025                 log_error_link(link, "Could not allocate RTM_SETLINK message");
1026                 return r;
1027         }
1028
1029         r = sd_rtnl_message_link_set_flags(req, IFF_UP, IFF_UP);
1030         if (r < 0) {
1031                 log_error_link(link, "Could not set link flags: %s",
1032                                strerror(-r));
1033                 return r;
1034         }
1035
1036         r = sd_rtnl_call_async(link->manager->rtnl, req, link_up_handler, link,
1037                                0, NULL);
1038         if (r < 0) {
1039                 log_error_link(link,
1040                                "Could not send rtnetlink message: %s",
1041                                strerror(-r));
1042                 return r;
1043         }
1044
1045         link_ref(link);
1046
1047         return 0;
1048 }
1049
1050 static int link_joined(Link *link) {
1051         int r;
1052
1053         assert(link);
1054         assert(link->state == LINK_STATE_ENSLAVING);
1055         assert(link->network);
1056
1057         if (!(link->flags & IFF_UP)) {
1058                 r = link_up(link);
1059                 if (r < 0) {
1060                         link_enter_failed(link);
1061                         return r;
1062                 }
1063         }
1064
1065         return link_enter_set_addresses(link);
1066 }
1067
1068 static int netdev_join_handler(sd_rtnl *rtnl, sd_rtnl_message *m,
1069                                void *userdata) {
1070         _cleanup_link_unref_ Link *link = userdata;
1071         int r;
1072
1073         assert(link);
1074         assert(IN_SET(link->state, LINK_STATE_ENSLAVING, LINK_STATE_FAILED,
1075                       LINK_STATE_LINGER));
1076         assert(link->network);
1077
1078         link->enslaving --;
1079
1080         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
1081                 return 1;
1082
1083         r = sd_rtnl_message_get_errno(m);
1084         if (r < 0 && r != -EEXIST) {
1085                 log_struct_link(LOG_ERR, link,
1086                                 "MESSAGE=%-*s: could not join netdev: %s",
1087                                 IFNAMSIZ,
1088                                 link->ifname, strerror(-r),
1089                                 "ERRNO=%d", -r,
1090                                 NULL);
1091                 link_enter_failed(link);
1092                 return 1;
1093         } else
1094                 log_debug_link(link, "joined netdev");
1095
1096         if (link->enslaving <= 0)
1097                 link_joined(link);
1098
1099         return 1;
1100 }
1101
1102 static int link_enter_join_netdev(Link *link) {
1103         NetDev *netdev;
1104         Iterator i;
1105         int r;
1106
1107         assert(link);
1108         assert(link->network);
1109         assert(link->state == LINK_STATE_PENDING);
1110
1111         link->state = LINK_STATE_ENSLAVING;
1112
1113         link_save(link);
1114
1115         if (!link->network->bridge &&
1116             !link->network->bond &&
1117             hashmap_isempty(link->network->stacked_netdevs))
1118                 return link_joined(link);
1119
1120         if (link->network->bond) {
1121                 log_struct_link(LOG_DEBUG, link,
1122                                 "MESSAGE=%-*s: enslaving by '%s'",
1123                                 IFNAMSIZ,
1124                                 link->ifname, link->network->bond->ifname,
1125                                 NETDEVIF(link->network->bond),
1126                                 NULL);
1127
1128                 r = netdev_join(link->network->bond, link, &netdev_join_handler);
1129                 if (r < 0) {
1130                         log_struct_link(LOG_WARNING, link,
1131                                         "MESSAGE=%-*s: could not join netdev '%s': %s",
1132                                         IFNAMSIZ,
1133                                         link->ifname, link->network->bond->ifname,
1134                                         strerror(-r),
1135                                         NETDEVIF(link->network->bond),
1136                                         NULL);
1137                         link_enter_failed(link);
1138                         return r;
1139                 }
1140
1141                 link->enslaving ++;
1142         }
1143
1144         if (link->network->bridge) {
1145                 log_struct_link(LOG_DEBUG, link,
1146                                 "MESSAGE=%-*s: enslaving by '%s'",
1147                                 IFNAMSIZ,
1148                                 link->ifname, link->network->bridge->ifname,
1149                                 NETDEVIF(link->network->bridge),
1150                                 NULL);
1151
1152                 r = netdev_join(link->network->bridge, link,
1153                                 &netdev_join_handler);
1154                 if (r < 0) {
1155                         log_struct_link(LOG_WARNING, link,
1156                                         "MESSAGE=%-*s: could not join netdev '%s': %s",
1157                                         IFNAMSIZ,
1158                                         link->ifname, link->network->bridge->ifname,
1159                                         strerror(-r),
1160                                         NETDEVIF(link->network->bridge),
1161                                         NULL);
1162                         link_enter_failed(link);
1163                         return r;
1164                 }
1165
1166                 link->enslaving ++;
1167         }
1168
1169         HASHMAP_FOREACH(netdev, link->network->stacked_netdevs, i) {
1170                 log_struct_link(LOG_DEBUG, link,
1171                                 "MESSAGE=%-*s: enslaving by '%s'",
1172                                 IFNAMSIZ,
1173                                 link->ifname, netdev->ifname, NETDEVIF(netdev),
1174                                 NULL);
1175
1176                 r = netdev_join(netdev, link, &netdev_join_handler);
1177                 if (r < 0) {
1178                         log_struct_link(LOG_WARNING, link,
1179                                         "MESSAGE=%-*s: could not join netdev '%s': %s",
1180                                         IFNAMSIZ,
1181                                         link->ifname, netdev->ifname,
1182                                         strerror(-r),
1183                                         NETDEVIF(netdev), NULL);
1184                         link_enter_failed(link);
1185                         return r;
1186                 }
1187
1188                 link->enslaving ++;
1189         }
1190
1191         return 0;
1192 }
1193
1194 static int link_configure(Link *link) {
1195         int r;
1196
1197         assert(link);
1198         assert(link->network);
1199         assert(link->state == LINK_STATE_PENDING);
1200
1201         if (link->network->ipv4ll) {
1202                 r = ipv4ll_configure(link);
1203                 if (r < 0)
1204                         return r;
1205         }
1206
1207         if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V4)) {
1208                 r = dhcp4_configure(link);
1209                 if (r < 0)
1210                         return r;
1211         }
1212
1213         if (link->network->dhcp_server) {
1214                 r = sd_dhcp_server_new(&link->dhcp_server, link->ifindex);
1215                 if (r < 0)
1216                         return r;
1217
1218                 r = sd_dhcp_server_attach_event(link->dhcp_server, NULL, 0);
1219                 if (r < 0)
1220                         return r;
1221         }
1222
1223         if (IN_SET(link->network->dhcp, DHCP_SUPPORT_BOTH, DHCP_SUPPORT_V6)) {
1224                 r = sd_icmp6_nd_new(&link->icmp6_router_discovery);
1225                 if (r < 0)
1226                         return r;
1227
1228                 r = sd_icmp6_nd_attach_event(link->icmp6_router_discovery,
1229                                              NULL, 0);
1230                 if (r < 0)
1231                         return r;
1232
1233                 r = sd_icmp6_nd_set_mac(link->icmp6_router_discovery,
1234                                         &link->mac);
1235                 if (r < 0)
1236                         return r;
1237
1238                 r = sd_icmp6_nd_set_index(link->icmp6_router_discovery,
1239                                           link->ifindex);
1240                 if (r < 0)
1241                         return r;
1242
1243                 r = sd_icmp6_nd_set_callback(link->icmp6_router_discovery,
1244                                              icmp6_router_handler, link);
1245                 if (r < 0)
1246                         return r;
1247         }
1248
1249         if (link_has_carrier(link->flags, link->kernel_operstate)) {
1250                 r = link_acquire_conf(link);
1251                 if (r < 0)
1252                         return r;
1253         }
1254
1255         return link_enter_join_netdev(link);
1256 }
1257
1258 static int link_initialized_and_synced(sd_rtnl *rtnl, sd_rtnl_message *m,
1259                                        void *userdata) {
1260         _cleanup_link_unref_ Link *link = userdata;
1261         Network *network;
1262         int r;
1263
1264         assert(link);
1265         assert(link->ifname);
1266         assert(link->manager);
1267
1268         if (link->state != LINK_STATE_PENDING)
1269                 return 1;
1270
1271         log_debug_link(link, "link state is up-to-date");
1272
1273         r = network_get(link->manager, link->udev_device, link->ifname,
1274                         &link->mac, &network);
1275         if (r == -ENOENT) {
1276                 link_enter_unmanaged(link);
1277                 return 1;
1278         } else if (r < 0)
1279                 return r;
1280
1281         r = network_apply(link->manager, network, link);
1282         if (r < 0)
1283                 return r;
1284
1285         r = link_configure(link);
1286         if (r < 0)
1287                 return r;
1288
1289         return 1;
1290 }
1291
1292 int link_initialized(Link *link, struct udev_device *device) {
1293         _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
1294         int r;
1295
1296         assert(link);
1297         assert(link->manager);
1298         assert(link->manager->rtnl);
1299         assert(device);
1300
1301         if (link->state != LINK_STATE_PENDING)
1302                 return 0;
1303
1304         if (link->udev_device)
1305                 return 0;
1306
1307         log_debug_link(link, "udev initialized link");
1308
1309         link->udev_device = udev_device_ref(device);
1310
1311         /* udev has initialized the link, but we don't know if we have yet
1312          * processed the NEWLINK messages with the latest state. Do a GETLINK,
1313          * when it returns we know that the pending NEWLINKs have already been
1314          * processed and that we are up-to-date */
1315
1316         r = sd_rtnl_message_new_link(link->manager->rtnl, &req, RTM_GETLINK,
1317                                      link->ifindex);
1318         if (r < 0)
1319                 return r;
1320
1321         r = sd_rtnl_call_async(link->manager->rtnl, req,
1322                                link_initialized_and_synced, link, 0, NULL);
1323         if (r < 0)
1324                 return r;
1325
1326         link_ref(link);
1327
1328         return 0;
1329 }
1330
1331 int link_rtnl_process_address(sd_rtnl *rtnl, sd_rtnl_message *message,
1332                               void *userdata) {
1333         Manager *m = userdata;
1334         Link *link = NULL;
1335         uint16_t type;
1336         _cleanup_address_free_ Address *address = NULL;
1337         Address *ad;
1338         char buf[INET6_ADDRSTRLEN];
1339         bool address_dropped = false;
1340         int r, ifindex;
1341
1342         assert(rtnl);
1343         assert(message);
1344         assert(m);
1345
1346         r = sd_rtnl_message_get_type(message, &type);
1347         if (r < 0) {
1348                 log_warning("rtnl: could not get message type");
1349                 return 0;
1350         }
1351
1352         r = sd_rtnl_message_addr_get_ifindex(message, &ifindex);
1353         if (r < 0 || ifindex <= 0) {
1354                 log_warning("rtnl: received address message without valid ifindex, ignoring");
1355                 return 0;
1356         } else {
1357                 r = link_get(m, ifindex, &link);
1358                 if (r < 0 || !link) {
1359                         log_warning("rtnl: received address for a nonexistent link, ignoring");
1360                         return 0;
1361                 }
1362         }
1363
1364         r = address_new_dynamic(&address);
1365         if (r < 0)
1366                 return r;
1367
1368         r = sd_rtnl_message_addr_get_family(message, &address->family);
1369         if (r < 0 || !IN_SET(address->family, AF_INET, AF_INET6)) {
1370                 log_warning_link(link,
1371                                  "rtnl: received address with invalid family, ignoring");
1372                 return 0;
1373         }
1374
1375         r = sd_rtnl_message_addr_get_prefixlen(message, &address->prefixlen);
1376         if (r < 0) {
1377                 log_warning_link(link,
1378                                  "rtnl: received address with invalid prefixlen, ignoring");
1379                 return 0;
1380         }
1381
1382         r = sd_rtnl_message_addr_get_scope(message, &address->scope);
1383         if (r < 0) {
1384                 log_warning_link(link,
1385                                  "rtnl: received address with invalid scope, ignoring");
1386                 return 0;
1387         }
1388
1389         switch (address->family) {
1390         case AF_INET:
1391                 r = sd_rtnl_message_read_in_addr(message, IFA_LOCAL,
1392                                                  &address->in_addr.in);
1393                 if (r < 0) {
1394                         log_warning_link(link,
1395                                          "rtnl: received address without valid address, ignoring");
1396                         return 0;
1397                 }
1398
1399                 break;
1400
1401         case AF_INET6:
1402                 r = sd_rtnl_message_read_in6_addr(message, IFA_ADDRESS,
1403                                                   &address->in_addr.in6);
1404                 if (r < 0) {
1405                         log_warning_link(link,
1406                                          "rtnl: received address without valid address, ignoring");
1407                         return 0;
1408                 }
1409
1410                 break;
1411
1412         default:
1413                 assert_not_reached("invalid address family");
1414         }
1415
1416         if (!inet_ntop(address->family, &address->in_addr, buf,
1417                        INET6_ADDRSTRLEN)) {
1418                 log_warning_link(link, "could not print address");
1419                 return 0;
1420         }
1421
1422         LIST_FOREACH(addresses, ad, link->addresses) {
1423                 if (address_equal(ad, address)) {
1424                         LIST_REMOVE(addresses, link->addresses, ad);
1425
1426                         address_free(ad);
1427
1428                         address_dropped = true;
1429
1430                         break;
1431                 }
1432         }
1433
1434         switch (type) {
1435         case RTM_NEWADDR:
1436                 if (!address_dropped)
1437                         log_debug_link(link, "added address: %s/%u", buf,
1438                                        address->prefixlen);
1439                 else
1440                         log_debug_link(link, "updated address: %s/%u", buf,
1441                                        address->prefixlen);
1442
1443                 LIST_PREPEND(addresses, link->addresses, address);
1444                 address = NULL;
1445
1446                 link_save(link);
1447
1448                 break;
1449         case RTM_DELADDR:
1450                 if (address_dropped) {
1451                         log_debug_link(link, "removed address: %s/%u", buf,
1452                                        address->prefixlen);
1453
1454                         link_save(link);
1455                 } else
1456                         log_warning_link(link,
1457                                          "removing non-existent address: %s/%u",
1458                                          buf, address->prefixlen);
1459
1460                 break;
1461         default:
1462                 assert_not_reached("Received invalid RTNL message type");
1463         }
1464
1465         return 1;
1466 }
1467
1468 int link_add(Manager *m, sd_rtnl_message *message, Link **ret) {
1469         Link *link;
1470         _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL;
1471         _cleanup_udev_device_unref_ struct udev_device *device = NULL;
1472         char ifindex_str[2 + DECIMAL_STR_MAX(int)];
1473         int r;
1474
1475         assert(m);
1476         assert(m->rtnl);
1477         assert(message);
1478         assert(ret);
1479
1480         r = link_new(m, message, ret);
1481         if (r < 0)
1482                 return r;
1483
1484         link = *ret;
1485
1486         log_debug_link(link, "link %d added", link->ifindex);
1487
1488         r = sd_rtnl_message_new_addr(m->rtnl, &req, RTM_GETADDR, link->ifindex,
1489                                      0);
1490         if (r < 0)
1491                 return r;
1492
1493         r = sd_rtnl_call_async(m->rtnl, req, link_get_address_handler, link, 0,
1494                                NULL);
1495         if (r < 0)
1496                 return r;
1497
1498         link_ref(link);
1499
1500         if (detect_container(NULL) <= 0) {
1501                 /* not in a container, udev will be around */
1502                 sprintf(ifindex_str, "n%d", link->ifindex);
1503                 device = udev_device_new_from_device_id(m->udev, ifindex_str);
1504                 if (!device) {
1505                         log_warning_link(link,
1506                                          "could not find udev device: %m");
1507                         return -errno;
1508                 }
1509
1510                 if (udev_device_get_is_initialized(device) <= 0) {
1511                         /* not yet ready */
1512                         log_debug_link(link, "link pending udev initialization...");
1513                         return 0;
1514                 }
1515
1516                 r = link_initialized(link, device);
1517                 if (r < 0)
1518                         return r;
1519         } else {
1520                 /* we are calling a callback directly, so must take a ref */
1521                 link_ref(link);
1522
1523                 r = link_initialized_and_synced(m->rtnl, NULL, link);
1524                 if (r < 0)
1525                         return r;
1526         }
1527
1528         return 0;
1529 }
1530
1531 int link_update(Link *link, sd_rtnl_message *m) {
1532         struct ether_addr mac;
1533         const char *ifname;
1534         uint32_t mtu;
1535         int r;
1536
1537         assert(link);
1538         assert(link->ifname);
1539         assert(m);
1540
1541         if (link->state == LINK_STATE_LINGER) {
1542                 link_ref(link);
1543                 log_info_link(link, "link readded");
1544                 link->state = LINK_STATE_ENSLAVING;
1545         }
1546
1547         r = sd_rtnl_message_read_string(m, IFLA_IFNAME, &ifname);
1548         if (r >= 0 && !streq(ifname, link->ifname)) {
1549                 log_info_link(link, "renamed to %s", ifname);
1550
1551                 free(link->ifname);
1552                 link->ifname = strdup(ifname);
1553                 if (!link->ifname)
1554                         return -ENOMEM;
1555         }
1556
1557         r = sd_rtnl_message_read_u32(m, IFLA_MTU, &mtu);
1558         if (r >= 0 && mtu > 0) {
1559                 link->mtu = mtu;
1560                 if (!link->original_mtu) {
1561                         link->original_mtu = mtu;
1562                         log_debug_link(link, "saved original MTU: %"
1563                                        PRIu32, link->original_mtu);
1564                 }
1565
1566                 if (link->dhcp_client) {
1567                         r = sd_dhcp_client_set_mtu(link->dhcp_client,
1568                                                    link->mtu);
1569                         if (r < 0) {
1570                                 log_warning_link(link,
1571                                                  "Could not update MTU in DHCP client: %s",
1572                                                  strerror(-r));
1573                                 return r;
1574                         }
1575                 }
1576         }
1577
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);
1581         if (r >= 0) {
1582                 if (memcmp(link->mac.ether_addr_octet, mac.ether_addr_octet,
1583                            ETH_ALEN)) {
1584
1585                         memcpy(link->mac.ether_addr_octet, mac.ether_addr_octet,
1586                                ETH_ALEN);
1587
1588                         log_debug_link(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]);
1596
1597                         if (link->ipv4ll) {
1598                                 r = sd_ipv4ll_set_mac(link->ipv4ll, &link->mac);
1599                                 if (r < 0) {
1600                                         log_warning_link(link,
1601                                                          "Could not update MAC address in IPv4LL client: %s",
1602                                                          strerror(-r));
1603                                         return r;
1604                                 }
1605                         }
1606
1607                         if (link->dhcp_client) {
1608                                 r = sd_dhcp_client_set_mac(link->dhcp_client,
1609                                                            &link->mac);
1610                                 if (r < 0) {
1611                                         log_warning_link(link,
1612                                                          "Could not update MAC address in DHCP client: %s",
1613                                                          strerror(-r));
1614                                         return r;
1615                                 }
1616                         }
1617
1618                         if (link->dhcp6_client) {
1619                                 r = sd_dhcp6_client_set_mac(link->dhcp6_client,
1620                                                             &link->mac);
1621                                 if (r < 0) {
1622                                         log_warning_link(link,
1623                                                          "Could not update MAC address in DHCPv6 client: %s",
1624                                                          strerror(-r));
1625                                         return r;
1626                                 }
1627                         }
1628                 }
1629         }
1630
1631         return link_update_flags(link, m);
1632 }
1633
1634 static void link_update_operstate(Link *link) {
1635
1636         assert(link);
1637
1638         if (link->kernel_operstate == IF_OPER_DORMANT)
1639                 link->operstate = LINK_OPERSTATE_DORMANT;
1640         else if (link_has_carrier(link->flags, link->kernel_operstate)) {
1641                 Address *address;
1642                 uint8_t scope = RT_SCOPE_NOWHERE;
1643
1644                 /* if we have carrier, check what addresses we have */
1645                 LIST_FOREACH(addresses, address, link->addresses) {
1646                         if (address->scope < scope)
1647                                 scope = address->scope;
1648                 }
1649
1650                 if (scope < RT_SCOPE_SITE)
1651                         /* universally accessible addresses found */
1652                         link->operstate = LINK_OPERSTATE_ROUTABLE;
1653                 else if (scope < RT_SCOPE_HOST)
1654                         /* only link or site local addresses found */
1655                         link->operstate = LINK_OPERSTATE_DEGRADED;
1656                 else
1657                         /* no useful addresses found */
1658                         link->operstate = LINK_OPERSTATE_CARRIER;
1659         } else if (link->flags & IFF_UP)
1660                 link->operstate = LINK_OPERSTATE_UP;
1661         else
1662                 link->operstate = LINK_OPERSTATE_DOWN;
1663 }
1664
1665 int link_save(Link *link) {
1666         _cleanup_free_ char *temp_path = NULL;
1667         _cleanup_fclose_ FILE *f = NULL;
1668         const char *admin_state, *oper_state;
1669         int r;
1670
1671         assert(link);
1672         assert(link->state_file);
1673         assert(link->lease_file);
1674         assert(link->manager);
1675
1676         link_update_operstate(link);
1677
1678         r = manager_save(link->manager);
1679         if (r < 0)
1680                 return r;
1681
1682         if (link->state == LINK_STATE_LINGER) {
1683                 unlink(link->state_file);
1684                 return 0;
1685         }
1686
1687         admin_state = link_state_to_string(link->state);
1688         assert(admin_state);
1689
1690         oper_state = link_operstate_to_string(link->operstate);
1691         assert(oper_state);
1692
1693         r = fopen_temporary(link->state_file, &f, &temp_path);
1694         if (r < 0)
1695                 return r;
1696
1697         fchmod(fileno(f), 0644);
1698
1699         fprintf(f,
1700                 "# This is private data. Do not parse.\n"
1701                 "ADMIN_STATE=%s\n"
1702                 "OPER_STATE=%s\n",
1703                 admin_state, oper_state);
1704
1705         if (link->network) {
1706                 char **address;
1707
1708                 fputs("DNS=", f);
1709
1710                 if (link->network->dhcp_dns &&
1711                     link->dhcp_lease) {
1712                         const struct in_addr *addresses;
1713
1714                         r = sd_dhcp_lease_get_dns(link->dhcp_lease, &addresses);
1715                         if (r > 0) {
1716                                 serialize_in_addrs(f, addresses, r);
1717                                 if (link->network->dns)
1718                                         fputs(" ", f);
1719                         }
1720                 }
1721
1722                 STRV_FOREACH(address, link->network->dns)
1723                         fprintf(f, "%s%s", *address,
1724                                 (address + 1 ? " " : ""));
1725
1726                 fputs("\n", f);
1727
1728                 fprintf(f, "NTP=");
1729
1730                 if (link->network->dhcp_ntp &&
1731                     link->dhcp_lease) {
1732                         const struct in_addr *addresses;
1733
1734                         r = sd_dhcp_lease_get_ntp(link->dhcp_lease, &addresses);
1735                         if (r > 0) {
1736                                 serialize_in_addrs(f, addresses, r);
1737                                 if (link->network->ntp)
1738                                         fputs(" ", f);
1739                         }
1740                 }
1741
1742                 STRV_FOREACH(address, link->network->ntp)
1743                         fprintf(f, "%s%s", *address,
1744                                 (address + 1 ? " " : ""));
1745
1746                 fputs("\n", f);
1747
1748                 fprintf(f, "LLMNR=%s\n",
1749                         llmnr_support_to_string(link->network->llmnr));
1750         }
1751
1752         if (link->dhcp_lease) {
1753                 assert(link->network);
1754
1755                 r = dhcp_lease_save(link->dhcp_lease, link->lease_file);
1756                 if (r < 0)
1757                         goto fail;
1758
1759                 fprintf(f,
1760                         "DHCP_LEASE=%s\n",
1761                         link->lease_file);
1762         } else
1763                 unlink(link->lease_file);
1764
1765         r = fflush_and_check(f);
1766         if (r < 0)
1767                 goto fail;
1768
1769         if (rename(temp_path, link->state_file) < 0) {
1770                 r = -errno;
1771                 goto fail;
1772         }
1773
1774         return 0;
1775 fail:
1776         log_error_link(link, "Failed to save link data to %s: %s", link->state_file, strerror(-r));
1777         unlink(link->state_file);
1778         unlink(temp_path);
1779         return r;
1780 }
1781
1782 static const char* const link_state_table[_LINK_STATE_MAX] = {
1783         [LINK_STATE_PENDING] = "pending",
1784         [LINK_STATE_ENSLAVING] = "configuring",
1785         [LINK_STATE_SETTING_ADDRESSES] = "configuring",
1786         [LINK_STATE_SETTING_ROUTES] = "configuring",
1787         [LINK_STATE_CONFIGURED] = "configured",
1788         [LINK_STATE_UNMANAGED] = "unmanaged",
1789         [LINK_STATE_FAILED] = "failed",
1790         [LINK_STATE_LINGER] = "linger",
1791 };
1792
1793 DEFINE_STRING_TABLE_LOOKUP(link_state, LinkState);
1794
1795 static const char* const link_operstate_table[_LINK_OPERSTATE_MAX] = {
1796         [LINK_OPERSTATE_DOWN] = "down",
1797         [LINK_OPERSTATE_UP] = "up",
1798         [LINK_OPERSTATE_DORMANT] = "dormant",
1799         [LINK_OPERSTATE_CARRIER] = "carrier",
1800         [LINK_OPERSTATE_DEGRADED] = "degraded",
1801         [LINK_OPERSTATE_ROUTABLE] = "routable",
1802 };
1803
1804 DEFINE_STRING_TABLE_LOOKUP(link_operstate, LinkOperationalState);