summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorYu Watanabe <watanabe.yu+github@gmail.com>2019-06-05 04:01:44 +0900
committerGitHub <noreply@github.com>2019-06-05 04:01:44 +0900
commit277cb7631e5bc18b152adc31df5b727a2fa20b7a (patch)
treedd31faa3537bc450927a651a5bb9dee16caa950b /src
parente8b88eb94c34f985b89cedbc4b3a22548ca0ba32 (diff)
parentf140ed02f764c731a948dc2b4c3349ba6e2eff24 (diff)
downloadsystemd-277cb7631e5bc18b152adc31df5b727a2fa20b7a.tar.gz
systemd-277cb7631e5bc18b152adc31df5b727a2fa20b7a.tar.bz2
systemd-277cb7631e5bc18b152adc31df5b727a2fa20b7a.zip
Merge pull request #12741 from keszybz/bpf-firewall-warning
Silence BPF firewall warning when not useful
Diffstat (limited to 'src')
-rw-r--r--src/core/bpf-firewall.c55
-rw-r--r--src/core/bpf-firewall.h2
-rw-r--r--src/core/cgroup.c4
-rw-r--r--src/core/dbus-cgroup.c15
-rw-r--r--src/core/ip-address-access.c15
5 files changed, 46 insertions, 45 deletions
diff --git a/src/core/bpf-firewall.c b/src/core/bpf-firewall.c
index 723c7b4b4e..7b9aeb6fbf 100644
--- a/src/core/bpf-firewall.c
+++ b/src/core/bpf-firewall.c
@@ -23,6 +23,7 @@
#include "memory-util.h"
#include "missing_syscall.h"
#include "unit.h"
+#include "virt.h"
enum {
MAP_KEY_PACKETS,
@@ -484,19 +485,17 @@ int bpf_firewall_compile(Unit *u) {
supported = bpf_firewall_supported();
if (supported < 0)
return supported;
- if (supported == BPF_FIREWALL_UNSUPPORTED) {
- log_unit_debug(u, "BPF firewalling not supported on this manager, proceeding without.");
- return -EOPNOTSUPP;
- }
- if (supported != BPF_FIREWALL_SUPPORTED_WITH_MULTI && u->type == UNIT_SLICE) {
+ if (supported == BPF_FIREWALL_UNSUPPORTED)
+ return log_unit_debug_errno(u, SYNTHETIC_ERRNO(EOPNOTSUPP),
+ "BPF firewalling not supported on this manager, proceeding without.");
+ if (supported != BPF_FIREWALL_SUPPORTED_WITH_MULTI && u->type == UNIT_SLICE)
/* If BPF_F_ALLOW_MULTI is not supported we don't support any BPF magic on inner nodes (i.e. on slice
* units), since that would mean leaf nodes couldn't do any BPF anymore at all. Under the assumption
* that BPF is more interesting on leaf nodes we hence avoid it on inner nodes in that case. This is
* consistent with old systemd behaviour from before v238, where BPF wasn't supported in inner nodes at
* all, either. */
- log_unit_debug(u, "BPF_F_ALLOW_MULTI is not supported on this manager, not doing BPF firewall on slice units.");
- return -EOPNOTSUPP;
- }
+ return log_unit_debug_errno(u, SYNTHETIC_ERRNO(EOPNOTSUPP),
+ "BPF_F_ALLOW_MULTI is not supported on this manager, not doing BPF firewall on slice units.");
/* Note that when we compile a new firewall we first flush out the access maps and the BPF programs themselves,
* but we reuse the the accounting maps. That way the firewall in effect always maps to the actual
@@ -645,6 +644,8 @@ int bpf_firewall_reset_accounting(int map_fd) {
return bpf_map_update_element(map_fd, &key, &value);
}
+static int bpf_firewall_unsupported_reason = 0;
+
int bpf_firewall_supported(void) {
struct bpf_insn trivial[] = {
BPF_MOV64_IMM(BPF_REG_0, 1),
@@ -669,7 +670,9 @@ int bpf_firewall_supported(void) {
return supported;
if (geteuid() != 0) {
- log_debug("Not enough privileges, BPF firewalling is not supported.");
+ bpf_firewall_unsupported_reason =
+ log_debug_errno(SYNTHETIC_ERRNO(EACCES),
+ "Not enough privileges, BPF firewalling is not supported.");
return supported = BPF_FIREWALL_UNSUPPORTED;
}
@@ -677,7 +680,9 @@ int bpf_firewall_supported(void) {
if (r < 0)
return log_error_errno(r, "Can't determine whether the unified hierarchy is used: %m");
if (r == 0) {
- log_debug("Not running with unified cgroups, BPF firewalling is not supported.");
+ bpf_firewall_unsupported_reason =
+ log_debug_errno(SYNTHETIC_ERRNO(EUCLEAN),
+ "Not running with unified cgroups, BPF firewalling is not supported.");
return supported = BPF_FIREWALL_UNSUPPORTED;
}
@@ -687,7 +692,8 @@ int bpf_firewall_supported(void) {
1,
BPF_F_NO_PREALLOC);
if (fd < 0) {
- log_debug_errno(fd, "Can't allocate BPF LPM TRIE map, BPF firewalling is not supported: %m");
+ bpf_firewall_unsupported_reason =
+ log_debug_errno(fd, "Can't allocate BPF LPM TRIE map, BPF firewalling is not supported: %m");
return supported = BPF_FIREWALL_UNSUPPORTED;
}
@@ -695,19 +701,22 @@ int bpf_firewall_supported(void) {
r = bpf_program_new(BPF_PROG_TYPE_CGROUP_SKB, &program);
if (r < 0) {
- log_debug_errno(r, "Can't allocate CGROUP SKB BPF program, BPF firewalling is not supported: %m");
+ bpf_firewall_unsupported_reason =
+ log_debug_errno(r, "Can't allocate CGROUP SKB BPF program, BPF firewalling is not supported: %m");
return supported = BPF_FIREWALL_UNSUPPORTED;
}
r = bpf_program_add_instructions(program, trivial, ELEMENTSOF(trivial));
if (r < 0) {
- log_debug_errno(r, "Can't add trivial instructions to CGROUP SKB BPF program, BPF firewalling is not supported: %m");
+ bpf_firewall_unsupported_reason =
+ log_debug_errno(r, "Can't add trivial instructions to CGROUP SKB BPF program, BPF firewalling is not supported: %m");
return supported = BPF_FIREWALL_UNSUPPORTED;
}
r = bpf_program_load_kernel(program, NULL, 0);
if (r < 0) {
- log_debug_errno(r, "Can't load kernel CGROUP SKB BPF program, BPF firewalling is not supported: %m");
+ bpf_firewall_unsupported_reason =
+ log_debug_errno(r, "Can't load kernel CGROUP SKB BPF program, BPF firewalling is not supported: %m");
return supported = BPF_FIREWALL_UNSUPPORTED;
}
@@ -727,7 +736,8 @@ int bpf_firewall_supported(void) {
if (bpf(BPF_PROG_DETACH, &attr, sizeof(attr)) < 0) {
if (errno != EBADF) {
- log_debug_errno(errno, "Didn't get EBADF from BPF_PROG_DETACH, BPF firewalling is not supported: %m");
+ bpf_firewall_unsupported_reason =
+ log_debug_errno(errno, "Didn't get EBADF from BPF_PROG_DETACH, BPF firewalling is not supported: %m");
return supported = BPF_FIREWALL_UNSUPPORTED;
}
@@ -766,3 +776,18 @@ int bpf_firewall_supported(void) {
return supported = BPF_FIREWALL_UNSUPPORTED;
}
}
+
+void emit_bpf_firewall_warning(Unit *u) {
+ static bool warned = false;
+
+ if (!warned) {
+ bool quiet = bpf_firewall_unsupported_reason == -EPERM && detect_container();
+
+ log_unit_full(u, quiet ? LOG_DEBUG : LOG_WARNING, bpf_firewall_unsupported_reason,
+ "unit configures an IP firewall, but %s.\n"
+ "(This warning is only shown for the first unit using IP firewalling.)",
+ getuid() != 0 ? "not running as root" :
+ "the local system does not support BPF/cgroup firewalling");
+ warned = true;
+ }
+}
diff --git a/src/core/bpf-firewall.h b/src/core/bpf-firewall.h
index 7d38483dbd..10cafcc02e 100644
--- a/src/core/bpf-firewall.h
+++ b/src/core/bpf-firewall.h
@@ -18,3 +18,5 @@ int bpf_firewall_install(Unit *u);
int bpf_firewall_read_accounting(int map_fd, uint64_t *ret_bytes, uint64_t *ret_packets);
int bpf_firewall_reset_accounting(int map_fd);
+
+void emit_bpf_firewall_warning(Unit *u);
diff --git a/src/core/cgroup.c b/src/core/cgroup.c
index 042a742fa9..a7263855dc 100644
--- a/src/core/cgroup.c
+++ b/src/core/cgroup.c
@@ -1540,6 +1540,10 @@ CGroupMask unit_get_target_mask(Unit *u) {
* hierarchy that shall be enabled for it. */
mask = unit_get_own_mask(u) | unit_get_members_mask(u) | unit_get_siblings_mask(u);
+
+ if (mask & CGROUP_MASK_BPF_FIREWALL & ~u->manager->cgroup_supported)
+ emit_bpf_firewall_warning(u);
+
mask &= u->manager->cgroup_supported;
mask &= ~unit_get_ancestor_disable_mask(u);
diff --git a/src/core/dbus-cgroup.c b/src/core/dbus-cgroup.c
index d75628c663..9f4fd06dc4 100644
--- a/src/core/dbus-cgroup.c
+++ b/src/core/dbus-cgroup.c
@@ -1426,21 +1426,6 @@ int bus_cgroup_set_property(
return r;
unit_write_setting(u, flags, name, buf);
-
- if (*list) {
- r = bpf_firewall_supported();
- if (r < 0)
- return r;
- if (r == BPF_FIREWALL_UNSUPPORTED) {
- static bool warned = false;
-
- log_full(warned ? LOG_DEBUG : LOG_WARNING,
- "Transient unit %s configures an IP firewall, but the local system does not support BPF/cgroup firewalling.\n"
- "Proceeding WITHOUT firewalling in effect! (This warning is only shown for the first started transient unit using IP firewalling.)", u->id);
-
- warned = true;
- }
- }
}
return 1;
diff --git a/src/core/ip-address-access.c b/src/core/ip-address-access.c
index 1d431bb674..36cec70c2c 100644
--- a/src/core/ip-address-access.c
+++ b/src/core/ip-address-access.c
@@ -134,21 +134,6 @@ int config_parse_ip_address_access(
*list = ip_address_access_reduce(*list);
- if (*list) {
- r = bpf_firewall_supported();
- if (r < 0)
- return r;
- if (r == BPF_FIREWALL_UNSUPPORTED) {
- static bool warned = false;
-
- log_full(warned ? LOG_DEBUG : LOG_WARNING,
- "File %s:%u configures an IP firewall (%s=%s), but the local system does not support BPF/cgroup based firewalling.\n"
- "Proceeding WITHOUT firewalling in effect! (This warning is only shown for the first loaded unit using IP firewalling.)", filename, line, lvalue, rvalue);
-
- warned = true;
- }
- }
-
return 0;
}