chiark / gitweb /
993931d1cd6a06141fdce3388977b1a3ac205a3a
[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
25 #include "networkd.h"
26 #include "libudev-private.h"
27 #include "util.h"
28
29 int link_new(Manager *manager, struct udev_device *device, Link **ret) {
30         _cleanup_link_free_ Link *link = NULL;
31         const char *mac;
32         struct ether_addr *mac_addr;
33         const char *ifname;
34         int r;
35
36         assert(device);
37         assert(ret);
38
39         link = new0(Link, 1);
40         if (!link)
41                 return -ENOMEM;
42
43         link->manager = manager;
44         link->state = _LINK_STATE_INVALID;
45
46         link->ifindex = udev_device_get_ifindex(device);
47         if (link->ifindex <= 0)
48                 return -EINVAL;
49
50         mac = udev_device_get_sysattr_value(device, "address");
51         if (mac) {
52                 mac_addr = ether_aton(mac);
53                 if (mac_addr)
54                         memcpy(&link->mac, mac_addr, sizeof(struct ether_addr));
55         }
56
57         ifname = udev_device_get_sysname(device);
58         link->ifname = strdup(ifname);
59
60         r = hashmap_put(manager->links, &link->ifindex, link);
61         if (r < 0)
62                 return r;
63
64         *ret = link;
65         link = NULL;
66
67         return 0;
68 }
69
70 void link_free(Link *link) {
71         if (!link)
72                 return;
73
74         assert(link->manager);
75
76         if (link->dhcp)
77                 sd_dhcp_client_free(link->dhcp);
78
79         route_free(link->dhcp_route);
80         link->dhcp_route = NULL;
81
82         address_free(link->dhcp_address);
83         link->dhcp_address = NULL;
84
85         hashmap_remove(link->manager->links, &link->ifindex);
86
87         free(link->ifname);
88
89         free(link);
90 }
91
92 int link_add(Manager *m, struct udev_device *device, Link **ret) {
93         Link *link;
94         Network *network;
95         int r;
96         uint64_t ifindex;
97         const char *devtype;
98
99         assert(m);
100         assert(device);
101
102         ifindex = udev_device_get_ifindex(device);
103         link = hashmap_get(m->links, &ifindex);
104         if (link) {
105                 *ret = link;
106                 return -EEXIST;
107         }
108
109         r = link_new(m, device, &link);
110         if (r < 0)
111                 return r;
112
113         *ret = link;
114
115         devtype = udev_device_get_devtype(device);
116         if (streq_ptr(devtype, "bridge")) {
117                 r = bridge_set_link(m, link);
118                 if (r < 0 && r != -ENOENT)
119                         return r;
120         }
121
122         r = network_get(m, device, &network);
123         if (r < 0)
124                 return r == -ENOENT ? 0 : r;
125
126         r = network_apply(m, network, link);
127         if (r < 0)
128                 return r;
129
130         return 0;
131 }
132
133 static int link_enter_configured(Link *link) {
134         assert(link);
135         assert(link->state == LINK_STATE_SETTING_ROUTES);
136
137         log_info_link(link, "link configured");
138
139         link->state = LINK_STATE_CONFIGURED;
140
141         return 0;
142 }
143
144 static void link_enter_failed(Link *link) {
145         assert(link);
146
147         log_warning_link(link, "failed");
148
149         link->state = LINK_STATE_FAILED;
150 }
151
152 static int route_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
153         Link *link = userdata;
154         int r;
155
156         assert(link->route_messages > 0);
157         assert(link->state == LINK_STATE_SETTING_ADDRESSES ||
158                link->state == LINK_STATE_SETTING_ROUTES ||
159                link->state == LINK_STATE_FAILED);
160
161         link->route_messages --;
162
163         if (link->state == LINK_STATE_FAILED)
164                 return 1;
165
166         r = sd_rtnl_message_get_errno(m);
167         if (r < 0 && r != -EEXIST)
168                 log_warning_link(link, "could not set route: %s", strerror(-r));
169
170         /* we might have received an old reply after moving back to SETTING_ADDRESSES,
171          * ignore it */
172         if (link->route_messages == 0 && link->state == LINK_STATE_SETTING_ROUTES) {
173                 log_debug_link(link, "routes set");
174                 link_enter_configured(link);
175         }
176
177         return 1;
178 }
179
180 static int link_enter_set_routes(Link *link) {
181         Route *route;
182         int r;
183
184         assert(link);
185         assert(link->network);
186         assert(link->state == LINK_STATE_SETTING_ADDRESSES);
187
188         link->state = LINK_STATE_SETTING_ROUTES;
189
190         if (!link->network->static_routes && !link->dhcp_route)
191                 return link_enter_configured(link);
192
193         log_debug_link(link, "setting routes");
194
195         LIST_FOREACH(static_routes, route, link->network->static_routes) {
196                 r = route_configure(route, link, &route_handler);
197                 if (r < 0) {
198                         log_warning_link(link,
199                                          "could not set routes: %s", strerror(-r));
200                         link_enter_failed(link);
201                         return r;
202                 }
203
204                 link->route_messages ++;
205         }
206
207         if (link->dhcp_route) {
208                 r = route_configure(link->dhcp_route, link, &route_handler);
209                 if (r < 0) {
210                         log_warning_link(link,
211                                          "could not set routes: %s", strerror(-r));
212                         link_enter_failed(link);
213                         return r;
214                 }
215
216                 link->route_messages ++;
217         }
218
219         return 0;
220 }
221
222 static int address_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
223         Link *link = userdata;
224         int r;
225
226         assert(m);
227         assert(link);
228         assert(link->ifname);
229         assert(link->addr_messages > 0);
230         assert(link->state == LINK_STATE_SETTING_ADDRESSES || link->state == LINK_STATE_FAILED);
231
232         link->addr_messages --;
233
234         if (link->state == LINK_STATE_FAILED)
235                 return 1;
236
237         r = sd_rtnl_message_get_errno(m);
238         if (r < 0 && r != -EEXIST)
239                 log_struct_link(LOG_ERR, link,
240                                 "MESSAGE=%s: could not set address: %s",
241                                 link->ifname, strerror(-r),
242                                 "ERRNO=%d", -r,
243                                 NULL);
244
245         if (link->addr_messages == 0) {
246                 log_debug_link(link, "addresses set");
247                 link_enter_set_routes(link);
248         }
249
250         return 1;
251 }
252
253 static int link_enter_set_addresses(Link *link) {
254         Address *address;
255         int r;
256
257         assert(link);
258         assert(link->network);
259         assert(link->state != _LINK_STATE_INVALID);
260
261         link->state = LINK_STATE_SETTING_ADDRESSES;
262
263         if (!link->network->static_addresses && !link->dhcp_address)
264                 return link_enter_set_routes(link);
265
266         log_debug_link(link, "setting addresses");
267
268         LIST_FOREACH(static_addresses, address, link->network->static_addresses) {
269                 r = address_configure(address, link, &address_handler);
270                 if (r < 0) {
271                         log_warning_link(link,
272                                          "could not set addresses: %s", strerror(-r));
273                         link_enter_failed(link);
274                         return r;
275                 }
276
277                 link->addr_messages ++;
278         }
279
280         if (link->dhcp_address) {
281                 r = address_configure(link->dhcp_address, link, &address_handler);
282                 if (r < 0) {
283                         log_warning_link(link,
284                                          "could not set addresses: %s", strerror(-r));
285                         link_enter_failed(link);
286                         return r;
287                 }
288
289                 link->addr_messages ++;
290         }
291
292         return 0;
293 }
294
295 static int address_drop_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
296         Link *link = userdata;
297         int r;
298
299         assert(m);
300         assert(link);
301         assert(link->ifname);
302
303         if (link->state == LINK_STATE_FAILED)
304                 return 1;
305
306         r = sd_rtnl_message_get_errno(m);
307         if (r < 0 && r != -EEXIST)
308                 log_warning_link(link, "could not drop address: %s", strerror(-r));
309
310         return 1;
311 }
312
313 static int set_mtu_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
314         Link *link = userdata;
315         int r;
316
317         assert(m);
318         assert(link);
319         assert(link->ifname);
320
321         if (link->state == LINK_STATE_FAILED)
322                 return 1;
323
324         r = sd_rtnl_message_get_errno(m);
325         if (r < 0 && r != -EEXIST)
326                 log_warning_link(link, "Could not set MTU: %s", strerror(-r));
327
328         return 1;
329 }
330
331 static int link_set_mtu(Link *link, uint32_t mtu) {
332         _cleanup_sd_rtnl_message_unref_ sd_rtnl_message *req = NULL;
333         int r;
334
335         assert(link);
336         assert(link->manager);
337         assert(link->manager->rtnl);
338
339         log_debug_link(link, "setting MTU: %" PRIu32, mtu);
340
341         r = sd_rtnl_message_link_new(RTM_SETLINK, link->ifindex, &req);
342         if (r < 0) {
343                 log_error_link(link, "Could not allocate RTM_SETLINK message");
344                 return r;
345         }
346
347         r = sd_rtnl_message_append_u32(req, IFLA_MTU, mtu);
348         if (r < 0) {
349                 log_error_link(link, "Could not append MTU: %s", strerror(-r));
350                 return r;
351         }
352
353         r = sd_rtnl_call_async(link->manager->rtnl, req, set_mtu_handler, link, 0, NULL);
354         if (r < 0) {
355                 log_error_link(link,
356                                "Could not send rtnetlink message: %s", strerror(-r));
357                 return r;
358         }
359
360         return 0;
361 }
362
363 static void dhcp_handler(sd_dhcp_client *client, int event, void *userdata) {
364         Link *link = userdata;
365         struct in_addr address;
366         struct in_addr netmask;
367         struct in_addr gateway;
368         int prefixlen;
369         int r;
370
371         assert(link);
372         assert(link->network);
373
374         if (link->state == LINK_STATE_FAILED)
375                 return;
376
377         if (event < 0) {
378                 log_warning_link(link, "DHCP error: %s", strerror(-event));
379                 link_enter_failed(link);
380                 return;
381         }
382
383         if (event == DHCP_EVENT_NO_LEASE)
384                 log_debug_link(link, "IP address in use.");
385
386         if (event == DHCP_EVENT_IP_CHANGE || event == DHCP_EVENT_EXPIRED ||
387             event == DHCP_EVENT_STOP) {
388                 if (link->dhcp_address) {
389                         address_drop(link->dhcp_address, link, address_drop_handler);
390
391                         address_free(link->dhcp_address);
392                         link->dhcp_address = NULL;
393                 }
394
395                 if (link->dhcp_route) {
396                         route_free(link->dhcp_route);
397                         link->dhcp_route = NULL;
398                 }
399
400                 if (link->network->dhcp_mtu) {
401                         uint16_t mtu;
402
403                         r = sd_dhcp_client_get_mtu(client, &mtu);
404                         if (r >= 0 && link->original_mtu != mtu) {
405                                 r = link_set_mtu(link, link->original_mtu);
406                                 if (r < 0) {
407                                         log_warning_link(link, "DHCP error: could not reset MTU");
408                                         link_enter_failed(link);
409                                         return;
410                                 }
411                         }
412                 }
413         }
414
415         r = sd_dhcp_client_get_address(client, &address);
416         if (r < 0) {
417                 log_warning_link(link, "DHCP error: no address");
418                 link_enter_failed(link);
419                 return;
420         }
421
422         r = sd_dhcp_client_get_netmask(client, &netmask);
423         if (r < 0) {
424                 log_warning_link(link, "DHCP error: no netmask");
425                 link_enter_failed(link);
426                 return;
427         }
428
429         prefixlen = sd_dhcp_client_prefixlen(&netmask);
430         if (prefixlen < 0) {
431                 log_warning_link(link, "DHCP error: no prefixlen");
432                 link_enter_failed(link);
433                 return;
434         }
435
436         r = sd_dhcp_client_get_router(client, &gateway);
437         if (r < 0) {
438                 log_warning_link(link, "DHCP error: no router");
439                 link_enter_failed(link);
440                 return;
441         }
442
443         if (event == DHCP_EVENT_IP_CHANGE || event == DHCP_EVENT_IP_ACQUIRE) {
444                 _cleanup_address_free_ Address *addr = NULL;
445                 _cleanup_route_free_ Route *rt = NULL;
446                 struct in_addr **nameservers;
447
448                 log_struct_link(LOG_INFO, link,
449                                 "MESSAGE=%s: DHCPv4 address %u.%u.%u.%u/%u via %u.%u.%u.%u",
450                                 link->ifname,
451                                 ADDRESS_FMT_VAL(address),
452                                 prefixlen,
453                                 ADDRESS_FMT_VAL(gateway),
454                                 "ADDRESS=%u.%u.%u.%u",
455                                 ADDRESS_FMT_VAL(address),
456                                 "PREFIXLEN=%u",
457                                 prefixlen,
458                                 "GATEWAY=%u.%u.%u.%u",
459                                 ADDRESS_FMT_VAL(gateway),
460                                 NULL);
461
462                 r = address_new_dynamic(&addr);
463                 if (r < 0) {
464                         log_error_link(link, "Could not allocate address");
465                         link_enter_failed(link);
466                         return;
467                 }
468
469                 addr->family = AF_INET;
470                 addr->in_addr.in = address;
471                 addr->prefixlen = prefixlen;
472                 addr->netmask = netmask;
473
474                 r = route_new_dynamic(&rt);
475                 if (r < 0) {
476                         log_error_link(link, "Could not allocate route");
477                         link_enter_failed(link);
478                         return;
479                 }
480
481                 rt->family = AF_INET;
482                 rt->in_addr.in = gateway;
483
484                 link->dhcp_address = addr;
485                 link->dhcp_route = rt;
486                 addr = NULL;
487                 rt = NULL;
488
489                 if (link->network->dhcp_dns) {
490                         r = sd_dhcp_client_get_dns(client, &nameservers);
491                         if (r >= 0) {
492                                 r = manager_update_resolv_conf(link->manager);
493                                 if (r < 0)
494                                         log_error("Failed to update resolv.conf");
495                         }
496                 }
497
498                 if (link->network->dhcp_mtu) {
499                         uint16_t mtu;
500
501                         r = sd_dhcp_client_get_mtu(client, &mtu);
502                         if (r >= 0) {
503                                 r = link_set_mtu(link, mtu);
504                                 if (r < 0)
505                                         log_error_link(link, "Failed to set MTU "
506                                                              "to %" PRIu16, mtu);
507                         }
508                 }
509
510                 link_enter_set_addresses(link);
511         }
512
513         return;
514 }
515
516 static int link_acquire_conf(Link *link) {
517         int r;
518
519         assert(link);
520         assert(link->network);
521         assert(link->network->dhcp);
522         assert(link->manager);
523         assert(link->manager->event);
524
525         if (!link->dhcp) {
526                 link->dhcp = sd_dhcp_client_new(link->manager->event);
527                 if (!link->dhcp)
528                         return -ENOMEM;
529
530                 r = sd_dhcp_client_set_index(link->dhcp, link->ifindex);
531                 if (r < 0)
532                         return r;
533
534                 r = sd_dhcp_client_set_mac(link->dhcp, &link->mac);
535                 if (r < 0)
536                         return r;
537
538                 r = sd_dhcp_client_set_callback(link->dhcp, dhcp_handler, link);
539                 if (r < 0)
540                         return r;
541         }
542
543         log_debug_link(link, "acquiring DHCPv4 lease");
544
545         if (link->network->dhcp_mtu) {
546                 r = sd_dhcp_client_set_request_option(link->dhcp, 26);
547                 if (r < 0)
548                         return r;
549         }
550
551         r = sd_dhcp_client_start(link->dhcp);
552         if (r < 0)
553                 return r;
554
555         return 0;
556 }
557
558 static int link_update_flags(Link *link, unsigned flags) {
559         int r;
560
561         assert(link);
562         assert(link->network);
563
564         if (link->state == LINK_STATE_FAILED)
565                 return 0;
566
567         if (link->flags == flags) {
568                 log_debug_link(link, "link status unchanged: %#.8x", flags);
569                 return 0;
570         }
571
572         if ((link->flags & IFF_UP) != (flags & IFF_UP))
573                 log_info_link(link,
574                               "power %s", flags & IFF_UP ? "on": "off");
575
576         if ((link->flags & IFF_LOWER_UP) != (flags & IFF_LOWER_UP)) {
577                 if (flags & IFF_LOWER_UP) {
578                         log_info_link(link, "carrier on");
579
580                         if (link->network->dhcp) {
581                                 r = link_acquire_conf(link);
582                                 if (r < 0) {
583                                         link_enter_failed(link);
584                                         return r;
585                                 }
586                         }
587                 } else {
588                         log_info_link(link, "carrier off");
589
590                         if (link->network->dhcp) {
591                                 r = sd_dhcp_client_stop(link->dhcp);
592                                 if (r < 0) {
593                                         link_enter_failed(link);
594                                         return r;
595                                 }
596                         }
597                 }
598         }
599
600         log_debug_link(link,
601                        "link status updated: %#.8x -> %#.8x", link->flags, flags);
602
603         link->flags = flags;
604
605         return 0;
606 }
607
608 static int link_up_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
609         Link *link = userdata;
610         int r;
611
612         assert(link);
613
614         if (link->state == LINK_STATE_FAILED)
615                 return 1;
616
617         r = sd_rtnl_message_get_errno(m);
618         if (r < 0) {
619                 log_warning_link(link,
620                                  "could not bring up interface: %s", strerror(-r));
621                 link_enter_failed(link);
622         }
623
624         link_update_flags(link, link->flags | IFF_UP);
625
626         return 1;
627 }
628
629 static int link_up(Link *link) {
630         _cleanup_sd_rtnl_message_unref_ sd_rtnl_message *req = NULL;
631         int r;
632
633         assert(link);
634         assert(link->manager);
635         assert(link->manager->rtnl);
636
637         log_debug_link(link, "bringing link up");
638
639         r = sd_rtnl_message_link_new(RTM_SETLINK, link->ifindex, &req);
640         if (r < 0) {
641                 log_error_link(link, "Could not allocate RTM_SETLINK message");
642                 return r;
643         }
644
645         r = sd_rtnl_message_link_set_flags(req, IFF_UP);
646         if (r < 0) {
647                 log_error_link(link, "Could not set link flags: %s", strerror(-r));
648                 return r;
649         }
650
651         r = sd_rtnl_call_async(link->manager->rtnl, req, link_up_handler, link, 0, NULL);
652         if (r < 0) {
653                 log_error_link(link,
654                                "Could not send rtnetlink message: %s", strerror(-r));
655                 return r;
656         }
657
658         return 0;
659 }
660
661 static int link_bridge_joined(Link *link) {
662         int r;
663
664         assert(link);
665         assert(link->state == LINK_STATE_JOINING_BRIDGE);
666         assert(link->network);
667
668         r = link_up(link);
669         if (r < 0) {
670                 link_enter_failed(link);
671                 return r;
672         }
673
674         if (!link->network->dhcp)
675                 return link_enter_set_addresses(link);
676
677         return 0;
678 }
679
680 static int bridge_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
681         Link *link = userdata;
682         int r;
683
684         assert(link);
685         assert(link->state == LINK_STATE_JOINING_BRIDGE || link->state == LINK_STATE_FAILED);
686         assert(link->network);
687
688         if (link->state == LINK_STATE_FAILED)
689                 return 1;
690
691         r = sd_rtnl_message_get_errno(m);
692         if (r < 0) {
693                 log_struct_link(LOG_ERR, link,
694                                 "MESSAGE=%s: could not join bridge '%s': %s",
695                                 link->ifname, link->network->bridge->name, strerror(-r),
696                                 BRIDGE(link->network->bridge),
697                                 NULL);
698                 link_enter_failed(link);
699                 return 1;
700         }
701
702         log_struct_link(LOG_DEBUG, link,
703                         "MESSAGE=%s: joined bridge '%s'",
704                         link->network->bridge->name,
705                         BRIDGE(link->network->bridge),
706                         NULL);
707
708         link_bridge_joined(link);
709
710         return 1;
711 }
712
713 static int link_enter_join_bridge(Link *link) {
714         int r;
715
716         assert(link);
717         assert(link->network);
718         assert(link->state == _LINK_STATE_INVALID);
719
720         link->state = LINK_STATE_JOINING_BRIDGE;
721
722         if (!link->network->bridge)
723                 return link_bridge_joined(link);
724
725         log_struct_link(LOG_DEBUG, link,
726                         "MESSAGE=%s: joining bridge '%s'",
727                         link->network->bridge->name,
728                         BRIDGE(link->network->bridge),
729                         NULL);
730         log_debug_link(link, "joining bridge");
731
732         r = bridge_join(link->network->bridge, link, &bridge_handler);
733         if (r < 0) {
734                 log_struct_link(LOG_WARNING, link,
735                                 "MESSAGE=%s: could not join bridge '%s': %s",
736                                 link->network->bridge->name, strerror(-r),
737                                 BRIDGE(link->network->bridge),
738                                 NULL);
739                 link_enter_failed(link);
740                 return r;
741         }
742
743         return 0;
744 }
745
746 static int link_get_handler(sd_rtnl *rtnl, sd_rtnl_message *m, void *userdata) {
747         Link *link = userdata;
748         int r;
749
750         assert(link);
751
752         if (link->state == LINK_STATE_FAILED)
753                 return 1;
754
755         r = sd_rtnl_message_get_errno(m);
756         if (r < 0) {
757                 log_warning_link(link, "could not get state: %s", strerror(-r));
758                 link_enter_failed(link);
759         }
760
761         log_debug_link(link, "got link state");
762
763         link_update(link, m);
764
765         return 1;
766 }
767
768 static int link_get(Link *link) {
769         _cleanup_sd_rtnl_message_unref_ sd_rtnl_message *req = NULL;
770         int r;
771
772         assert(link);
773         assert(link->manager);
774         assert(link->manager->rtnl);
775
776         log_debug_link(link, "requesting link status");
777
778         r = sd_rtnl_message_link_new(RTM_GETLINK, link->ifindex, &req);
779         if (r < 0) {
780                 log_error_link(link, "Could not allocate RTM_GETLINK message");
781                 return r;
782         }
783
784         r = sd_rtnl_call_async(link->manager->rtnl, req, link_get_handler, link, 0, NULL);
785         if (r < 0) {
786                 log_error_link(link,
787                                "Could not send rtnetlink message: %s", strerror(-r));
788                 return r;
789         }
790
791         return 0;
792 }
793
794 int link_configure(Link *link) {
795         int r;
796
797         assert(link);
798         assert(link->network);
799         assert(link->state == _LINK_STATE_INVALID);
800
801         r = link_get(link);
802         if (r < 0) {
803                 link_enter_failed(link);
804                 return r;
805         }
806
807         return link_enter_join_bridge(link);
808 }
809
810 int link_update(Link *link, sd_rtnl_message *m) {
811         unsigned flags;
812         void *data;
813         uint16_t type;
814         int r;
815
816         assert(link);
817         assert(m);
818
819         if (link->state == LINK_STATE_FAILED)
820                 return 0;
821
822         r = sd_rtnl_message_link_get_flags(m, &flags);
823         if (r < 0) {
824                 log_warning_link(link, "Could not get link flags");
825                 return r;
826         }
827
828         while (sd_rtnl_message_read(m, &type, &data) > 0) {
829                 if (type == IFLA_MTU && link->network->dhcp_mtu && !link->original_mtu) {
830                         link->original_mtu = *(uint16_t *) data;
831                         log_debug_link(link, "saved original MTU: %" PRIu16, link->original_mtu);
832                 }
833         }
834
835         return link_update_flags(link, flags);
836 }