diff options
author | Yu Watanabe <watanabe.yu+github@gmail.com> | 2019-06-05 04:01:44 +0900 |
---|---|---|
committer | GitHub <noreply@github.com> | 2019-06-05 04:01:44 +0900 |
commit | 277cb7631e5bc18b152adc31df5b727a2fa20b7a (patch) | |
tree | dd31faa3537bc450927a651a5bb9dee16caa950b /src | |
parent | e8b88eb94c34f985b89cedbc4b3a22548ca0ba32 (diff) | |
parent | f140ed02f764c731a948dc2b4c3349ba6e2eff24 (diff) | |
download | systemd-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.c | 55 | ||||
-rw-r--r-- | src/core/bpf-firewall.h | 2 | ||||
-rw-r--r-- | src/core/cgroup.c | 4 | ||||
-rw-r--r-- | src/core/dbus-cgroup.c | 15 | ||||
-rw-r--r-- | src/core/ip-address-access.c | 15 |
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; } |