On 8/17/24 7:13 PM, Geliang Tang wrote:
Take a look at a recent example [0]. The mptcp test is under a cgroup
already
and has the cgroup setup. An extra "cgroup/getsockopt" prog should be
enough.
That prog can walk the msk->conn_list and use bpf_rdonly_cast (or the
>> bpf_core_cast macro in libbpf) to cast a pointer to tcp_sock for

[ ... ]

SEC("cgroup/getsockopt")
int _getsockopt(struct bpf_sockopt *ctx)
{
         struct mptcp_sock *msk = bpf_core_cast(ctx->sk, struct
mptcp_sock);
         struct mptcp_subflow_context *subflow;
         __u32 token = 0;

         if (!msk || ctx->level != SOL_TCP ||
                        ctx->optname != TCP_CONGESTION)
                 return 1;

         subflow = list_first_entry(&msk->conn_list,
                        struct mptcp_subflow_context, node);
         token = subflow->token;
         bpf_trace_printk(fmt, sizeof(fmt), msk, token);

         return 1;
}

And got some access errors:

; token = subflow->token; @ mptcp_subflow.c:92
13: (61) r4 = *(u32 *)(r1 +524)
access beyond struct list_head at off 524 size 4

Similar to your bpf_core_cast() usage earlier that casts a sock ptr to mptcp_sock ptr. r1 is in list_head ptr type. It needs to cast to mptcp_subflow_context ptr.

The same cast to tcp_sock is needed when you try to get the tcp_sock ptr from subflow->tcp_sock which is in "struct sock *" type in the kernel instead of "struct tcp_sock *".


Reply via email to