From nobody Sat Sep 26 02:02:52 2026 Received: from m16.mail.163.com (m16.mail.163.com [220.197.31.4]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 2669650255F; Fri, 18 Sep 2026 17:24:56 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=220.197.31.4 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1789752306; cv=none; b=YCIP53VXhWJFRycHKwcXg6gjNtYHvNoVICEXoHJqC0gJ14OJwemPC7p0GB6SrgljHhlBUXVxXKvSpg80zaeRAfNGtoWmXxO8cQGzGdhN2f4Q7d3fSpZV35OjEAxq+jKKtzTepFI/VACoEF64GRiZoGNkg2VBQzCQXIGJpGSJBnk= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1789752306; c=relaxed/simple; bh=LaO+SqfW2deYM/scbJpdFmumIN9PsPB68r8/lRl4k94=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=qy/gvLwFcGdWLMTjF9XbRu+80Nw39mN0fuchuloPm766OLGjHjoatIvSHWazG7YF70s+L8/GopUjDvoimOk+yMHcBPww6vSXp94YWx/YFsUE0uMCkiI7SlMlxUpra4devDgpquAysI8R++g1AoakJdEorUidKrysipBBarcPHdw= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=163.com; spf=pass smtp.mailfrom=163.com; dkim=pass (1024-bit key) header.d=163.com header.i=@163.com header.b=QYYah+fV; arc=none smtp.client-ip=220.197.31.4 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=163.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=163.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=163.com header.i=@163.com header.b="QYYah+fV" DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=163.com; s=s110527; h=From:To:Subject:Date:Message-ID:MIME-Version; bh=Ti 9A+/UoRybWlQcIRPQ3w4tKAGiqMm7blYW1NdiCiEc=; b=QYYah+fVudniydHECO JIqm6UwIWfMPUPWHzmCh6CHxYeMhilNsZTBYjkWRdOP2T/NjDzMxpCyYr4by5uT2 Oyjb27Em2F5w0F2QvrqOzDy8FuXoiLg95X0TIAU6aZwinZkyVG3xjEetwkXyAjQw 0WoFW+hPQOpk/iTmPe5l752B0= Received: from localhost (unknown []) by gzga-smtp-mtada-g1-3 (Coremail) with SMTP id _____wCnLZG5c61qRycvBQ--.1403S2; Sat, 19 Sep 2026 01:24:10 +0800 (CST) From: Hui Su To: bpf@vger.kernel.org, Alexei Starovoitov , Daniel Borkmann , Andrii Nakryiko , Eduard Zingerman , Kumar Kartikeya Dwivedi Cc: Yonghong Song , Quentin Monnet , Martin KaFai Lau , Song Liu , Jiri Olsa , Emil Tsalapatis , Ihor Solodrai , Shuah Khan , linux-kselftest@vger.kernel.org, linux-kernel@vger.kernel.org, Hui Su Subject: [PATCH bpf 1/3] bpf: Report BPF_F_PREORDER in cgroup program queries Date: Sat, 19 Sep 2026 02:24:05 +0900 Message-ID: <20260918172407.3459188-2-sh_def@163.com> X-Mailer: git-send-email 2.55.0 In-Reply-To: <20260918172407.3459188-1-sh_def@163.com> References: <20260918172407.3459188-1-sh_def@163.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-CM-TRANSID: _____wCnLZG5c61qRycvBQ--.1403S2 X-Coremail-Antispam: 1Uf129KBjvJXoW7tr1rXr17uF1rJFyxZrWxtFb_yoW8uFWfpF 4kXFy7Wa1qvr12qanFv3yrXFW8Kwn3XF4UCFZxJw1rCFW3Wr1IyryIkFWYvFy5ArZFyr10 yF90vrn0gF1DZFJanT9S1TB71UUUUU7qnTZGkaVYY2UrUUUUjbIjqfuFe4nvWSU5nxnvy2 9KBjDUYxBIdaVFxhVjvjDU0xZFpf9x0zioq2tUUUUU= X-CM-SenderInfo: xvkbvvri6rljoofrz/xtbCwRoRcGqtc7pTUwAA30 Content-Type: text/plain; charset="utf-8" Commit 4b82b181a26c ("bpf: Allow pre-ordering for bpf cgroup progs") introduced BPF_F_PREORDER to request pre-order execution across the cgroup hierarchy, altering the effective prog array ordering. While pl->flags stores BPF_F_PREORDER for each attached program, __cgroup_bpf_query() currently fails to report it. When querying attached programs (!effective_query), __cgroup_bpf_query() fills prog_attach_flags[] with cgrp->bpf.flags[atype] for all entries, omitting the per-program BPF_F_PREORDER attribute. As a result, user space tools and query callers cannot distinguish pre-ordered programs from standard multi-prog attachments via BPF_PROG_QUERY. Fix this by merging (pl->flags & BPF_F_PREORDER) with the cgroup-wide flags when copying prog_attach_flags to user space. Only BPF_F_PREORDER is extracted from pl->flags to ensure transient positioning flags (such as BPF_F_BEFORE, BPF_F_AFTER, BPF_F_ID, or BPF_F_REPLACE) are not leaked to user space. Also perform both ID and attach flags copies within the same hlist iteration. Fixes: 4b82b181a26c ("bpf: Allow pre-ordering for bpf cgroup progs") Signed-off-by: Hui Su --- kernel/bpf/cgroup.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/kernel/bpf/cgroup.c b/kernel/bpf/cgroup.c index 149672c76c49..e7c7efa1baa7 100644 --- a/kernel/bpf/cgroup.c +++ b/kernel/bpf/cgroup.c @@ -1353,19 +1353,19 @@ static int __cgroup_bpf_query(struct cgroup *cgrp, = const union bpf_attr *attr, id =3D prog->aux->id; if (copy_to_user(prog_ids + i, &id, sizeof(id))) return -EFAULT; + if (prog_attach_flags) { + flags =3D cgrp->bpf.flags[atype] | + (pl->flags & BPF_F_PREORDER); + if (copy_to_user(prog_attach_flags + i, + &flags, sizeof(flags))) + return -EFAULT; + } if (++i =3D=3D cnt) break; } =20 - if (prog_attach_flags) { - flags =3D cgrp->bpf.flags[atype]; - - for (i =3D 0; i < cnt; i++) - if (copy_to_user(prog_attach_flags + i, - &flags, sizeof(flags))) - return -EFAULT; + if (prog_attach_flags) prog_attach_flags +=3D cnt; - } } =20 prog_ids +=3D cnt; --=20 2.55.0 From nobody Sat Sep 26 02:02:52 2026 Received: from m16.mail.163.com (m16.mail.163.com [220.197.31.5]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 40E5651B172; Fri, 18 Sep 2026 17:24:58 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=220.197.31.5 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1789752304; cv=none; b=czxARAsXWzDTMNNWzISw57lz365o80yc5k7h4IfGrEzNSRzHRGjlROQwN8JalBudA0cnBULGHvofRylZIdFTTgzqHftbEFTW4Xt+5/eWV/VrGHYB0S3/erUEUSz6p8fGjww2ShgSiHdalNOTvZs0m82YHOgCE6d1GwukHSPE3y8= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1789752304; c=relaxed/simple; bh=k9loHwbjbFtNefqL9fgH782oIzs3XLn/+r9Ypzw4pk8=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=cAaPe3P2cKOXTdbNva1NeD6h0kHOdfBAvDTtXgMiEwM22It6dG9QCNY8SMpZNeXq9hh24/jJHxCHErf6E3Y92x7P2InWLLr1oW+JHe62KxNTK73S1HgRIIGuVKyjcA8MxUY8XhgA3eBBruZHSn4r2UXtIX/c7zXHsD9GuqV7+9Y= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=163.com; spf=pass smtp.mailfrom=163.com; dkim=pass (1024-bit key) header.d=163.com header.i=@163.com header.b=Z1sevU0p; arc=none smtp.client-ip=220.197.31.5 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=163.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=163.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=163.com header.i=@163.com header.b="Z1sevU0p" DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=163.com; s=s110527; h=From:To:Subject:Date:Message-ID:MIME-Version; bh=LO NQR/eTuMAe5RuWYz+f969kvAnzBf9rM/KZ984g2kg=; b=Z1sevU0pS9ofcMSHOo eTXqxGrHZoCEIueEcfha+uT2t/CATKWCQouePoLXivBemA6kQ/b1yPNrNHqpZbcq MkRf12Y/63affycHnTBvTMkbhvGcgGs9mkfvkEMnVDKvOal07Hm3Rnc06bTR449i f3YwrSXYT/RXnaDrJPixt4Gu4= Received: from localhost (unknown []) by gzga-smtp-mtada-g0-2 (Coremail) with SMTP id _____wCHKsy6c61q2cb6BQ--.22248S2; Sat, 19 Sep 2026 01:24:11 +0800 (CST) From: Hui Su To: bpf@vger.kernel.org, Alexei Starovoitov , Daniel Borkmann , Andrii Nakryiko , Eduard Zingerman , Kumar Kartikeya Dwivedi Cc: Yonghong Song , Quentin Monnet , Martin KaFai Lau , Song Liu , Jiri Olsa , Emil Tsalapatis , Ihor Solodrai , Shuah Khan , linux-kselftest@vger.kernel.org, linux-kernel@vger.kernel.org, Hui Su Subject: [PATCH bpf 2/3] selftests/bpf: Test querying BPF_F_PREORDER cgroup attachments Date: Sat, 19 Sep 2026 02:24:06 +0900 Message-ID: <20260918172407.3459188-3-sh_def@163.com> X-Mailer: git-send-email 2.55.0 In-Reply-To: <20260918172407.3459188-1-sh_def@163.com> References: <20260918172407.3459188-1-sh_def@163.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-CM-TRANSID: _____wCHKsy6c61q2cb6BQ--.22248S2 X-Coremail-Antispam: 1Uf129KBjvJXoW3Jr4kWw4UKrykuFW5Kr15Arb_yoWxGr15pF ykXFyUKF15Xa4UXF4Ut3y7Zr42qF1DXF1YkrZ5Wr1Y9FWUWFyv9ryrKF4YkFyft3yDZw1I vwn8Zrs8XrWDWF7anT9S1TB71UUUUU7qnTZGkaVYY2UrUUUUjbIjqfuFe4nvWSU5nxnvy2 9KBjDUYxBIdaVFxhVjvjDU0xZFpf9x0pi5CzJUUUUU= X-CM-SenderInfo: xvkbvvri6rljoofrz/xtbC6hsRcGqtc7ueCgAA3L Content-Type: text/plain; charset="utf-8" Extend cgroup_mprog_opts selftests to verify that BPF_PROG_QUERY reports BPF_F_PREORDER in prog_attach_flags for both direct program and link attachments. Specifically, in test_preorder_prog_attach_detach() and test_preorder_link_attach_detach(), verify that: - Programs attached with BPF_F_PREORDER report BPF_F_ALLOW_MULTI | BPF_F_PREORDER (0x42) in prog_attach_flags. - Programs attached without BPF_F_PREORDER report BPF_F_ALLOW_MULTI (0x2). - Transient flags such as BPF_F_AFTER or BPF_F_LINK are not present in prog_attach_flags. - Per-program attach flags are validated by matching each attached prog_id via a query helper, avoiding fragile assumptions on the internal slot order of the direct query list. Signed-off-by: Hui Su --- .../bpf/prog_tests/cgroup_mprog_opts.c | 94 ++++++++++++++++++- 1 file changed, 91 insertions(+), 3 deletions(-) diff --git a/tools/testing/selftests/bpf/prog_tests/cgroup_mprog_opts.c b/t= ools/testing/selftests/bpf/prog_tests/cgroup_mprog_opts.c index bb60704a3ef9..343357d9c460 100644 --- a/tools/testing/selftests/bpf/prog_tests/cgroup_mprog_opts.c +++ b/tools/testing/selftests/bpf/prog_tests/cgroup_mprog_opts.c @@ -273,13 +273,31 @@ static void test_link_attach_detach(int atype) close(cg); } =20 +static int find_prog_attach_flags(const struct bpf_prog_query_opts *opts, + __u32 prog_id, __u32 *flags) +{ + __u32 i; + + for (i =3D 0; i < opts->count; i++) { + if (opts->prog_ids[i] =3D=3D prog_id) { + *flags =3D opts->prog_attach_flags[i]; + return 0; + } + } + return -ENOENT; +} + static void test_preorder_prog_attach_detach(int atype) { LIBBPF_OPTS(bpf_prog_attach_opts, opta); LIBBPF_OPTS(bpf_prog_detach_opts, optd); - __u32 fd1, fd2, fd3, fd4; + LIBBPF_OPTS(bpf_prog_query_opts, optq); + __u32 fd1, fd2, fd3, fd4, id1, id2, id3, id4; + __u32 prog_attach_flags[10] =3D {0}; + __u32 prog_ids[10] =3D {0}; struct cgroup_mprog *skel; int cg, err; + __u32 flags; =20 cg =3D test__join_cgroup("/preorder_prog_attach_detach"); if (!ASSERT_GE(cg, 0, "join_cgroup /preorder_prog_attach_detach")) @@ -294,6 +312,11 @@ static void test_preorder_prog_attach_detach(int atype) fd3 =3D bpf_program__fd(skel->progs.getsockopt_3); fd4 =3D bpf_program__fd(skel->progs.getsockopt_4); =20 + id1 =3D id_from_prog_fd(fd1); + id2 =3D id_from_prog_fd(fd2); + id3 =3D id_from_prog_fd(fd3); + id4 =3D id_from_prog_fd(fd4); + assert_mprog_count(cg, atype, 0); =20 LIBBPF_OPTS_RESET(opta, @@ -357,6 +380,34 @@ static void test_preorder_prog_attach_detach(int atype) =20 assert_mprog_count(cg, atype, 4); =20 + optq.prog_ids =3D prog_ids; + optq.prog_attach_flags =3D prog_attach_flags; + optq.count =3D 10; + err =3D bpf_prog_query_opts(cg, atype, &optq); + if (!ASSERT_OK(err, "prog_query")) + goto cleanup4; + + ASSERT_EQ(optq.count, 4, "count"); + /* Direct query reports attached programs in cgroup list order. + * Lookup by prog_id to verify per-program flags independently of slot in= dex. + */ + err =3D find_prog_attach_flags(&optq, id1, &flags); + if (ASSERT_OK(err, "find id1")) + ASSERT_EQ(flags, BPF_F_ALLOW_MULTI, "flags id1"); + + err =3D find_prog_attach_flags(&optq, id2, &flags); + if (ASSERT_OK(err, "find id2")) + ASSERT_EQ(flags, BPF_F_ALLOW_MULTI | BPF_F_PREORDER, "flags id2"); + + err =3D find_prog_attach_flags(&optq, id3, &flags); + if (ASSERT_OK(err, "find id3")) + ASSERT_EQ(flags, BPF_F_ALLOW_MULTI | BPF_F_PREORDER, "flags id3"); + + err =3D find_prog_attach_flags(&optq, id4, &flags); + if (ASSERT_OK(err, "find id4")) + ASSERT_EQ(flags, BPF_F_ALLOW_MULTI, "flags id4"); + +cleanup4: err =3D bpf_prog_detach_opts(fd4, cg, atype, &optd); ASSERT_OK(err, "prog_detach"); assert_mprog_count(cg, atype, 3); @@ -384,10 +435,14 @@ static void test_preorder_prog_attach_detach(int atyp= e) static void test_preorder_link_attach_detach(int atype) { LIBBPF_OPTS(bpf_cgroup_opts, opta); + LIBBPF_OPTS(bpf_prog_query_opts, optq); struct bpf_link *link1, *link2, *link3, *link4; struct cgroup_mprog *skel; - __u32 fd2; - int cg; + __u32 fd2, id1, id2, id3, id4; + __u32 prog_attach_flags[10] =3D {0}; + __u32 prog_ids[10] =3D {0}; + int cg, err; + __u32 flags; =20 cg =3D test__join_cgroup("/preorder_link_attach_detach"); if (!ASSERT_GE(cg, 0, "join_cgroup /preorder_link_attach_detach")) @@ -399,6 +454,11 @@ static void test_preorder_link_attach_detach(int atype) =20 fd2 =3D bpf_program__fd(skel->progs.getsockopt_2); =20 + id1 =3D id_from_prog_fd(bpf_program__fd(skel->progs.getsockopt_1)); + id2 =3D id_from_prog_fd(fd2); + id3 =3D id_from_prog_fd(bpf_program__fd(skel->progs.getsockopt_3)); + id4 =3D id_from_prog_fd(bpf_program__fd(skel->progs.getsockopt_4)); + assert_mprog_count(cg, atype, 0); =20 LIBBPF_OPTS_RESET(opta, @@ -460,6 +520,34 @@ static void test_preorder_link_attach_detach(int atype) =20 assert_mprog_count(cg, atype, 4); =20 + optq.prog_ids =3D prog_ids; + optq.prog_attach_flags =3D prog_attach_flags; + optq.count =3D 10; + err =3D bpf_prog_query_opts(cg, atype, &optq); + if (!ASSERT_OK(err, "prog_query")) + goto cleanup4; + + ASSERT_EQ(optq.count, 4, "count"); + /* Direct query reports attached programs in cgroup list order. + * Lookup by prog_id to verify per-program flags independently of slot in= dex. + */ + err =3D find_prog_attach_flags(&optq, id1, &flags); + if (ASSERT_OK(err, "find id1")) + ASSERT_EQ(flags, BPF_F_ALLOW_MULTI, "flags id1"); + + err =3D find_prog_attach_flags(&optq, id2, &flags); + if (ASSERT_OK(err, "find id2")) + ASSERT_EQ(flags, BPF_F_ALLOW_MULTI | BPF_F_PREORDER, "flags id2"); + + err =3D find_prog_attach_flags(&optq, id3, &flags); + if (ASSERT_OK(err, "find id3")) + ASSERT_EQ(flags, BPF_F_ALLOW_MULTI | BPF_F_PREORDER, "flags id3"); + + err =3D find_prog_attach_flags(&optq, id4, &flags); + if (ASSERT_OK(err, "find id4")) + ASSERT_EQ(flags, BPF_F_ALLOW_MULTI, "flags id4"); + +cleanup4: bpf_link__destroy(link4); assert_mprog_count(cg, atype, 3); =20 --=20 2.55.0 From nobody Sat Sep 26 02:02:52 2026 Received: from m16.mail.163.com (m16.mail.163.com [117.135.210.5]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id E5DD151A14E; Fri, 18 Sep 2026 17:24:55 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=117.135.210.5 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1789752300; cv=none; b=ffbx0DWUStPkMvxPG/JeYIppocjWB4TMQCr7dEU+y2Qdmtw530QG/jdd9uX49yjmEglrgYsRTkNZMivM0lYYCG+93okbMM8TjF5g5VnTuk0Rdw/GbpgbkdP7QedJYth/MWfyc6jQnXuMwiELjWyOr+Deb4W4eqzhfK3Ph4lBUSY= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1789752300; c=relaxed/simple; bh=vUh7k6/sgzYvC1EwkqVYUJP2zwwUD/OVrEJJTTCiv6w=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=Sgdl27HDSZ7R3biAepuY9iOeNCBUTOfm8jyd2yVlMN/664nl+ZtOLHizUfiJJtiVsPHkr385rzQPwJCy/49Qyal0n5EFTQGSdTrTgK1m/awiVdz+iWCiMCRDZBG8WPj1nVhj+1ZoToyu22v5sXEoupnPMsT7ts1vmBt6SW/lSIk= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=163.com; spf=pass smtp.mailfrom=163.com; dkim=pass (1024-bit key) header.d=163.com header.i=@163.com header.b=CCxLPu7K; arc=none smtp.client-ip=117.135.210.5 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=163.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=163.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=163.com header.i=@163.com header.b="CCxLPu7K" DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=163.com; s=s110527; h=From:To:Subject:Date:Message-ID:MIME-Version; bh=w5 fWPWYIbg6KghdEbDIe/kAKt5hevm4hGcALmYK1xKI=; b=CCxLPu7KgvBIuMgU1t 2ojYib9vk5rrQGqFSA2juOyQSQvQuTnO2SZ7d99IxSa2leH/E+QFXbV6AKBY4Fz+ U/WHg7amkEUx9ODaHlYwWhnpqU80hebvK4g5DgB95beeWSvng9G7o35VJyuGmTpv QJ0Q5Xjq7XY+zLZcBC98i9cQI= Received: from localhost (unknown []) by gzsmtp4 (Coremail) with SMTP id PygvCgAXUUq7c61qHvN9AA--.16484S2; Sat, 19 Sep 2026 01:24:12 +0800 (CST) From: Hui Su To: bpf@vger.kernel.org, Alexei Starovoitov , Daniel Borkmann , Andrii Nakryiko , Eduard Zingerman , Kumar Kartikeya Dwivedi Cc: Yonghong Song , Quentin Monnet , Martin KaFai Lau , Song Liu , Jiri Olsa , Emil Tsalapatis , Ihor Solodrai , Shuah Khan , linux-kselftest@vger.kernel.org, linux-kernel@vger.kernel.org, Hui Su Subject: [PATCH bpf 3/3] bpftool: Add support for BPF_F_PREORDER cgroup attach flag Date: Sat, 19 Sep 2026 02:24:07 +0900 Message-ID: <20260918172407.3459188-4-sh_def@163.com> X-Mailer: git-send-email 2.55.0 In-Reply-To: <20260918172407.3459188-1-sh_def@163.com> References: <20260918172407.3459188-1-sh_def@163.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-CM-TRANSID: PygvCgAXUUq7c61qHvN9AA--.16484S2 X-Coremail-Antispam: 1Uf129KBjvJXoWxKr17Cr1DGry7XF1kCw47twb_yoWxWr4rpF 4kXFyUK3WrW3sxXa1xC390gFWFgrs7WFWUCFy5Jw1Y9FW3Gw1vkrWfKFWF9rn8XFW3Aw40 vrWYvr45WF1jvFDanT9S1TB71UUUUU7qnTZGkaVYY2UrUUUUjbIjqfuFe4nvWSU5nxnvy2 9KBjDUYxBIdaVFxhVjvjDU0xZFpf9x0pi5CzJUUUUU= X-CM-SenderInfo: xvkbvvri6rljoofrz/xtbC6hwScWqtc7yeHAAA3f Content-Type: text/plain; charset="utf-8" Commit 4b82b181a26c ("bpf: Allow pre-ordering for bpf cgroup progs") introduced BPF_F_PREORDER to request pre-order execution across the cgroup hierarchy. Furthermore, attachments legitimately use combinations such as BPF_F_ALLOW_MULTI | BPF_F_PREORDER. With BPF_PROG_QUERY reporting the per-program BPF_F_PREORDER attribute, bpftool's exact-match formatter falls back to "unknown(40)" when BPF_F_PREORDER is present alone, or "unknown(42)" when combined with BPF_F_ALLOW_MULTI. Additionally, do_attach() only accepts "multi" and "override", rejecting "preorder" with "unknown option". Before: $ bpftool cgroup show 1234 cgroup_inet_ingress unknown(42) test_prog $ bpftool cgroup attach cgroup_inet_ingress id 5678 multi preorder Error: unknown option: preorder After: $ bpftool cgroup show 1234 cgroup_inet_ingress multi,preorder test_prog $ bpftool cgroup attach cgroup_inet_ingress id 5678 multi preorder (attaches successfully) Refactor the attach flags formatter to use a bitmask formatter that outputs comma-separated flag names while preserving unrecognized bits as "unknown(...)". Also accept "preorder" in do_attach(), and update bpftool-cgroup.rst, usage help, and bash completion. Signed-off-by: Hui Su --- .../bpftool/Documentation/bpftool-cgroup.rst | 9 ++- tools/bpf/bpftool/bash-completion/bpftool | 2 +- tools/bpf/bpftool/cgroup.c | 55 +++++++++++++------ 3 files changed, 45 insertions(+), 21 deletions(-) diff --git a/tools/bpf/bpftool/Documentation/bpftool-cgroup.rst b/tools/bpf= /bpftool/Documentation/bpftool-cgroup.rst index e8185596a759..8ec2546c0b8e 100644 --- a/tools/bpf/bpftool/Documentation/bpftool-cgroup.rst +++ b/tools/bpf/bpftool/Documentation/bpftool-cgroup.rst @@ -45,7 +45,7 @@ CGROUP COMMANDS | **cgroup_unix_recvmsg** | **cgroup_sysctl** | | **cgroup_getsockopt** | **cgroup_setsockopt** | | **cgroup_inet_sock_release** } -| *ATTACH_FLAGS* :=3D { **multi** | **override** } +| *ATTACH_FLAGS* :=3D { **multi** | **override** | **preorder** } =20 DESCRIPTION =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D @@ -75,10 +75,13 @@ bpftool cgroup attach *CGROUP* *ATTACH_TYPE* *PROG* [*A= TTACH_FLAGS*] Attach program *PROG* to the cgroup *CGROUP* with attach type *ATTACH_= TYPE* and optional *ATTACH_FLAGS*. =20 - *ATTACH_FLAGS* can be one of: **override** if a sub-cgroup installs so= me + *ATTACH_FLAGS* can include: **override** if a sub-cgroup installs some bpf program, the program in this cgroup yields to sub-cgroup program; **multi** if a sub-cgroup installs some bpf program, that cgroup progr= am - gets run in addition to the program in this cgroup. + gets run in addition to the program in this cgroup; + **preorder** requests that this program executes before programs attac= hed + further down the cgroup hierarchy during evaluation. **preorder** can = be + combined with **multi**. =20 Only one program is allowed to be attached to a cgroup with no attach = flags or the **override** flag. Attaching another program will release old diff --git a/tools/bpf/bpftool/bash-completion/bpftool b/tools/bpf/bpftool/= bash-completion/bpftool index 75cbcb512eba..819757d7a360 100644 --- a/tools/bpf/bpftool/bash-completion/bpftool +++ b/tools/bpf/bpftool/bash-completion/bpftool @@ -1057,7 +1057,7 @@ _bpftool() attach|detach) local BPFTOOL_CGROUP_ATTACH_TYPES=3D"$(bpftool feature= list_builtins attach_types 2>/dev/null | \ grep '^cgroup_')" - local ATTACH_FLAGS=3D'multi override' + local ATTACH_FLAGS=3D'multi override preorder' # Check for $prev =3D $command first if [ $prev =3D $command ]; then _filedir diff --git a/tools/bpf/bpftool/cgroup.c b/tools/bpf/bpftool/cgroup.c index ce69d1e5468e..aec1281c95d8 100644 --- a/tools/bpf/bpftool/cgroup.c +++ b/tools/bpf/bpftool/cgroup.c @@ -56,7 +56,7 @@ static const int cgroup_attach_types[] =3D { }; =20 #define HELP_SPEC_ATTACH_FLAGS \ - "ATTACH_FLAGS :=3D { multi | override }" + "ATTACH_FLAGS :=3D { multi | override | preorder }" =20 #define HELP_SPEC_ATTACH_TYPES \ " ATTACH_TYPE :=3D { cgroup_inet_ingress | cgroup_inet_egress |\n" \ @@ -269,6 +269,39 @@ static int show_effective_bpf_progs(int cgroup_fd, enu= m bpf_attach_type type, return 0; } =20 +static const char *format_attach_flags(__u32 attach_flags, char *buf, size= _t sz) +{ + static const struct { + __u32 flag; + const char *name; + } flags[] =3D { + { BPF_F_ALLOW_MULTI, "multi" }, + { BPF_F_ALLOW_OVERRIDE, "override" }, + { BPF_F_PREORDER, "preorder" }, + }; + size_t len =3D 0; + size_t i; + int n; + + buf[0] =3D '\0'; + for (i =3D 0; i < ARRAY_SIZE(flags); i++) { + if (attach_flags & flags[i].flag) { + n =3D snprintf(buf + len, sz - len, "%s%s", + len ? "," : "", flags[i].name); + if (n < 0 || (size_t)n >=3D sz - len) + return buf; + len +=3D n; + attach_flags &=3D ~flags[i].flag; + } + } + + if (attach_flags) + snprintf(buf + len, sz - len, "%sunknown(%x)", + len ? "," : "", attach_flags); + + return buf; +} + static int show_attached_bpf_progs(int cgroup_fd, enum bpf_attach_type typ= e, int level) { @@ -276,7 +309,7 @@ static int show_attached_bpf_progs(int cgroup_fd, enum = bpf_attach_type type, __u32 prog_attach_flags[1024] =3D {0}; const char *attach_flags_str; __u32 prog_ids[1024] =3D {0}; - char buf[32]; + char buf[64]; __u32 iter; int ret; =20 @@ -296,21 +329,7 @@ static int show_attached_bpf_progs(int cgroup_fd, enum= bpf_attach_type type, __u32 attach_flags; =20 attach_flags =3D prog_attach_flags[iter] ?: p.attach_flags; - - switch (attach_flags) { - case BPF_F_ALLOW_MULTI: - attach_flags_str =3D "multi"; - break; - case BPF_F_ALLOW_OVERRIDE: - attach_flags_str =3D "override"; - break; - case 0: - attach_flags_str =3D ""; - break; - default: - snprintf(buf, sizeof(buf), "unknown(%x)", attach_flags); - attach_flags_str =3D buf; - } + attach_flags_str =3D format_attach_flags(attach_flags, buf, sizeof(buf)); =20 show_bpf_prog(prog_ids[iter], type, attach_flags_str, level); @@ -593,6 +612,8 @@ static int do_attach(int argc, char **argv) attach_flags |=3D BPF_F_ALLOW_MULTI; } else if (is_prefix(argv[i], "override")) { attach_flags |=3D BPF_F_ALLOW_OVERRIDE; + } else if (is_prefix(argv[i], "preorder")) { + attach_flags |=3D BPF_F_PREORDER; } else { p_err("unknown option: %s", argv[i]); goto exit_cgroup; --=20 2.55.0