]> git.ipfire.org Git - thirdparty/systemd.git/blame - src/network/networkd-manager.c
Replace empty ternary with helper method
[thirdparty/systemd.git] / src / network / networkd-manager.c
CommitLineData
53e1b683 1/* SPDX-License-Identifier: LGPL-2.1+ */
f579559b
TG
2/***
3 This file is part of systemd.
4
5 Copyright 2013 Tom Gundersen <teg@jklm.no>
6
7 systemd is free software; you can redistribute it and/or modify it
8 under the terms of the GNU Lesser General Public License as published by
9 the Free Software Foundation; either version 2.1 of the License, or
10 (at your option) any later version.
11
12 systemd is distributed in the hope that it will be useful, but
13 WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 Lesser General Public License for more details.
16
17 You should have received a copy of the GNU Lesser General Public License
18 along with systemd; If not, see <http://www.gnu.org/licenses/>.
19 ***/
20
091a364c 21#include <sys/socket.h>
bbf7c048 22#include <linux/if.h>
bce67bbe 23#include <linux/fib_rules.h>
3bef724f 24
fc2f9534 25#include "sd-daemon.h"
07630cea 26#include "sd-netlink.h"
fc2f9534 27
b5efdb8a 28#include "alloc-util.h"
a97dcc12 29#include "bus-util.h"
07630cea 30#include "conf-parser.h"
a97dcc12 31#include "def.h"
482d1aeb 32#include "dns-domain.h"
3ffd4af2 33#include "fd-util.h"
0d39fa9c 34#include "fileio.h"
07630cea 35#include "libudev-private.h"
4f5f911e 36#include "local-addresses.h"
07630cea 37#include "netlink-util.h"
23f53b99 38#include "networkd-manager.h"
00616955 39#include "ordered-set.h"
07630cea
LP
40#include "path-util.h"
41#include "set.h"
42#include "udev-util.h"
43#include "virt.h"
505f8da7 44
be660c37
AR
45/* use 8 MB for receive socket kernel queue. */
46#define RCVBUF_SIZE (8*1024*1024)
47
2ad8416d
ZJS
48const char* const network_dirs[] = {
49 "/etc/systemd/network",
50 "/run/systemd/network",
51 "/usr/lib/systemd/network",
349cc4a5 52#if HAVE_SPLIT_USR
2ad8416d
ZJS
53 "/lib/systemd/network",
54#endif
55 NULL};
56
11bf3cce
LP
57static int setup_default_address_pool(Manager *m) {
58 AddressPool *p;
59 int r;
60
61 assert(m);
62
63 /* Add in the well-known private address ranges. */
64
65 r = address_pool_new_from_string(m, &p, AF_INET6, "fc00::", 7);
66 if (r < 0)
67 return r;
68
69 r = address_pool_new_from_string(m, &p, AF_INET, "192.168.0.0", 16);
70 if (r < 0)
71 return r;
72
73 r = address_pool_new_from_string(m, &p, AF_INET, "172.16.0.0", 12);
74 if (r < 0)
75 return r;
76
77 r = address_pool_new_from_string(m, &p, AF_INET, "10.0.0.0", 8);
78 if (r < 0)
79 return r;
80
81 return 0;
82}
83
9c0a72f9
TG
84static int on_bus_retry(sd_event_source *s, usec_t usec, void *userdata) {
85 Manager *m = userdata;
86
87 assert(s);
88 assert(m);
89
90 m->bus_retry_event_source = sd_event_source_unref(m->bus_retry_event_source);
91
92 manager_connect_bus(m);
93
94 return 0;
95}
96
97static int manager_reset_all(Manager *m) {
98 Link *link;
99 Iterator i;
100 int r;
101
102 assert(m);
103
104 HASHMAP_FOREACH(link, m->links, i) {
105 r = link_carrier_reset(link);
106 if (r < 0)
2f3cf1f9 107 log_link_warning_errno(link, r, "Could not reset carrier: %m");
9c0a72f9
TG
108 }
109
110 return 0;
111}
112
19070062 113static int match_prepare_for_sleep(sd_bus_message *message, void *userdata, sd_bus_error *ret_error) {
9c0a72f9
TG
114 Manager *m = userdata;
115 int b, r;
116
19070062 117 assert(message);
9c0a72f9
TG
118
119 r = sd_bus_message_read(message, "b", &b);
120 if (r < 0) {
121 log_debug_errno(r, "Failed to parse PrepareForSleep signal: %m");
122 return 0;
123 }
124
125 if (b)
126 return 0;
127
128 log_debug("Coming back from suspend, resetting all connections...");
129
130 manager_reset_all(m);
131
132 return 0;
133}
134
135int manager_connect_bus(Manager *m) {
136 int r;
137
138 assert(m);
139
140 r = sd_bus_default_system(&m->bus);
fb72b1d9 141 if (r < 0) {
9c0a72f9 142 /* We failed to connect? Yuck, we must be in early
d7ea7bb8 143 * boot. Let's try in 5s again. */
9c0a72f9
TG
144
145 log_debug_errno(r, "Failed to connect to bus, trying again in 5s: %m");
146
147 r = sd_event_add_time(m->event, &m->bus_retry_event_source, CLOCK_MONOTONIC, now(CLOCK_MONOTONIC) + 5*USEC_PER_SEC, 0, on_bus_retry, m);
148 if (r < 0)
149 return log_error_errno(r, "Failed to install bus reconnect time event: %m");
150
151 return 0;
7d6884b6
TA
152 }
153
154 if (r < 0)
9c0a72f9
TG
155 return r;
156
9c0a72f9
TG
157 r = sd_bus_add_match(m->bus, &m->prepare_for_sleep_slot,
158 "type='signal',"
159 "sender='org.freedesktop.login1',"
160 "interface='org.freedesktop.login1.Manager',"
161 "member='PrepareForSleep',"
162 "path='/org/freedesktop/login1'",
163 match_prepare_for_sleep,
164 m);
165 if (r < 0)
166 return log_error_errno(r, "Failed to add match for PrepareForSleep: %m");
167
e331e246
TG
168 r = sd_bus_add_object_vtable(m->bus, NULL, "/org/freedesktop/network1", "org.freedesktop.network1.Manager", manager_vtable, m);
169 if (r < 0)
170 return log_error_errno(r, "Failed to add manager object vtable: %m");
171
172 r = sd_bus_add_fallback_vtable(m->bus, NULL, "/org/freedesktop/network1/link", "org.freedesktop.network1.Link", link_vtable, link_object_find, m);
173 if (r < 0)
174 return log_error_errno(r, "Failed to add link object vtable: %m");
175
176 r = sd_bus_add_node_enumerator(m->bus, NULL, "/org/freedesktop/network1/link", link_node_enumerator, m);
177 if (r < 0)
178 return log_error_errno(r, "Failed to add link enumerator: %m");
3175fcde
TG
179
180 r = sd_bus_add_fallback_vtable(m->bus, NULL, "/org/freedesktop/network1/network", "org.freedesktop.network1.Network", network_vtable, network_object_find, m);
181 if (r < 0)
182 return log_error_errno(r, "Failed to add network object vtable: %m");
183
184 r = sd_bus_add_node_enumerator(m->bus, NULL, "/org/freedesktop/network1/network", network_node_enumerator, m);
185 if (r < 0)
186 return log_error_errno(r, "Failed to add network enumerator: %m");
e331e246
TG
187
188 r = sd_bus_request_name(m->bus, "org.freedesktop.network1", 0);
189 if (r < 0)
190 return log_error_errno(r, "Failed to register name: %m");
191
192 r = sd_bus_attach_event(m->bus, m->event, 0);
193 if (r < 0)
194 return log_error_errno(r, "Failed to attach bus to event loop: %m");
195
7901cea1
MP
196 /* Did we get a timezone or transient hostname from DHCP while D-Bus wasn't up yet? */
197 if (m->dynamic_hostname) {
198 r = manager_set_hostname(m, m->dynamic_hostname);
199 if (r < 0)
200 return r;
201 }
202 if (m->dynamic_timezone) {
203 r = manager_set_timezone(m, m->dynamic_timezone);
204 if (r < 0)
205 return r;
206 }
207
9c0a72f9
TG
208 return 0;
209}
210
5fae368b
TG
211static int manager_udev_process_link(Manager *m, struct udev_device *device) {
212 Link *link = NULL;
213 int r, ifindex;
5544ee85 214
5fae368b
TG
215 assert(m);
216 assert(device);
5544ee85 217
5fae368b
TG
218 if (!streq_ptr(udev_device_get_action(device), "add"))
219 return 0;
5544ee85 220
5fae368b
TG
221 ifindex = udev_device_get_ifindex(device);
222 if (ifindex <= 0) {
2f3cf1f9 223 log_debug("Ignoring udev ADD event for device with invalid ifindex");
5fae368b 224 return 0;
5544ee85
TG
225 }
226
5fae368b
TG
227 r = link_get(m, ifindex, &link);
228 if (r == -ENODEV)
229 return 0;
230 else if (r < 0)
f579559b
TG
231 return r;
232
5fae368b 233 r = link_initialized(link, device);
44de0efc
LP
234 if (r < 0)
235 return r;
236
5fae368b
TG
237 return 0;
238}
be660c37 239
5fae368b
TG
240static int manager_dispatch_link_udev(sd_event_source *source, int fd, uint32_t revents, void *userdata) {
241 Manager *m = userdata;
242 struct udev_monitor *monitor = m->udev_monitor;
243 _cleanup_udev_device_unref_ struct udev_device *device = NULL;
f579559b 244
5fae368b
TG
245 device = udev_monitor_receive_device(monitor);
246 if (!device)
02b59d57
TG
247 return -ENOMEM;
248
5fae368b 249 manager_udev_process_link(m, device);
f579559b
TG
250 return 0;
251}
252
5fae368b
TG
253static int manager_connect_udev(Manager *m) {
254 int r;
f579559b 255
5fae368b
TG
256 /* udev does not initialize devices inside containers,
257 * so we rely on them being already initialized before
258 * entering the container */
75f86906 259 if (detect_container() > 0)
5fae368b 260 return 0;
f579559b 261
5fae368b
TG
262 m->udev = udev_new();
263 if (!m->udev)
264 return -ENOMEM;
02b59d57 265
5fae368b
TG
266 m->udev_monitor = udev_monitor_new_from_netlink(m->udev, "udev");
267 if (!m->udev_monitor)
268 return -ENOMEM;
02b59d57 269
5fae368b 270 r = udev_monitor_filter_add_match_subsystem_devtype(m->udev_monitor, "net", NULL);
02b59d57 271 if (r < 0)
5fae368b 272 return log_error_errno(r, "Could not add udev monitor filter: %m");
02b59d57 273
5fae368b
TG
274 r = udev_monitor_enable_receiving(m->udev_monitor);
275 if (r < 0) {
276 log_error("Could not enable udev monitor");
02b59d57 277 return r;
667fcc6d 278 }
505f8da7 279
5fae368b
TG
280 r = sd_event_add_io(m->event,
281 &m->udev_event_source,
282 udev_monitor_get_fd(m->udev_monitor),
283 EPOLLIN, manager_dispatch_link_udev,
284 m);
285 if (r < 0)
667fcc6d 286 return r;
505f8da7 287
5fae368b 288 r = sd_event_source_set_description(m->udev_event_source, "networkd-udev");
505f8da7
TG
289 if (r < 0)
290 return r;
11a7f229 291
505f8da7
TG
292 return 0;
293}
f579559b 294
1c8e710c
TG
295int manager_rtnl_process_route(sd_netlink *rtnl, sd_netlink_message *message, void *userdata) {
296 Manager *m = userdata;
297 Link *link = NULL;
298 uint16_t type;
299 uint32_t ifindex, priority = 0;
983226f3 300 unsigned char protocol, scope, tos, table, rt_type;
1c8e710c
TG
301 int family;
302 unsigned char dst_prefixlen, src_prefixlen;
303 union in_addr_union dst = {}, gw = {}, src = {}, prefsrc = {};
304 Route *route = NULL;
305 int r;
306
307 assert(rtnl);
308 assert(message);
309 assert(m);
310
311 if (sd_netlink_message_is_error(message)) {
312 r = sd_netlink_message_get_errno(message);
313 if (r < 0)
314 log_warning_errno(r, "rtnl: failed to receive route: %m");
315
316 return 0;
317 }
318
319 r = sd_netlink_message_get_type(message, &type);
320 if (r < 0) {
321 log_warning_errno(r, "rtnl: could not get message type: %m");
322 return 0;
25a1bffc 323 } else if (!IN_SET(type, RTM_NEWROUTE, RTM_DELROUTE)) {
1c8e710c
TG
324 log_warning("rtnl: received unexpected message type when processing route");
325 return 0;
326 }
327
328 r = sd_netlink_message_read_u32(message, RTA_OIF, &ifindex);
329 if (r == -ENODATA) {
330 log_debug("rtnl: received route without ifindex, ignoring");
331 return 0;
332 } else if (r < 0) {
333 log_warning_errno(r, "rtnl: could not get ifindex from route, ignoring: %m");
334 return 0;
335 } else if (ifindex <= 0) {
336 log_warning("rtnl: received route message with invalid ifindex, ignoring: %d", ifindex);
337 return 0;
338 } else {
339 r = link_get(m, ifindex, &link);
340 if (r < 0 || !link) {
341 /* when enumerating we might be out of sync, but we will
342 * get the route again, so just ignore it */
343 if (!m->enumerating)
344 log_warning("rtnl: received route for nonexistent link (%d), ignoring", ifindex);
345 return 0;
346 }
347 }
348
349 r = sd_rtnl_message_route_get_family(message, &family);
350 if (r < 0 || !IN_SET(family, AF_INET, AF_INET6)) {
351 log_link_warning(link, "rtnl: received address with invalid family, ignoring.");
352 return 0;
353 }
354
355 r = sd_rtnl_message_route_get_protocol(message, &protocol);
356 if (r < 0) {
357 log_warning_errno(r, "rtnl: could not get route protocol: %m");
358 return 0;
359 }
360
361 switch (family) {
362 case AF_INET:
363 r = sd_netlink_message_read_in_addr(message, RTA_DST, &dst.in);
364 if (r < 0 && r != -ENODATA) {
365 log_link_warning_errno(link, r, "rtnl: received route without valid destination, ignoring: %m");
366 return 0;
367 }
368
369 r = sd_netlink_message_read_in_addr(message, RTA_GATEWAY, &gw.in);
370 if (r < 0 && r != -ENODATA) {
371 log_link_warning_errno(link, r, "rtnl: received route with invalid gateway, ignoring: %m");
372 return 0;
373 }
374
375 r = sd_netlink_message_read_in_addr(message, RTA_SRC, &src.in);
376 if (r < 0 && r != -ENODATA) {
377 log_link_warning_errno(link, r, "rtnl: received route with invalid source, ignoring: %m");
378 return 0;
379 }
380
381 r = sd_netlink_message_read_in_addr(message, RTA_PREFSRC, &prefsrc.in);
382 if (r < 0 && r != -ENODATA) {
383 log_link_warning_errno(link, r, "rtnl: received route with invalid preferred source, ignoring: %m");
384 return 0;
385 }
386
387 break;
388
389 case AF_INET6:
390 r = sd_netlink_message_read_in6_addr(message, RTA_DST, &dst.in6);
391 if (r < 0 && r != -ENODATA) {
392 log_link_warning_errno(link, r, "rtnl: received route without valid destination, ignoring: %m");
393 return 0;
394 }
395
396 r = sd_netlink_message_read_in6_addr(message, RTA_GATEWAY, &gw.in6);
397 if (r < 0 && r != -ENODATA) {
398 log_link_warning_errno(link, r, "rtnl: received route with invalid gateway, ignoring: %m");
399 return 0;
400 }
401
402 r = sd_netlink_message_read_in6_addr(message, RTA_SRC, &src.in6);
403 if (r < 0 && r != -ENODATA) {
404 log_link_warning_errno(link, r, "rtnl: received route with invalid source, ignoring: %m");
405 return 0;
406 }
407
408 r = sd_netlink_message_read_in6_addr(message, RTA_PREFSRC, &prefsrc.in6);
409 if (r < 0 && r != -ENODATA) {
410 log_link_warning_errno(link, r, "rtnl: received route with invalid preferred source, ignoring: %m");
411 return 0;
412 }
413
414 break;
415
416 default:
74dead34 417 assert_not_reached("Received unsupported address family");
1c8e710c
TG
418 return 0;
419 }
420
421 r = sd_rtnl_message_route_get_dst_prefixlen(message, &dst_prefixlen);
422 if (r < 0) {
423 log_link_warning_errno(link, r, "rtnl: received route with invalid destination prefixlen, ignoring: %m");
424 return 0;
425 }
426
427 r = sd_rtnl_message_route_get_src_prefixlen(message, &src_prefixlen);
428 if (r < 0) {
429 log_link_warning_errno(link, r, "rtnl: received route with invalid source prefixlen, ignoring: %m");
430 return 0;
431 }
432
433 r = sd_rtnl_message_route_get_scope(message, &scope);
434 if (r < 0) {
435 log_link_warning_errno(link, r, "rtnl: received route with invalid scope, ignoring: %m");
436 return 0;
437 }
438
439 r = sd_rtnl_message_route_get_tos(message, &tos);
440 if (r < 0) {
441 log_link_warning_errno(link, r, "rtnl: received route with invalid tos, ignoring: %m");
442 return 0;
443 }
444
983226f3
SS
445 r = sd_rtnl_message_route_get_type(message, &rt_type);
446 if (r < 0) {
447 log_link_warning_errno(link, r, "rtnl: received route with invalid type, ignoring: %m");
448 return 0;
449 }
450
1c8e710c
TG
451 r = sd_rtnl_message_route_get_table(message, &table);
452 if (r < 0) {
453 log_link_warning_errno(link, r, "rtnl: received route with invalid table, ignoring: %m");
454 return 0;
455 }
456
457 r = sd_netlink_message_read_u32(message, RTA_PRIORITY, &priority);
458 if (r < 0 && r != -ENODATA) {
459 log_link_warning_errno(link, r, "rtnl: received route with invalid priority, ignoring: %m");
460 return 0;
461 }
462
463 route_get(link, family, &dst, dst_prefixlen, tos, priority, table, &route);
464
465 switch (type) {
466 case RTM_NEWROUTE:
467 if (!route) {
468 /* A route appeared that we did not request */
469 r = route_add_foreign(link, family, &dst, dst_prefixlen, tos, priority, table, &route);
470 if (r < 0)
471 return 0;
472 }
473
983226f3 474 route_update(route, &src, src_prefixlen, &gw, &prefsrc, scope, rt_type, protocol);
1c8e710c
TG
475
476 break;
477
478 case RTM_DELROUTE:
b9642f41 479 route_free(route);
1c8e710c 480 break;
b9642f41 481
1c8e710c
TG
482 default:
483 assert_not_reached("Received invalid RTNL message type");
484 }
485
486 return 1;
487}
488
200a0868
TG
489int manager_rtnl_process_address(sd_netlink *rtnl, sd_netlink_message *message, void *userdata) {
490 Manager *m = userdata;
491 Link *link = NULL;
492 uint16_t type;
200a0868 493 unsigned char flags;
054f0db4
TG
494 int family;
495 unsigned char prefixlen;
496 unsigned char scope;
497 union in_addr_union in_addr;
498 struct ifa_cacheinfo cinfo;
499 Address *address = NULL;
200a0868
TG
500 char buf[INET6_ADDRSTRLEN], valid_buf[FORMAT_TIMESPAN_MAX];
501 const char *valid_str = NULL;
502 int r, ifindex;
503
504 assert(rtnl);
505 assert(message);
506 assert(m);
507
508 if (sd_netlink_message_is_error(message)) {
509 r = sd_netlink_message_get_errno(message);
510 if (r < 0)
511 log_warning_errno(r, "rtnl: failed to receive address: %m");
512
513 return 0;
514 }
515
516 r = sd_netlink_message_get_type(message, &type);
517 if (r < 0) {
518 log_warning_errno(r, "rtnl: could not get message type: %m");
519 return 0;
25a1bffc 520 } else if (!IN_SET(type, RTM_NEWADDR, RTM_DELADDR)) {
200a0868
TG
521 log_warning("rtnl: received unexpected message type when processing address");
522 return 0;
523 }
524
525 r = sd_rtnl_message_addr_get_ifindex(message, &ifindex);
526 if (r < 0) {
527 log_warning_errno(r, "rtnl: could not get ifindex from address: %m");
528 return 0;
529 } else if (ifindex <= 0) {
530 log_warning("rtnl: received address message with invalid ifindex: %d", ifindex);
531 return 0;
532 } else {
533 r = link_get(m, ifindex, &link);
534 if (r < 0 || !link) {
535 /* when enumerating we might be out of sync, but we will
536 * get the address again, so just ignore it */
537 if (!m->enumerating)
538 log_warning("rtnl: received address for nonexistent link (%d), ignoring", ifindex);
539 return 0;
540 }
541 }
542
054f0db4
TG
543 r = sd_rtnl_message_addr_get_family(message, &family);
544 if (r < 0 || !IN_SET(family, AF_INET, AF_INET6)) {
200a0868
TG
545 log_link_warning(link, "rtnl: received address with invalid family, ignoring.");
546 return 0;
547 }
548
054f0db4 549 r = sd_rtnl_message_addr_get_prefixlen(message, &prefixlen);
200a0868
TG
550 if (r < 0) {
551 log_link_warning_errno(link, r, "rtnl: received address with invalid prefixlen, ignoring: %m");
552 return 0;
553 }
554
054f0db4 555 r = sd_rtnl_message_addr_get_scope(message, &scope);
200a0868
TG
556 if (r < 0) {
557 log_link_warning_errno(link, r, "rtnl: received address with invalid scope, ignoring: %m");
558 return 0;
559 }
560
561 r = sd_rtnl_message_addr_get_flags(message, &flags);
562 if (r < 0) {
563 log_link_warning_errno(link, r, "rtnl: received address with invalid flags, ignoring: %m");
564 return 0;
565 }
200a0868 566
054f0db4 567 switch (family) {
200a0868 568 case AF_INET:
054f0db4 569 r = sd_netlink_message_read_in_addr(message, IFA_LOCAL, &in_addr.in);
200a0868
TG
570 if (r < 0) {
571 log_link_warning_errno(link, r, "rtnl: received address without valid address, ignoring: %m");
572 return 0;
573 }
574
575 break;
576
577 case AF_INET6:
054f0db4 578 r = sd_netlink_message_read_in6_addr(message, IFA_ADDRESS, &in_addr.in6);
200a0868
TG
579 if (r < 0) {
580 log_link_warning_errno(link, r, "rtnl: received address without valid address, ignoring: %m");
581 return 0;
582 }
583
584 break;
585
586 default:
1c8e710c 587 log_link_debug(link, "rtnl: ignoring unsupported address family: %d", family);
200a0868
TG
588 }
589
054f0db4 590 if (!inet_ntop(family, &in_addr, buf, INET6_ADDRSTRLEN)) {
200a0868
TG
591 log_link_warning(link, "Could not print address");
592 return 0;
593 }
594
054f0db4 595 r = sd_netlink_message_read_cache_info(message, IFA_CACHEINFO, &cinfo);
200a0868 596 if (r >= 0) {
4058d339 597 if (cinfo.ifa_valid != CACHE_INFO_INFINITY_LIFE_TIME)
200a0868 598 valid_str = format_timespan(valid_buf, FORMAT_TIMESPAN_MAX,
054f0db4 599 cinfo.ifa_valid * USEC_PER_SEC,
200a0868
TG
600 USEC_PER_SEC);
601 }
602
054f0db4 603 address_get(link, family, &in_addr, prefixlen, &address);
200a0868
TG
604
605 switch (type) {
606 case RTM_NEWADDR:
36c32f61 607 if (address)
4058d339 608 log_link_debug(link, "Updating address: %s/%u (valid %s%s)", buf, prefixlen,
87e4e28d 609 valid_str ? "for " : "forever", strempty(valid_str));
36c32f61 610 else {
adda1ed9
TG
611 /* An address appeared that we did not request */
612 r = address_add_foreign(link, family, &in_addr, prefixlen, &address);
cf1d700d 613 if (r < 0) {
054f0db4 614 log_link_warning_errno(link, r, "Failed to add address %s/%u: %m", buf, prefixlen);
cf1d700d
TG
615 return 0;
616 } else
4058d339 617 log_link_debug(link, "Adding address: %s/%u (valid %s%s)", buf, prefixlen,
87e4e28d 618 valid_str ? "for " : "forever", strempty(valid_str));
200a0868
TG
619 }
620
58fda79c 621 address_update(address, flags, scope, &cinfo);
36c32f61 622
200a0868
TG
623 break;
624
625 case RTM_DELADDR:
626
054f0db4 627 if (address) {
4058d339 628 log_link_debug(link, "Removing address: %s/%u (valid %s%s)", buf, prefixlen,
87e4e28d 629 valid_str ? "for " : "forever", strempty(valid_str));
91b5f997 630 address_drop(address);
200a0868 631 } else
4058d339 632 log_link_warning(link, "Removing non-existent address: %s/%u (valid %s%s)", buf, prefixlen,
87e4e28d 633 valid_str ? "for " : "forever", strempty(valid_str));
200a0868
TG
634
635 break;
636 default:
637 assert_not_reached("Received invalid RTNL message type");
638 }
639
640 return 1;
641}
642
1c4baffc 643static int manager_rtnl_process_link(sd_netlink *rtnl, sd_netlink_message *message, void *userdata) {
505f8da7
TG
644 Manager *m = userdata;
645 Link *link = NULL;
4d473d5d 646 NetDev *netdev = NULL;
f2236469 647 uint16_t type;
ca4e095a 648 const char *name;
505f8da7 649 int r, ifindex;
f579559b 650
505f8da7
TG
651 assert(rtnl);
652 assert(message);
f579559b
TG
653 assert(m);
654
1c4baffc
TG
655 if (sd_netlink_message_is_error(message)) {
656 r = sd_netlink_message_get_errno(message);
45af44d4 657 if (r < 0)
2f3cf1f9 658 log_warning_errno(r, "rtnl: Could not receive link: %m");
45af44d4
TG
659
660 return 0;
661 }
662
1c4baffc 663 r = sd_netlink_message_get_type(message, &type);
f2236469 664 if (r < 0) {
2f3cf1f9 665 log_warning_errno(r, "rtnl: Could not get message type: %m");
f2236469 666 return 0;
25a1bffc 667 } else if (!IN_SET(type, RTM_NEWLINK, RTM_DELLINK)) {
2f3cf1f9 668 log_warning("rtnl: Received unexpected message type when processing link");
cdfee943 669 return 0;
f2236469
TG
670 }
671
505f8da7 672 r = sd_rtnl_message_link_get_ifindex(message, &ifindex);
45af44d4 673 if (r < 0) {
2f3cf1f9 674 log_warning_errno(r, "rtnl: Could not get ifindex from link: %m");
45af44d4
TG
675 return 0;
676 } else if (ifindex <= 0) {
677 log_warning("rtnl: received link message with invalid ifindex: %d", ifindex);
505f8da7 678 return 0;
a0db8e46 679 }
f579559b 680
1c4baffc 681 r = sd_netlink_message_read_string(message, IFLA_IFNAME, &name);
45af44d4 682 if (r < 0) {
2f3cf1f9 683 log_warning_errno(r, "rtnl: Received link message without ifname: %m");
4d473d5d 684 return 0;
a0db8e46
ZJS
685 }
686
687 (void) link_get(m, ifindex, &link);
688 (void) netdev_get(m, name, &netdev);
4d473d5d
TG
689
690 switch (type) {
691 case RTM_NEWLINK:
692 if (!link) {
693 /* link is new, so add it */
694 r = link_add(m, message, &link);
695 if (r < 0) {
2f3cf1f9 696 log_warning_errno(r, "Could not add new link: %m");
4d473d5d
TG
697 return 0;
698 }
699 }
700
701 if (netdev) {
702 /* netdev exists, so make sure the ifindex matches */
505f8da7
TG
703 r = netdev_set_ifindex(netdev, message);
704 if (r < 0) {
2f3cf1f9 705 log_warning_errno(r, "Could not set ifindex on netdev: %m");
505f8da7
TG
706 return 0;
707 }
708 }
e1202047 709
f2236469
TG
710 r = link_update(link, message);
711 if (r < 0)
712 return 0;
4d473d5d
TG
713
714 break;
715
716 case RTM_DELLINK:
717 link_drop(link);
718 netdev_drop(netdev);
719
720 break;
721
722 default:
723 assert_not_reached("Received invalid RTNL message type.");
f2236469 724 }
505f8da7
TG
725
726 return 1;
727}
728
bce67bbe
SS
729int manager_rtnl_process_rule(sd_netlink *rtnl, sd_netlink_message *message, void *userdata) {
730 uint8_t tos = 0, to_prefixlen = 0, from_prefixlen = 0;
731 RoutingPolicyRule *rule = NULL;
732 union in_addr_union to, from;
733 uint32_t fwmark = 0, table = 0;
734 Manager *m = userdata;
762e2659 735 char *iif, *oif;
bce67bbe
SS
736 uint16_t type;
737 int family;
738 int r;
739
740 assert(rtnl);
741 assert(message);
742 assert(m);
743
744 if (sd_netlink_message_is_error(message)) {
745 r = sd_netlink_message_get_errno(message);
746 if (r < 0)
747 log_warning_errno(r, "rtnl: failed to receive rule: %m");
748
749 return 0;
750 }
751
752 r = sd_netlink_message_get_type(message, &type);
753 if (r < 0) {
754 log_warning_errno(r, "rtnl: could not get message type: %m");
755 return 0;
756 } else if (!IN_SET(type, RTM_NEWRULE, RTM_DELRULE)) {
757 log_warning("rtnl: received unexpected message type '%u' when processing rule.", type);
758 return 0;
759 }
760
761 r = sd_rtnl_message_get_family(message, &family);
615ded62
YW
762 if (r < 0) {
763 log_warning_errno(r, "rtnl: could not get rule family: %m");
764 return 0;
765 } else if (!IN_SET(family, AF_INET, AF_INET6)) {
766 log_debug("rtnl: received address with invalid family %u, ignoring.", family);
bce67bbe
SS
767 return 0;
768 }
769
770 switch (family) {
771 case AF_INET:
772 r = sd_netlink_message_read_in_addr(message, FRA_SRC, &from.in);
773 if (r >= 0) {
774 r = sd_rtnl_message_routing_policy_rule_get_rtm_src_prefixlen(message, &from_prefixlen);
775 if (r < 0)
776 log_warning_errno(r, "rtnl: failed to retrive rule from prefix length: %m");
777 }
778
779 r = sd_netlink_message_read_in_addr(message, FRA_DST, &to.in);
780 if (r >= 0) {
781 r = sd_rtnl_message_routing_policy_rule_get_rtm_dst_prefixlen(message, &to_prefixlen);
782 if (r < 0)
783 log_warning_errno(r, "rtnl: failed to retrive rule to prefix length: %m");
784 }
785
786 break;
787
788 case AF_INET6:
789 r = sd_netlink_message_read_in6_addr(message, FRA_SRC, &from.in6);
790 if (r >= 0) {
791 r = sd_rtnl_message_routing_policy_rule_get_rtm_src_prefixlen(message, &from_prefixlen);
792 if (r < 0)
793 log_warning_errno(r, "rtnl: failed to retrive rule from prefix length: %m");
794 }
795
796 r = sd_netlink_message_read_in6_addr(message, FRA_DST, &to.in6);
797 if (r >= 0) {
798 r = sd_rtnl_message_routing_policy_rule_get_rtm_dst_prefixlen(message, &to_prefixlen);
799 if (r < 0)
800 log_warning_errno(r, "rtnl: failed to retrive rule to prefix length: %m");
801 }
802
803 break;
804
805 default:
74dead34 806 assert_not_reached("Received unsupported address family");
bce67bbe
SS
807 }
808
809 if (from_prefixlen == 0 && to_prefixlen == 0)
810 return 0;
811
812 (void) sd_netlink_message_read_u32(message, FRA_FWMARK, &fwmark);
813 (void) sd_netlink_message_read_u32(message, FRA_TABLE, &table);
814 (void) sd_rtnl_message_routing_policy_rule_get_tos(message, &tos);
762e2659
SS
815 (void) sd_netlink_message_read_string(message, FRA_IIFNAME, (const char **) &iif);
816 (void) sd_netlink_message_read_string(message, FRA_OIFNAME, (const char **) &oif);
bce67bbe 817
762e2659 818 (void) routing_policy_rule_get(m, family, &from, from_prefixlen, &to, to_prefixlen, tos, fwmark, table, iif, oif, &rule);
bce67bbe
SS
819
820 switch (type) {
821 case RTM_NEWRULE:
822 if(!rule) {
762e2659 823 r = routing_policy_rule_add_foreign(m, family, &from, from_prefixlen, &to, to_prefixlen, tos, fwmark, table, iif, oif, &rule);
bce67bbe
SS
824 if (r < 0) {
825 log_warning_errno(r, "Could not add rule: %m");
826 return 0;
827 }
828 }
829 break;
830 case RTM_DELRULE:
831 routing_policy_rule_free(rule);
832
833 break;
834
835 default:
836 assert_not_reached("Received invalid RTNL message type");
837 }
838
839 return 1;
840}
841
5fae368b
TG
842static int systemd_netlink_fd(void) {
843 int n, fd, rtnl_fd = -EINVAL;
844
845 n = sd_listen_fds(true);
846 if (n <= 0)
847 return -EINVAL;
848
849 for (fd = SD_LISTEN_FDS_START; fd < SD_LISTEN_FDS_START + n; fd ++) {
850 if (sd_is_socket(fd, AF_NETLINK, SOCK_RAW, -1) > 0) {
851 if (rtnl_fd >= 0)
852 return -EINVAL;
853
854 rtnl_fd = fd;
855 }
856 }
857
858 return rtnl_fd;
859}
860
861static int manager_connect_rtnl(Manager *m) {
862 int fd, r;
505f8da7
TG
863
864 assert(m);
505f8da7 865
5fae368b
TG
866 fd = systemd_netlink_fd();
867 if (fd < 0)
1c4baffc 868 r = sd_netlink_open(&m->rtnl);
5fae368b 869 else
1c4baffc 870 r = sd_netlink_open_fd(&m->rtnl, fd);
505f8da7
TG
871 if (r < 0)
872 return r;
873
1c4baffc 874 r = sd_netlink_inc_rcvbuf(m->rtnl, RCVBUF_SIZE);
f579559b 875 if (r < 0)
bf5332d2 876 return r;
f579559b 877
1c4baffc 878 r = sd_netlink_attach_event(m->rtnl, m->event, 0);
505f8da7
TG
879 if (r < 0)
880 return r;
f579559b 881
1c4baffc 882 r = sd_netlink_add_match(m->rtnl, RTM_NEWLINK, &manager_rtnl_process_link, m);
5fae368b
TG
883 if (r < 0)
884 return r;
505f8da7 885
1c4baffc 886 r = sd_netlink_add_match(m->rtnl, RTM_DELLINK, &manager_rtnl_process_link, m);
5fae368b
TG
887 if (r < 0)
888 return r;
45af44d4 889
200a0868 890 r = sd_netlink_add_match(m->rtnl, RTM_NEWADDR, &manager_rtnl_process_address, m);
5fae368b
TG
891 if (r < 0)
892 return r;
893
200a0868 894 r = sd_netlink_add_match(m->rtnl, RTM_DELADDR, &manager_rtnl_process_address, m);
5fae368b
TG
895 if (r < 0)
896 return r;
897
1c8e710c
TG
898 r = sd_netlink_add_match(m->rtnl, RTM_NEWROUTE, &manager_rtnl_process_route, m);
899 if (r < 0)
900 return r;
901
902 r = sd_netlink_add_match(m->rtnl, RTM_DELROUTE, &manager_rtnl_process_route, m);
903 if (r < 0)
904 return r;
905
bce67bbe
SS
906 r = sd_netlink_add_match(m->rtnl, RTM_NEWRULE, &manager_rtnl_process_rule, m);
907 if (r < 0)
908 return r;
909
910 r = sd_netlink_add_match(m->rtnl, RTM_DELRULE, &manager_rtnl_process_rule, m);
911 if (r < 0)
912 return r;
913
5fae368b 914 return 0;
45af44d4 915}
505f8da7 916
5512a963 917static int ordered_set_put_in_addr_data(OrderedSet *s, const struct in_addr_data *address) {
84de38c5
TG
918 char *p;
919 int r;
920
921 assert(s);
5512a963
LP
922 assert(address);
923
924 r = in_addr_to_string(address->family, &address->address, &p);
925 if (r < 0)
926 return r;
927
928 r = ordered_set_consume(s, p);
929 if (r == -EEXIST)
930 return 0;
931
932 return r;
933}
934
935static int ordered_set_put_in_addr_datav(OrderedSet *s, const struct in_addr_data *addresses, unsigned n) {
936 int r, c = 0;
937 unsigned i;
938
939 assert(s);
940 assert(addresses || n == 0);
941
942 for (i = 0; i < n; i++) {
943 r = ordered_set_put_in_addr_data(s, addresses+i);
944 if (r < 0)
945 return r;
946
947 c += r;
948 }
949
950 return c;
951}
952
953static int ordered_set_put_in4_addr(OrderedSet *s, const struct in_addr *address) {
954 char *p;
955 int r;
956
957 assert(s);
958 assert(address);
84de38c5
TG
959
960 r = in_addr_to_string(AF_INET, (const union in_addr_union*) address, &p);
961 if (r < 0)
962 return r;
963
00616955 964 r = ordered_set_consume(s, p);
84de38c5
TG
965 if (r == -EEXIST)
966 return 0;
967
968 return r;
969}
970
5512a963
LP
971static int ordered_set_put_in4_addrv(OrderedSet *s, const struct in_addr *addresses, unsigned n) {
972 int r, c = 0;
973 unsigned i;
84de38c5
TG
974
975 assert(s);
5512a963 976 assert(n == 0 || addresses);
84de38c5
TG
977
978 for (i = 0; i < n; i++) {
5512a963 979 r = ordered_set_put_in4_addr(s, addresses+i);
84de38c5
TG
980 if (r < 0)
981 return r;
982
983 c += r;
984 }
985
986 return c;
987}
988
00616955 989static void print_string_set(FILE *f, const char *field, OrderedSet *s) {
84de38c5
TG
990 bool space = false;
991 Iterator i;
992 char *p;
993
00616955 994 if (ordered_set_isempty(s))
84de38c5
TG
995 return;
996
4b61c875 997 fputs_unlocked(field, f);
84de38c5 998
d390f8ef
LP
999 ORDERED_SET_FOREACH(p, s, i)
1000 fputs_with_space(f, p, NULL, &space);
1001
4b61c875 1002 fputc_unlocked('\n', f);
84de38c5
TG
1003}
1004
1005static int manager_save(Manager *m) {
00616955 1006 _cleanup_ordered_set_free_free_ OrderedSet *dns = NULL, *ntp = NULL, *search_domains = NULL, *route_domains = NULL;
bce67bbe
SS
1007 RoutingPolicyRule *rule = NULL;
1008 bool space = false;
84de38c5
TG
1009 Link *link;
1010 Iterator i;
1011 _cleanup_free_ char *temp_path = NULL;
1012 _cleanup_fclose_ FILE *f = NULL;
1013 LinkOperationalState operstate = LINK_OPERSTATE_OFF;
1014 const char *operstate_str;
1015 int r;
1016
1017 assert(m);
1018 assert(m->state_file);
1019
1020 /* We add all NTP and DNS server to a set, to filter out duplicates */
00616955 1021 dns = ordered_set_new(&string_hash_ops);
84de38c5
TG
1022 if (!dns)
1023 return -ENOMEM;
1024
00616955 1025 ntp = ordered_set_new(&string_hash_ops);
84de38c5
TG
1026 if (!ntp)
1027 return -ENOMEM;
1028
482d1aeb 1029 search_domains = ordered_set_new(&dns_name_hash_ops);
3df9bec5
LP
1030 if (!search_domains)
1031 return -ENOMEM;
1032
482d1aeb 1033 route_domains = ordered_set_new(&dns_name_hash_ops);
3df9bec5 1034 if (!route_domains)
84de38c5
TG
1035 return -ENOMEM;
1036
1037 HASHMAP_FOREACH(link, m->links, i) {
1038 if (link->flags & IFF_LOOPBACK)
1039 continue;
1040
1041 if (link->operstate > operstate)
1042 operstate = link->operstate;
1043
1044 if (!link->network)
1045 continue;
1046
1047 /* First add the static configured entries */
5512a963 1048 r = ordered_set_put_in_addr_datav(dns, link->network->dns, link->network->n_dns);
84de38c5
TG
1049 if (r < 0)
1050 return r;
1051
00616955 1052 r = ordered_set_put_strdupv(ntp, link->network->ntp);
84de38c5
TG
1053 if (r < 0)
1054 return r;
1055
00616955 1056 r = ordered_set_put_strdupv(search_domains, link->network->search_domains);
3df9bec5
LP
1057 if (r < 0)
1058 return r;
1059
00616955 1060 r = ordered_set_put_strdupv(route_domains, link->network->route_domains);
84de38c5
TG
1061 if (r < 0)
1062 return r;
1063
1064 if (!link->dhcp_lease)
1065 continue;
1066
1067 /* Secondly, add the entries acquired via DHCP */
27cb34f5 1068 if (link->network->dhcp_use_dns) {
84de38c5
TG
1069 const struct in_addr *addresses;
1070
1071 r = sd_dhcp_lease_get_dns(link->dhcp_lease, &addresses);
1072 if (r > 0) {
5512a963 1073 r = ordered_set_put_in4_addrv(dns, addresses, r);
84de38c5
TG
1074 if (r < 0)
1075 return r;
1076 } else if (r < 0 && r != -ENODATA)
1077 return r;
1078 }
1079
27cb34f5 1080 if (link->network->dhcp_use_ntp) {
84de38c5
TG
1081 const struct in_addr *addresses;
1082
1083 r = sd_dhcp_lease_get_ntp(link->dhcp_lease, &addresses);
1084 if (r > 0) {
5512a963 1085 r = ordered_set_put_in4_addrv(ntp, addresses, r);
84de38c5
TG
1086 if (r < 0)
1087 return r;
1088 } else if (r < 0 && r != -ENODATA)
1089 return r;
1090 }
1091
b2a81c0b 1092 if (link->network->dhcp_use_domains != DHCP_USE_DOMAINS_NO) {
84de38c5 1093 const char *domainname;
b85bc551 1094 char **domains = NULL;
84de38c5 1095
b85bc551 1096 OrderedSet *target_domains = (link->network->dhcp_use_domains == DHCP_USE_DOMAINS_YES) ? search_domains : route_domains;
84de38c5
TG
1097 r = sd_dhcp_lease_get_domainname(link->dhcp_lease, &domainname);
1098 if (r >= 0) {
b85bc551
DW
1099 r = ordered_set_put_strdup(target_domains, domainname);
1100 if (r < 0)
1101 return r;
1102 } else if (r != -ENODATA)
1103 return r;
b2a81c0b 1104
b85bc551
DW
1105 r = sd_dhcp_lease_get_search_domains(link->dhcp_lease, &domains);
1106 if (r >= 0) {
1107 r = ordered_set_put_strdupv(target_domains, domains);
84de38c5
TG
1108 if (r < 0)
1109 return r;
1110 } else if (r != -ENODATA)
1111 return r;
1112 }
1113 }
1114
1115 operstate_str = link_operstate_to_string(operstate);
1116 assert(operstate_str);
1117
1118 r = fopen_temporary(m->state_file, &f, &temp_path);
1119 if (r < 0)
1120 return r;
1121
5512a963 1122 (void) fchmod(fileno(f), 0644);
84de38c5
TG
1123
1124 fprintf(f,
1125 "# This is private data. Do not parse.\n"
1126 "OPER_STATE=%s\n", operstate_str);
1127
1128 print_string_set(f, "DNS=", dns);
1129 print_string_set(f, "NTP=", ntp);
3df9bec5
LP
1130 print_string_set(f, "DOMAINS=", search_domains);
1131 print_string_set(f, "ROUTE_DOMAINS=", route_domains);
84de38c5 1132
bce67bbe
SS
1133 SET_FOREACH(rule, m->rules, i) {
1134 _cleanup_free_ char *from_str = NULL, *to_str = NULL;
1135 fputs("RULE=", f);
1136
1137 if (!in_addr_is_null(rule->family, &rule->from)) {
1138 r = in_addr_to_string(rule->family, &rule->from, &from_str);
1139 if (r < 0)
1140 goto fail;
1141 }
1142
1143 if (!in_addr_is_null(rule->family, &rule->to)) {
1144 r = in_addr_to_string(rule->family, &rule->to, &to_str);
1145 if (r < 0)
1146 goto fail;
1147 }
1148
ecc3f340
ZJS
1149 fprintf(f, "from=%s%s/%hhu to=%s%s/%hhu tos=%hhu fwmark=%"PRIu32"/%"PRIu32" table=%"PRIu32,
1150 space ? " " : "", from_str, rule->from_prefixlen,
1151 space ? " " : "", to_str, rule->to_prefixlen,
1152 rule->tos,
1153 rule->fwmark, rule->fwmask,
1154 rule->table);
bce67bbe
SS
1155
1156 fputc('\n', f);
1157 }
1158
84de38c5
TG
1159 r = fflush_and_check(f);
1160 if (r < 0)
1161 goto fail;
1162
1163 if (rename(temp_path, m->state_file) < 0) {
1164 r = -errno;
1165 goto fail;
1166 }
1167
1168 if (m->operational_state != operstate) {
1169 m->operational_state = operstate;
1170 r = manager_send_changed(m, "OperationalState", NULL);
1171 if (r < 0)
1172 log_error_errno(r, "Could not emit changed OperationalState: %m");
1173 }
1174
1175 m->dirty = false;
1176
1177 return 0;
1178
1179fail:
1180 (void) unlink(m->state_file);
1181 (void) unlink(temp_path);
1182
1183 return log_error_errno(r, "Failed to save network state to %s: %m", m->state_file);
1184}
1185
1186static int manager_dirty_handler(sd_event_source *s, void *userdata) {
1187 Manager *m = userdata;
1188 Link *link;
1189 Iterator i;
1190 int r;
1191
1192 assert(m);
1193
1194 if (m->dirty)
1195 manager_save(m);
1196
1197 SET_FOREACH(link, m->dirty_links, i) {
1198 r = link_save(link);
1199 if (r >= 0)
1200 link_clean(link);
1201 }
1202
1203 return 1;
1204}
1205
b76d99d9 1206int manager_new(Manager **ret, sd_event *event) {
5fae368b 1207 _cleanup_manager_free_ Manager *m = NULL;
45af44d4 1208 int r;
f579559b 1209
5fae368b
TG
1210 m = new0(Manager, 1);
1211 if (!m)
1212 return -ENOMEM;
45af44d4 1213
5fae368b
TG
1214 m->state_file = strdup("/run/systemd/netif/state");
1215 if (!m->state_file)
1216 return -ENOMEM;
1217
b76d99d9 1218 m->event = sd_event_ref(event);
5fae368b 1219
84de38c5
TG
1220 r = sd_event_add_post(m->event, NULL, manager_dirty_handler, m);
1221 if (r < 0)
1222 return r;
1223
5fae368b 1224 r = manager_connect_rtnl(m);
45af44d4
TG
1225 if (r < 0)
1226 return r;
1227
5fae368b
TG
1228 r = manager_connect_udev(m);
1229 if (r < 0)
1230 return r;
45af44d4 1231
5fae368b
TG
1232 m->netdevs = hashmap_new(&string_hash_ops);
1233 if (!m->netdevs)
1234 return -ENOMEM;
f579559b 1235
5fae368b 1236 LIST_HEAD_INIT(m->networks);
f579559b 1237
5fae368b
TG
1238 r = setup_default_address_pool(m);
1239 if (r < 0)
1240 return r;
f579559b 1241
8341a5c3 1242 m->duid.type = DUID_TYPE_EN;
413708d1 1243
bce67bbe
SS
1244 (void) routing_policy_rule_load(m);
1245
5fae368b
TG
1246 *ret = m;
1247 m = NULL;
f579559b 1248
f579559b
TG
1249 return 0;
1250}
1251
5fae368b 1252void manager_free(Manager *m) {
bce67bbe 1253 RoutingPolicyRule *rule;
5fae368b
TG
1254 Network *network;
1255 NetDev *netdev;
1256 Link *link;
1257 AddressPool *pool;
f579559b 1258
5fae368b
TG
1259 if (!m)
1260 return;
505f8da7 1261
5fae368b 1262 free(m->state_file);
505f8da7 1263
bce67bbe
SS
1264 while ((network = m->networks))
1265 network_free(network);
1266
5fae368b
TG
1267 while ((link = hashmap_first(m->links)))
1268 link_unref(link);
1269 hashmap_free(m->links);
f579559b 1270
dbffab87
TG
1271 hashmap_free(m->networks_by_name);
1272
5fae368b
TG
1273 while ((netdev = hashmap_first(m->netdevs)))
1274 netdev_unref(netdev);
1275 hashmap_free(m->netdevs);
1276
1277 while ((pool = m->address_pools))
1278 address_pool_free(pool);
1279
bce67bbe
SS
1280 set_free(m->rules);
1281 set_free(m->rules_foreign);
1282
1283 while ((rule = set_steal_first(m->rules_saved)))
1284 free(rule);
1285
1286 set_free(m->rules_saved);
1287
1c4baffc 1288 sd_netlink_unref(m->rtnl);
2f5b4a77 1289 sd_event_unref(m->event);
5fae368b 1290
7d20d375
TG
1291 sd_event_source_unref(m->udev_event_source);
1292 udev_monitor_unref(m->udev_monitor);
1293 udev_unref(m->udev);
1294
1295 sd_bus_unref(m->bus);
1296 sd_bus_slot_unref(m->prepare_for_sleep_slot);
1297 sd_event_source_unref(m->bus_retry_event_source);
1298
7901cea1
MP
1299 free(m->dynamic_timezone);
1300 free(m->dynamic_hostname);
1301
5fae368b
TG
1302 free(m);
1303}
1304
b76d99d9 1305int manager_start(Manager *m) {
84de38c5
TG
1306 Link *link;
1307 Iterator i;
1308
a97dcc12
TG
1309 assert(m);
1310
84de38c5
TG
1311 /* The dirty handler will deal with future serialization, but the first one
1312 must be done explicitly. */
1313
1314 manager_save(m);
1315
1316 HASHMAP_FOREACH(link, m->links, i)
1317 link_save(link);
1318
b76d99d9 1319 return 0;
a97dcc12
TG
1320}
1321
5fae368b
TG
1322int manager_load_config(Manager *m) {
1323 int r;
1324
1325 /* update timestamp */
1326 paths_check_timestamp(network_dirs, &m->network_dirs_ts_usec, true);
1327
1328 r = netdev_load(m);
f579559b
TG
1329 if (r < 0)
1330 return r;
1331
5fae368b 1332 r = network_load(m);
9021bb9f
TG
1333 if (r < 0)
1334 return r;
1335
f579559b
TG
1336 return 0;
1337}
f882c247 1338
5fae368b
TG
1339bool manager_should_reload(Manager *m) {
1340 return paths_check_timestamp(network_dirs, &m->network_dirs_ts_usec, false);
1341}
1342
1343int manager_rtnl_enumerate_links(Manager *m) {
4afd3348 1344 _cleanup_(sd_netlink_message_unrefp) sd_netlink_message *req = NULL, *reply = NULL;
1c4baffc 1345 sd_netlink_message *link;
f882c247
TG
1346 int r;
1347
5da8149f 1348 assert(m);
5fae368b 1349 assert(m->rtnl);
5da8149f 1350
5fae368b 1351 r = sd_rtnl_message_new_link(m->rtnl, &req, RTM_GETLINK, 0);
f882c247
TG
1352 if (r < 0)
1353 return r;
1354
1c4baffc 1355 r = sd_netlink_message_request_dump(req, true);
dd3efc09
TG
1356 if (r < 0)
1357 return r;
1358
1c4baffc 1359 r = sd_netlink_call(m->rtnl, req, 0, &reply);
f2236469
TG
1360 if (r < 0)
1361 return r;
1362
1c4baffc 1363 for (link = reply; link; link = sd_netlink_message_next(link)) {
5fae368b 1364 int k;
2e9f08ea 1365
6a24f148
TG
1366 m->enumerating = true;
1367
5fae368b
TG
1368 k = manager_rtnl_process_link(m->rtnl, link, m);
1369 if (k < 0)
1370 r = k;
6a24f148
TG
1371
1372 m->enumerating = false;
5fae368b 1373 }
2e9f08ea 1374
5fae368b 1375 return r;
f882c247 1376}
3bef724f 1377
5fae368b 1378int manager_rtnl_enumerate_addresses(Manager *m) {
4afd3348 1379 _cleanup_(sd_netlink_message_unrefp) sd_netlink_message *req = NULL, *reply = NULL;
1c4baffc 1380 sd_netlink_message *addr;
1346b1f0
TG
1381 int r;
1382
5fae368b
TG
1383 assert(m);
1384 assert(m->rtnl);
bcbca829 1385
5fae368b
TG
1386 r = sd_rtnl_message_new_addr(m->rtnl, &req, RTM_GETADDR, 0, 0);
1387 if (r < 0)
1388 return r;
bcbca829 1389
1c4baffc 1390 r = sd_netlink_message_request_dump(req, true);
1346b1f0
TG
1391 if (r < 0)
1392 return r;
1393
1c4baffc 1394 r = sd_netlink_call(m->rtnl, req, 0, &reply);
5fae368b
TG
1395 if (r < 0)
1396 return r;
1397
1c4baffc 1398 for (addr = reply; addr; addr = sd_netlink_message_next(addr)) {
5fae368b
TG
1399 int k;
1400
6a24f148
TG
1401 m->enumerating = true;
1402
200a0868 1403 k = manager_rtnl_process_address(m->rtnl, addr, m);
5fae368b
TG
1404 if (k < 0)
1405 r = k;
6a24f148
TG
1406
1407 m->enumerating = false;
5fae368b
TG
1408 }
1409
1410 return r;
1346b1f0
TG
1411}
1412
1c8e710c 1413int manager_rtnl_enumerate_routes(Manager *m) {
4afd3348 1414 _cleanup_(sd_netlink_message_unrefp) sd_netlink_message *req = NULL, *reply = NULL;
1c8e710c
TG
1415 sd_netlink_message *route;
1416 int r;
1417
1418 assert(m);
1419 assert(m->rtnl);
1420
1421 r = sd_rtnl_message_new_route(m->rtnl, &req, RTM_GETROUTE, 0, 0);
1422 if (r < 0)
1423 return r;
1424
1425 r = sd_netlink_message_request_dump(req, true);
1426 if (r < 0)
1427 return r;
1428
1429 r = sd_netlink_call(m->rtnl, req, 0, &reply);
1430 if (r < 0)
1431 return r;
1432
1433 for (route = reply; route; route = sd_netlink_message_next(route)) {
1434 int k;
1435
1436 m->enumerating = true;
1437
1438 k = manager_rtnl_process_route(m->rtnl, route, m);
1439 if (k < 0)
1440 r = k;
1441
1442 m->enumerating = false;
1443 }
1444
1445 return r;
1446}
1447
bce67bbe
SS
1448int manager_rtnl_enumerate_rules(Manager *m) {
1449 _cleanup_(sd_netlink_message_unrefp) sd_netlink_message *req = NULL, *reply = NULL;
1450 sd_netlink_message *rule;
1451 int r;
1452
1453 assert(m);
1454 assert(m->rtnl);
1455
1456 r = sd_rtnl_message_new_routing_policy_rule(m->rtnl, &req, RTM_GETRULE, 0);
1457 if (r < 0)
1458 return r;
1459
1460 r = sd_netlink_message_request_dump(req, true);
1461 if (r < 0)
1462 return r;
1463
1464 r = sd_netlink_call(m->rtnl, req, 0, &reply);
6acbbdd4
SS
1465 if (r < 0) {
1466 if (r == -EOPNOTSUPP) {
1467 log_debug("FIB Rules are not supported by the kernel. Ignoring.");
1468 return 0;
1469 }
1470
bce67bbe 1471 return r;
6acbbdd4 1472 }
bce67bbe
SS
1473
1474 for (rule = reply; rule; rule = sd_netlink_message_next(rule)) {
1475 int k;
1476
1477 m->enumerating = true;
1478
1479 k = manager_rtnl_process_rule(m->rtnl, rule, m);
1480 if (k < 0)
1481 r = k;
1482
1483 m->enumerating = false;
1484 }
1485
1486 return r;
1487}
1488
0dd25fb9 1489int manager_address_pool_acquire(Manager *m, int family, unsigned prefixlen, union in_addr_union *found) {
11bf3cce
LP
1490 AddressPool *p;
1491 int r;
1492
1493 assert(m);
1494 assert(prefixlen > 0);
1495 assert(found);
1496
1497 LIST_FOREACH(address_pools, p, m->address_pools) {
1498 if (p->family != family)
1499 continue;
1500
1501 r = address_pool_acquire(p, prefixlen, found);
1502 if (r != 0)
1503 return r;
1504 }
1505
1506 return 0;
1507}
4f5f911e
LP
1508
1509Link* manager_find_uplink(Manager *m, Link *exclude) {
1510 _cleanup_free_ struct local_address *gateways = NULL;
1511 int n, i;
1512
1513 assert(m);
1514
1515 /* Looks for a suitable "uplink", via black magic: an
1516 * interface that is up and where the default route with the
1517 * highest priority points to. */
1518
1519 n = local_gateways(m->rtnl, 0, AF_UNSPEC, &gateways);
1520 if (n < 0) {
1521 log_warning_errno(n, "Failed to determine list of default gateways: %m");
1522 return NULL;
1523 }
1524
1525 for (i = 0; i < n; i++) {
1526 Link *link;
1527
1528 link = hashmap_get(m->links, INT_TO_PTR(gateways[i].ifindex));
1529 if (!link) {
c2c940bd 1530 log_debug("Weird, found a gateway for a link we don't know. Ignoring.");
4f5f911e
LP
1531 continue;
1532 }
1533
1534 if (link == exclude)
1535 continue;
1536
1537 if (link->operstate < LINK_OPERSTATE_ROUTABLE)
1538 continue;
1539
1540 return link;
1541 }
1542
1543 return NULL;
1544}
84de38c5
TG
1545
1546void manager_dirty(Manager *manager) {
1547 assert(manager);
1548
1549 /* the serialized state in /run is no longer up-to-date */
1550 manager->dirty = true;
1551}
59eb33e0
MP
1552
1553static int set_hostname_handler(sd_bus_message *m, void *userdata, sd_bus_error *ret_error) {
1554 Manager *manager = userdata;
1555 const sd_bus_error *e;
1556
1557 assert(m);
1558 assert(manager);
1559
1560 e = sd_bus_message_get_error(m);
1561 if (e)
1562 log_warning_errno(sd_bus_error_get_errno(e), "Could not set hostname: %s", e->message);
1563
1564 return 1;
1565}
1566
1567int manager_set_hostname(Manager *m, const char *hostname) {
1568 int r;
1569
1570 log_debug("Setting transient hostname: '%s'", strna(hostname));
7901cea1
MP
1571 if (free_and_strdup(&m->dynamic_hostname, hostname) < 0)
1572 return log_oom();
59eb33e0
MP
1573
1574 if (!m->bus) {
1575 /* TODO: replace by assert when we can rely on kdbus */
1576 log_info("Not connected to system bus, ignoring transient hostname.");
1577 return 0;
1578 }
1579
1580 r = sd_bus_call_method_async(
1581 m->bus,
1582 NULL,
1583 "org.freedesktop.hostname1",
1584 "/org/freedesktop/hostname1",
1585 "org.freedesktop.hostname1",
1586 "SetHostname",
1587 set_hostname_handler,
1588 m,
1589 "sb",
1590 hostname,
1591 false);
1592
1593 if (r < 0)
1594 return log_error_errno(r, "Could not set transient hostname: %m");
1595
1596 return 0;
1597}
1598
1599static int set_timezone_handler(sd_bus_message *m, void *userdata, sd_bus_error *ret_error) {
1600 Manager *manager = userdata;
1601 const sd_bus_error *e;
1602
1603 assert(m);
1604 assert(manager);
1605
1606 e = sd_bus_message_get_error(m);
1607 if (e)
1608 log_warning_errno(sd_bus_error_get_errno(e), "Could not set timezone: %s", e->message);
1609
1610 return 1;
1611}
1612
1613int manager_set_timezone(Manager *m, const char *tz) {
1614 int r;
1615
1616 assert(m);
1617 assert(tz);
1618
1619 log_debug("Setting system timezone: '%s'", tz);
7901cea1
MP
1620 if (free_and_strdup(&m->dynamic_timezone, tz) < 0)
1621 return log_oom();
59eb33e0
MP
1622
1623 if (!m->bus) {
1624 log_info("Not connected to system bus, ignoring timezone.");
1625 return 0;
1626 }
1627
1628 r = sd_bus_call_method_async(
1629 m->bus,
1630 NULL,
1631 "org.freedesktop.timedate1",
1632 "/org/freedesktop/timedate1",
1633 "org.freedesktop.timedate1",
1634 "SetTimezone",
1635 set_timezone_handler,
1636 m,
1637 "sb",
1638 tz,
1639 false);
1640 if (r < 0)
1641 return log_error_errno(r, "Could not set timezone: %m");
1642
1643 return 0;
1644}