report bpf_current_task_under_cgroup() errors to userspace

bpf_current_task_under_cgroup() returns 1 if the task is under the
specified cgroup, 0 if not, negative if an error happens.

Differentiate the 1 and -1 cases, and report to userspace when we got
and error.
An error like this is mostly unlikely, the only common one is that the
userspace doesn't populate the map, and the call returns -EAGAIN.

Tested by mocking the return value of bpf_current_task_under_cgroup():
    Enumeration completed
    enp1s0f0np0: Configuring with /etc/systemd/network/20-test.network.
    Sysctl monitor BPF returned error: Link number out of range
    Sysctl monitor BPF returned error: No CSI structure available
    Sysctl monitor BPF returned error: Invalid exchange
    Sysctl monitor BPF returned error: Exchange full
    Sysctl monitor BPF returned error: Invalid request code
    Sysctl monitor BPF returned error: Unknown error 58
    Sysctl monitor BPF returned error: Device not a stream
    Sysctl monitor BPF returned error: Timer expired
    Sysctl monitor BPF returned error: Machine is not on the network
    Sysctl monitor BPF returned error: Object is remote
    Sysctl monitor BPF returned error: Advertise error
This commit is contained in:
Matteo Croce
2024-10-12 04:47:18 +09:00
committed by Yu Watanabe
parent b950a8acd8
commit 75355f22db
@@ -65,10 +65,6 @@ SEC("cgroup/sysctl")
int sysctl_monitor(struct bpf_sysctl *ctx) {
int r;
/* Ignore events generated by us */
if (bpf_current_task_under_cgroup(&cgroup_map, 0))
return 1;
/* Allow reads */
if (!ctx->write)
return 1;
@@ -89,6 +85,14 @@ int sysctl_monitor(struct bpf_sysctl *ctx) {
we.pid = bpf_get_current_pid_tgid() >> 32;
we.cgroup_id = bpf_get_current_cgroup_id();
r = bpf_current_task_under_cgroup(&cgroup_map, 0);
if (r < 0) {
we.errorcode = r;
goto send_event;
}
if (r == 1)
return 1; /* Ignore events generated by us */
/* Only monitor /proc/sys/net/ */
r = bpf_sysctl_get_name(ctx, we.path, sizeof(we.path), 0);
if (r < 0) {