chiark / gitweb /
Remove src/modules-load
[elogind.git] / src / network / networkd-manager.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 <sys/socket.h>
23 #include <linux/if.h>
24
25 #include "conf-parser.h"
26 #include "path-util.h"
27 #include "networkd.h"
28 #include "networkd-netdev.h"
29 #include "networkd-link.h"
30 #include "libudev-private.h"
31 #include "udev-util.h"
32 #include "rtnl-util.h"
33 #include "bus-util.h"
34 #include "def.h"
35 #include "virt.h"
36
37 #include "sd-rtnl.h"
38 #include "sd-daemon.h"
39
40 /* use 8 MB for receive socket kernel queue. */
41 #define RCVBUF_SIZE    (8*1024*1024)
42
43 const char* const network_dirs[] = {
44         "/etc/systemd/network",
45         "/run/systemd/network",
46         "/usr/lib/systemd/network",
47 #ifdef HAVE_SPLIT_USR
48         "/lib/systemd/network",
49 #endif
50         NULL};
51
52 static int setup_default_address_pool(Manager *m) {
53         AddressPool *p;
54         int r;
55
56         assert(m);
57
58         /* Add in the well-known private address ranges. */
59
60         r = address_pool_new_from_string(m, &p, AF_INET6, "fc00::", 7);
61         if (r < 0)
62                 return r;
63
64         r = address_pool_new_from_string(m, &p, AF_INET, "192.168.0.0", 16);
65         if (r < 0)
66                 return r;
67
68         r = address_pool_new_from_string(m, &p, AF_INET, "172.16.0.0", 12);
69         if (r < 0)
70                 return r;
71
72         r = address_pool_new_from_string(m, &p, AF_INET, "10.0.0.0", 8);
73         if (r < 0)
74                 return r;
75
76         return 0;
77 }
78
79 static int on_bus_retry(sd_event_source *s, usec_t usec, void *userdata) {
80         Manager *m = userdata;
81
82         assert(s);
83         assert(m);
84
85         m->bus_retry_event_source = sd_event_source_unref(m->bus_retry_event_source);
86
87         manager_connect_bus(m);
88
89         return 0;
90 }
91
92 static int manager_reset_all(Manager *m) {
93         Link *link;
94         Iterator i;
95         int r;
96
97         assert(m);
98
99         HASHMAP_FOREACH(link, m->links, i) {
100                 r = link_carrier_reset(link);
101                 if (r < 0)
102                         log_link_warning_errno(link, r, "could not reset carrier: %m");
103         }
104
105         return 0;
106 }
107
108 static int match_prepare_for_sleep(sd_bus *bus, sd_bus_message *message, void *userdata, sd_bus_error *ret_error) {
109         Manager *m = userdata;
110         int b, r;
111
112         assert(bus);
113         assert(bus);
114
115         r = sd_bus_message_read(message, "b", &b);
116         if (r < 0) {
117                 log_debug_errno(r, "Failed to parse PrepareForSleep signal: %m");
118                 return 0;
119         }
120
121         if (b)
122                 return 0;
123
124         log_debug("Coming back from suspend, resetting all connections...");
125
126         manager_reset_all(m);
127
128         return 0;
129 }
130
131 int manager_connect_bus(Manager *m) {
132         int r;
133
134         assert(m);
135
136         r = sd_bus_default_system(&m->bus);
137         if (r == -ENOENT) {
138                 /* We failed to connect? Yuck, we must be in early
139                  * boot. Let's try in 5s again. As soon as we have
140                  * kdbus we can stop doing this... */
141
142                 log_debug_errno(r, "Failed to connect to bus, trying again in 5s: %m");
143
144                 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);
145                 if (r < 0)
146                         return log_error_errno(r, "Failed to install bus reconnect time event: %m");
147
148                 return 0;
149         } if (r < 0)
150                 return r;
151
152         r = sd_bus_add_match(m->bus, &m->prepare_for_sleep_slot,
153                              "type='signal',"
154                              "sender='org.freedesktop.login1',"
155                              "interface='org.freedesktop.login1.Manager',"
156                              "member='PrepareForSleep',"
157                              "path='/org/freedesktop/login1'",
158                              match_prepare_for_sleep,
159                              m);
160         if (r < 0)
161                 return log_error_errno(r, "Failed to add match for PrepareForSleep: %m");
162
163         r = sd_bus_add_object_vtable(m->bus, NULL, "/org/freedesktop/network1", "org.freedesktop.network1.Manager", manager_vtable, m);
164         if (r < 0)
165                 return log_error_errno(r, "Failed to add manager object vtable: %m");
166
167         r = sd_bus_add_fallback_vtable(m->bus, NULL, "/org/freedesktop/network1/link", "org.freedesktop.network1.Link", link_vtable, link_object_find, m);
168         if (r < 0)
169                return log_error_errno(r, "Failed to add link object vtable: %m");
170
171         r = sd_bus_add_node_enumerator(m->bus, NULL, "/org/freedesktop/network1/link", link_node_enumerator, m);
172         if (r < 0)
173                 return log_error_errno(r, "Failed to add link enumerator: %m");
174
175         r = sd_bus_add_fallback_vtable(m->bus, NULL, "/org/freedesktop/network1/network", "org.freedesktop.network1.Network", network_vtable, network_object_find, m);
176         if (r < 0)
177                return log_error_errno(r, "Failed to add network object vtable: %m");
178
179         r = sd_bus_add_node_enumerator(m->bus, NULL, "/org/freedesktop/network1/network", network_node_enumerator, m);
180         if (r < 0)
181                 return log_error_errno(r, "Failed to add network enumerator: %m");
182
183         r = sd_bus_request_name(m->bus, "org.freedesktop.network1", 0);
184         if (r < 0)
185                 return log_error_errno(r, "Failed to register name: %m");
186
187         r = sd_bus_attach_event(m->bus, m->event, 0);
188         if (r < 0)
189                 return log_error_errno(r, "Failed to attach bus to event loop: %m");
190
191         return 0;
192 }
193
194 static int manager_udev_process_link(Manager *m, struct udev_device *device) {
195         Link *link = NULL;
196         int r, ifindex;
197
198         assert(m);
199         assert(device);
200
201         if (!streq_ptr(udev_device_get_action(device), "add"))
202                 return 0;
203
204         ifindex = udev_device_get_ifindex(device);
205         if (ifindex <= 0) {
206                 log_debug("ignoring udev ADD event for device with invalid ifindex");
207                 return 0;
208         }
209
210         r = link_get(m, ifindex, &link);
211         if (r == -ENODEV)
212                 return 0;
213         else if (r < 0)
214                 return r;
215
216         r = link_initialized(link, device);
217         if (r < 0)
218                 return r;
219
220         return 0;
221 }
222
223 static int manager_dispatch_link_udev(sd_event_source *source, int fd, uint32_t revents, void *userdata) {
224         Manager *m = userdata;
225         struct udev_monitor *monitor = m->udev_monitor;
226         _cleanup_udev_device_unref_ struct udev_device *device = NULL;
227
228         device = udev_monitor_receive_device(monitor);
229         if (!device)
230                 return -ENOMEM;
231
232         manager_udev_process_link(m, device);
233         return 0;
234 }
235
236 static int manager_connect_udev(Manager *m) {
237         int r;
238
239         /* udev does not initialize devices inside containers,
240          * so we rely on them being already initialized before
241          * entering the container */
242         if (detect_container(NULL) > 0)
243                 return 0;
244
245         m->udev = udev_new();
246         if (!m->udev)
247                 return -ENOMEM;
248
249         m->udev_monitor = udev_monitor_new_from_netlink(m->udev, "udev");
250         if (!m->udev_monitor)
251                 return -ENOMEM;
252
253         r = udev_monitor_filter_add_match_subsystem_devtype(m->udev_monitor, "net", NULL);
254         if (r < 0)
255                 return log_error_errno(r, "Could not add udev monitor filter: %m");
256
257         r = udev_monitor_enable_receiving(m->udev_monitor);
258         if (r < 0) {
259                 log_error("Could not enable udev monitor");
260                 return r;
261         }
262
263         r = sd_event_add_io(m->event,
264                         &m->udev_event_source,
265                         udev_monitor_get_fd(m->udev_monitor),
266                         EPOLLIN, manager_dispatch_link_udev,
267                         m);
268         if (r < 0)
269                 return r;
270
271         r = sd_event_source_set_description(m->udev_event_source, "networkd-udev");
272         if (r < 0)
273                 return r;
274
275         return 0;
276 }
277
278 static int manager_rtnl_process_link(sd_rtnl *rtnl, sd_rtnl_message *message, void *userdata) {
279         Manager *m = userdata;
280         Link *link = NULL;
281         NetDev *netdev = NULL;
282         uint16_t type;
283         const char *name;
284         int r, ifindex;
285
286         assert(rtnl);
287         assert(message);
288         assert(m);
289
290         if (sd_rtnl_message_is_error(message)) {
291                 r = sd_rtnl_message_get_errno(message);
292                 if (r < 0)
293                         log_warning_errno(r, "rtnl: could not receive link: %m");
294
295                 return 0;
296         }
297
298         r = sd_rtnl_message_get_type(message, &type);
299         if (r < 0) {
300                 log_warning_errno(r, "rtnl: could not get message type: %m");
301                 return 0;
302         } else if (type != RTM_NEWLINK && type != RTM_DELLINK) {
303                 log_warning("rtnl: received unexpected message type when processing link");
304                 return 0;
305         }
306
307         r = sd_rtnl_message_link_get_ifindex(message, &ifindex);
308         if (r < 0) {
309                 log_warning_errno(r, "rtnl: could not get ifindex from link: %m");
310                 return 0;
311         } else if (ifindex <= 0) {
312                 log_warning("rtnl: received link message with invalid ifindex: %d", ifindex);
313                 return 0;
314         } else
315                 link_get(m, ifindex, &link);
316
317         r = sd_rtnl_message_read_string(message, IFLA_IFNAME, &name);
318         if (r < 0) {
319                 log_warning_errno(r, "rtnl: received link message without ifname: %m");
320                 return 0;
321         } else
322                 netdev_get(m, name, &netdev);
323
324         switch (type) {
325         case RTM_NEWLINK:
326                 if (!link) {
327                         /* link is new, so add it */
328                         r = link_add(m, message, &link);
329                         if (r < 0) {
330                                 log_warning_errno(r, "could not add new link: %m");
331                                 return 0;
332                         }
333                 }
334
335                 if (netdev) {
336                         /* netdev exists, so make sure the ifindex matches */
337                         r = netdev_set_ifindex(netdev, message);
338                         if (r < 0) {
339                                 log_warning_errno(r, "could not set ifindex on netdev: %m");
340                                 return 0;
341                         }
342                 }
343
344                 r = link_update(link, message);
345                 if (r < 0)
346                         return 0;
347
348                 break;
349
350         case RTM_DELLINK:
351                 link_drop(link);
352                 netdev_drop(netdev);
353
354                 break;
355
356         default:
357                 assert_not_reached("Received invalid RTNL message type.");
358         }
359
360         return 1;
361 }
362
363 static int systemd_netlink_fd(void) {
364         int n, fd, rtnl_fd = -EINVAL;
365
366         n = sd_listen_fds(true);
367         if (n <= 0)
368                 return -EINVAL;
369
370         for (fd = SD_LISTEN_FDS_START; fd < SD_LISTEN_FDS_START + n; fd ++) {
371                 if (sd_is_socket(fd, AF_NETLINK, SOCK_RAW, -1) > 0) {
372                         if (rtnl_fd >= 0)
373                                 return -EINVAL;
374
375                         rtnl_fd = fd;
376                 }
377         }
378
379         return rtnl_fd;
380 }
381
382 static int manager_connect_rtnl(Manager *m) {
383         int fd, r;
384
385         assert(m);
386
387         fd = systemd_netlink_fd();
388         if (fd < 0)
389                 r = sd_rtnl_open(&m->rtnl, 3, RTNLGRP_LINK, RTNLGRP_IPV4_IFADDR, RTNLGRP_IPV6_IFADDR);
390         else
391                 r = sd_rtnl_open_fd(&m->rtnl, fd, 0);
392         if (r < 0)
393                 return r;
394
395         r = sd_rtnl_inc_rcvbuf(m->rtnl, RCVBUF_SIZE);
396         if (r < 0)
397                 return r;
398
399         r = sd_rtnl_attach_event(m->rtnl, m->event, 0);
400         if (r < 0)
401                 return r;
402
403         r = sd_rtnl_add_match(m->rtnl, RTM_NEWLINK, &manager_rtnl_process_link, m);
404         if (r < 0)
405                 return r;
406
407         r = sd_rtnl_add_match(m->rtnl, RTM_DELLINK, &manager_rtnl_process_link, m);
408         if (r < 0)
409                 return r;
410
411         r = sd_rtnl_add_match(m->rtnl, RTM_NEWADDR, &link_rtnl_process_address, m);
412         if (r < 0)
413                 return r;
414
415         r = sd_rtnl_add_match(m->rtnl, RTM_DELADDR, &link_rtnl_process_address, m);
416         if (r < 0)
417                 return r;
418
419         return 0;
420 }
421
422 int manager_new(Manager **ret) {
423         _cleanup_manager_free_ Manager *m = NULL;
424         int r;
425
426         m = new0(Manager, 1);
427         if (!m)
428                 return -ENOMEM;
429
430         m->state_file = strdup("/run/systemd/netif/state");
431         if (!m->state_file)
432                 return -ENOMEM;
433
434         r = sd_event_default(&m->event);
435         if (r < 0)
436                 return r;
437
438         sd_event_set_watchdog(m->event, true);
439
440         sd_event_add_signal(m->event, NULL, SIGTERM, NULL, NULL);
441         sd_event_add_signal(m->event, NULL, SIGINT, NULL, NULL);
442
443         r = manager_connect_rtnl(m);
444         if (r < 0)
445                 return r;
446
447         r = manager_connect_udev(m);
448         if (r < 0)
449                 return r;
450
451         m->netdevs = hashmap_new(&string_hash_ops);
452         if (!m->netdevs)
453                 return -ENOMEM;
454
455         LIST_HEAD_INIT(m->networks);
456
457         r = setup_default_address_pool(m);
458         if (r < 0)
459                 return r;
460
461         *ret = m;
462         m = NULL;
463
464         return 0;
465 }
466
467 void manager_free(Manager *m) {
468         Network *network;
469         NetDev *netdev;
470         Link *link;
471         AddressPool *pool;
472
473         if (!m)
474                 return;
475
476         free(m->state_file);
477
478         udev_monitor_unref(m->udev_monitor);
479         udev_unref(m->udev);
480         sd_bus_unref(m->bus);
481         sd_bus_slot_unref(m->prepare_for_sleep_slot);
482         sd_event_source_unref(m->udev_event_source);
483         sd_event_source_unref(m->bus_retry_event_source);
484         sd_event_unref(m->event);
485
486         while ((link = hashmap_first(m->links)))
487                 link_unref(link);
488         hashmap_free(m->links);
489
490         while ((network = m->networks))
491                 network_free(network);
492
493         hashmap_free(m->networks_by_name);
494
495         while ((netdev = hashmap_first(m->netdevs)))
496                 netdev_unref(netdev);
497         hashmap_free(m->netdevs);
498
499         while ((pool = m->address_pools))
500                 address_pool_free(pool);
501
502         sd_rtnl_unref(m->rtnl);
503
504         free(m);
505 }
506
507 static bool manager_check_idle(void *userdata) {
508         Manager *m = userdata;
509         Link *link;
510         Iterator i;
511
512         assert(m);
513
514         HASHMAP_FOREACH(link, m->links, i) {
515                 /* we are not woken on udev activity, so let's just wait for the
516                  * pending udev event */
517                 if (link->state == LINK_STATE_PENDING)
518                         return false;
519
520                 if (!link->network)
521                         continue;
522
523                 /* we are not woken on netork activity, so let's stay around */
524                 if (link_lldp_enabled(link) ||
525                     link_ipv4ll_enabled(link) ||
526                     link_dhcp4_server_enabled(link) ||
527                     link_dhcp4_enabled(link) ||
528                     link_dhcp6_enabled(link))
529                         return false;
530         }
531
532         return true;
533 }
534
535 int manager_run(Manager *m) {
536         assert(m);
537
538         if (m->bus)
539                 return bus_event_loop_with_idle(
540                                 m->event,
541                                 m->bus,
542                                 "org.freedesktop.network1",
543                                 DEFAULT_EXIT_USEC,
544                                 manager_check_idle,
545                                 m);
546         else
547                 /* failed to connect to the bus, so we lose exit-on-idle logic,
548                    this should not happen except if dbus is not around at all */
549                 return sd_event_loop(m->event);
550 }
551
552 int manager_load_config(Manager *m) {
553         int r;
554
555         /* update timestamp */
556         paths_check_timestamp(network_dirs, &m->network_dirs_ts_usec, true);
557
558         r = netdev_load(m);
559         if (r < 0)
560                 return r;
561
562         r = network_load(m);
563         if (r < 0)
564                 return r;
565
566         return 0;
567 }
568
569 bool manager_should_reload(Manager *m) {
570         return paths_check_timestamp(network_dirs, &m->network_dirs_ts_usec, false);
571 }
572
573 int manager_rtnl_enumerate_links(Manager *m) {
574         _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL, *reply = NULL;
575         sd_rtnl_message *link;
576         int r;
577
578         assert(m);
579         assert(m->rtnl);
580
581         r = sd_rtnl_message_new_link(m->rtnl, &req, RTM_GETLINK, 0);
582         if (r < 0)
583                 return r;
584
585         r = sd_rtnl_message_request_dump(req, true);
586         if (r < 0)
587                 return r;
588
589         r = sd_rtnl_call(m->rtnl, req, 0, &reply);
590         if (r < 0)
591                 return r;
592
593         for (link = reply; link; link = sd_rtnl_message_next(link)) {
594                 int k;
595
596                 m->enumerating = true;
597
598                 k = manager_rtnl_process_link(m->rtnl, link, m);
599                 if (k < 0)
600                         r = k;
601
602                 m->enumerating = false;
603         }
604
605         return r;
606 }
607
608 int manager_rtnl_enumerate_addresses(Manager *m) {
609         _cleanup_rtnl_message_unref_ sd_rtnl_message *req = NULL, *reply = NULL;
610         sd_rtnl_message *addr;
611         int r;
612
613         assert(m);
614         assert(m->rtnl);
615
616         r = sd_rtnl_message_new_addr(m->rtnl, &req, RTM_GETADDR, 0, 0);
617         if (r < 0)
618                 return r;
619
620         r = sd_rtnl_message_request_dump(req, true);
621         if (r < 0)
622                 return r;
623
624         r = sd_rtnl_call(m->rtnl, req, 0, &reply);
625         if (r < 0)
626                 return r;
627
628         for (addr = reply; addr; addr = sd_rtnl_message_next(addr)) {
629                 int k;
630
631                 m->enumerating = true;
632
633                 k = link_rtnl_process_address(m->rtnl, addr, m);
634                 if (k < 0)
635                         r = k;
636
637                 m->enumerating = false;
638         }
639
640         return r;
641 }
642
643 static int set_put_in_addr(Set *s, const struct in_addr *address) {
644         char *p;
645         int r;
646
647         assert(s);
648
649         r = in_addr_to_string(AF_INET, (const union in_addr_union*) address, &p);
650         if (r < 0)
651                 return r;
652
653         r = set_consume(s, p);
654         if (r == -EEXIST)
655                 return 0;
656
657         return r;
658 }
659
660 static int set_put_in_addrv(Set *s, const struct in_addr *addresses, int n) {
661         int r, i, c = 0;
662
663         assert(s);
664         assert(n <= 0 || addresses);
665
666         for (i = 0; i < n; i++) {
667                 r = set_put_in_addr(s, addresses+i);
668                 if (r < 0)
669                         return r;
670
671                 c += r;
672         }
673
674         return c;
675 }
676
677 static void print_string_set(FILE *f, const char *field, Set *s) {
678         bool space = false;
679         Iterator i;
680         char *p;
681
682         if (set_isempty(s))
683                 return;
684
685         fputs(field, f);
686
687         SET_FOREACH(p, s, i) {
688                 if (space)
689                         fputc(' ', f);
690                 fputs(p, f);
691                 space = true;
692         }
693         fputc('\n', f);
694 }
695
696 int manager_save(Manager *m) {
697         _cleanup_set_free_free_ Set *dns = NULL, *ntp = NULL, *domains = NULL;
698         Link *link;
699         Iterator i;
700         _cleanup_free_ char *temp_path = NULL;
701         _cleanup_fclose_ FILE *f = NULL;
702         LinkOperationalState operstate = LINK_OPERSTATE_OFF;
703         const char *operstate_str;
704         int r;
705
706         assert(m);
707         assert(m->state_file);
708
709         /* We add all NTP and DNS server to a set, to filter out duplicates */
710         dns = set_new(&string_hash_ops);
711         if (!dns)
712                 return -ENOMEM;
713
714         ntp = set_new(&string_hash_ops);
715         if (!ntp)
716                 return -ENOMEM;
717
718         domains = set_new(&string_hash_ops);
719         if (!domains)
720                 return -ENOMEM;
721
722         HASHMAP_FOREACH(link, m->links, i) {
723                 if (link->flags & IFF_LOOPBACK)
724                         continue;
725
726                 if (link->operstate > operstate)
727                         operstate = link->operstate;
728
729                 if (!link->network)
730                         continue;
731
732                 /* First add the static configured entries */
733                 r = set_put_strdupv(dns, link->network->dns);
734                 if (r < 0)
735                         return r;
736
737                 r = set_put_strdupv(ntp, link->network->ntp);
738                 if (r < 0)
739                         return r;
740
741                 r = set_put_strdupv(domains, link->network->domains);
742                 if (r < 0)
743                         return r;
744
745                 if (!link->dhcp_lease)
746                         continue;
747
748                 /* Secondly, add the entries acquired via DHCP */
749                 if (link->network->dhcp_dns) {
750                         const struct in_addr *addresses;
751
752                         r = sd_dhcp_lease_get_dns(link->dhcp_lease, &addresses);
753                         if (r > 0) {
754                                 r = set_put_in_addrv(dns, addresses, r);
755                                 if (r < 0)
756                                         return r;
757                         } else if (r < 0 && r != -ENOENT)
758                                 return r;
759                 }
760
761                 if (link->network->dhcp_ntp) {
762                         const struct in_addr *addresses;
763
764                         r = sd_dhcp_lease_get_ntp(link->dhcp_lease, &addresses);
765                         if (r > 0) {
766                                 r = set_put_in_addrv(ntp, addresses, r);
767                                 if (r < 0)
768                                         return r;
769                         } else if (r < 0 && r != -ENOENT)
770                                 return r;
771                 }
772
773                 if (link->network->dhcp_domains) {
774                         const char *domainname;
775
776                         r = sd_dhcp_lease_get_domainname(link->dhcp_lease, &domainname);
777                         if (r >= 0) {
778                                 r = set_put_strdup(domains, domainname);
779                                 if (r < 0)
780                                         return r;
781                         } else if (r != -ENOENT)
782                                 return r;
783                 }
784         }
785
786         operstate_str = link_operstate_to_string(operstate);
787         assert(operstate_str);
788
789         r = fopen_temporary(m->state_file, &f, &temp_path);
790         if (r < 0)
791                 return r;
792
793         fchmod(fileno(f), 0644);
794
795         fprintf(f,
796                 "# This is private data. Do not parse.\n"
797                 "OPER_STATE=%s\n", operstate_str);
798
799         print_string_set(f, "DNS=", dns);
800         print_string_set(f, "NTP=", ntp);
801         print_string_set(f, "DOMAINS=", domains);
802
803         r = fflush_and_check(f);
804         if (r < 0)
805                 goto fail;
806
807         if (rename(temp_path, m->state_file) < 0) {
808                 r = -errno;
809                 goto fail;
810         }
811
812         if (m->operational_state != operstate) {
813                 m->operational_state = operstate;
814                 r = manager_send_changed(m, "OperationalState", NULL);
815                 if (r < 0)
816                         log_error_errno(r, "Could not emit changed OperationalState: %m");
817         }
818
819         return 0;
820
821 fail:
822         log_error_errno(r, "Failed to save network state to %s: %m", m->state_file);
823         unlink(m->state_file);
824         unlink(temp_path);
825         return r;
826 }
827
828 int manager_address_pool_acquire(Manager *m, int family, unsigned prefixlen, union in_addr_union *found) {
829         AddressPool *p;
830         int r;
831
832         assert(m);
833         assert(prefixlen > 0);
834         assert(found);
835
836         LIST_FOREACH(address_pools, p, m->address_pools) {
837                 if (p->family != family)
838                         continue;
839
840                 r = address_pool_acquire(p, prefixlen, found);
841                 if (r != 0)
842                         return r;
843         }
844
845         return 0;
846 }
847
848 const char *address_family_boolean_to_string(AddressFamilyBoolean b) {
849         if (b == ADDRESS_FAMILY_YES ||
850             b == ADDRESS_FAMILY_NO)
851                 return yes_no(b == ADDRESS_FAMILY_YES);
852
853         if (b == ADDRESS_FAMILY_IPV4)
854                 return "ipv4";
855         if (b == ADDRESS_FAMILY_IPV6)
856                 return "ipv6";
857
858         return NULL;
859 }
860
861 AddressFamilyBoolean address_family_boolean_from_string(const char *s) {
862         int r;
863
864         /* Make this a true superset of a boolean */
865
866         r = parse_boolean(s);
867         if (r > 0)
868                 return ADDRESS_FAMILY_YES;
869         if (r == 0)
870                 return ADDRESS_FAMILY_NO;
871
872         if (streq(s, "ipv4"))
873                 return ADDRESS_FAMILY_IPV4;
874         if (streq(s, "ipv6"))
875                 return ADDRESS_FAMILY_IPV6;
876
877         return _ADDRESS_FAMILY_BOOLEAN_INVALID;
878 }
879
880 DEFINE_CONFIG_PARSE_ENUM(config_parse_address_family_boolean, address_family_boolean, AddressFamilyBoolean, "Failed to parse option");