]> git.ipfire.org Git - thirdparty/systemd.git/blame - src/core/loopback-setup.c
util-lib: split our string related calls from util.[ch] into its own file string...
[thirdparty/systemd.git] / src / core / loopback-setup.c
CommitLineData
d6c9574f 1/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
af5bc85d
LP
2
3/***
4 This file is part of systemd.
5
6 Copyright 2010 Lennart Poettering
7
8 systemd is free software; you can redistribute it and/or modify it
5430f7f2
LP
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
af5bc85d
LP
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
5430f7f2 16 Lesser General Public License for more details.
af5bc85d 17
5430f7f2 18 You should have received a copy of the GNU Lesser General Public License
af5bc85d
LP
19 along with systemd; If not, see <http://www.gnu.org/licenses/>.
20***/
21
af5bc85d 22#include <net/if.h>
af5bc85d 23#include <stdlib.h>
af5bc85d 24
1c4baffc 25#include "sd-netlink.h"
07630cea 26
9ca903cc 27#include "loopback-setup.h"
07630cea
LP
28#include "missing.h"
29#include "netlink-util.h"
5a723174 30
1c4baffc
TG
31static int start_loopback(sd_netlink *rtnl) {
32 _cleanup_netlink_message_unref_ sd_netlink_message *req = NULL;
81eca919 33 int r;
af5bc85d 34
f3fc4815 35 r = sd_rtnl_message_new_link(rtnl, &req, RTM_SETLINK, LOOPBACK_IFINDEX);
fc25d7f8
TG
36 if (r < 0)
37 return r;
38
5d4795f3 39 r = sd_rtnl_message_link_set_flags(req, IFF_UP, IFF_UP);
81eca919
TG
40 if (r < 0)
41 return r;
af5bc85d 42
1c4baffc 43 r = sd_netlink_call(rtnl, req, 0, NULL);
81eca919
TG
44 if (r < 0)
45 return r;
af5bc85d
LP
46
47 return 0;
48}
49
1c4baffc
TG
50static bool check_loopback(sd_netlink *rtnl) {
51 _cleanup_netlink_message_unref_ sd_netlink_message *req = NULL, *reply = NULL;
e95e909d 52 unsigned flags;
e62d8c39 53 int r;
e95e909d
TG
54
55 r = sd_rtnl_message_new_link(rtnl, &req, RTM_GETLINK, LOOPBACK_IFINDEX);
56 if (r < 0)
2f0af4e1 57 return false;
e95e909d 58
1c4baffc 59 r = sd_netlink_call(rtnl, req, 0, &reply);
e95e909d 60 if (r < 0)
2f0af4e1 61 return false;
e95e909d
TG
62
63 r = sd_rtnl_message_link_get_flags(reply, &flags);
64 if (r < 0)
2f0af4e1 65 return false;
e95e909d
TG
66
67 return flags & IFF_UP;
2c3ff76e
LP
68}
69
af5bc85d 70int loopback_setup(void) {
1c4baffc 71 _cleanup_netlink_unref_ sd_netlink *rtnl = NULL;
f3fc4815 72 int r;
0a0dc69b 73
1c4baffc 74 r = sd_netlink_open(&rtnl);
2c3ff76e 75 if (r < 0)
81eca919 76 return r;
af5bc85d 77
f3fc4815 78 r = start_loopback(rtnl);
8f084002
LP
79 if (r < 0) {
80
81 /* If we lack the permissions to configure the
82 * loopback device, but we find it to be already
83 * configured, let's exit cleanly, in order to
84 * supported unprivileged containers. */
85 if (r == -EPERM && check_loopback(rtnl))
86 return 0;
af5bc85d 87
8f084002
LP
88 return log_warning_errno(r, "Failed to configure loopback device: %m");
89 }
2c3ff76e 90
e62d8c39 91 return 0;
af5bc85d 92}