From nobody Sat Mar 08 08:13:53 2025 X-Original-To: dev-commits-src-all@mlmmj.nyi.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2610:1c1:1:606c::19:1]) by mlmmj.nyi.freebsd.org (Postfix) with ESMTP id 4Z8wsZ6M47z5qcnP; Sat, 08 Mar 2025 08:13:54 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from mxrelay.nyi.freebsd.org (mxrelay.nyi.freebsd.org [IPv6:2610:1c1:1:606c::19:3]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256 client-signature RSA-PSS (4096 bits) client-digest SHA256) (Client CN "mxrelay.nyi.freebsd.org", Issuer "R10" (verified OK)) by mx1.freebsd.org (Postfix) with ESMTPS id 4Z8wsY66Jdz3klb; Sat, 08 Mar 2025 08:13:53 +0000 (UTC) (envelope-from git@FreeBSD.org) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=freebsd.org; s=dkim; t=1741421633; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=e70a3kWaTYQQXk9THXbI0oLPvkV+/f6ZVmhrVXXMOnM=; b=Z5Bczxu9qs8eQzegHLsfFX+r6rlG5mCictayeGnGBMNhHTNT6y50qPI7nUuharq0ylD/cA Oq5VdZYCamflVuSP+S617arQpd74i82c/jcxzcqvVIWQgO/8xr5zv6/Kp6Q2UaXYm4qiGM pR/DcoXpvPZLA066OL0xPDpsIoW5RD63y2Mu1U5U98wSC5570ybXEKgKjMz8qa5k4HG2VA 2E7Dhuorb2FUwWfJloH4EFsAKKCgbHLQlwC7eIy9A/RH5hzV8QNlY4A/F8vExXNVev6H8Z As0p0yU50BVP/+hL0odKlVprwa2aD3nyuq/BJu9aiOtff3tu2RVVS6ybJrUAJA== ARC-Seal: i=1; s=dkim; d=freebsd.org; t=1741421633; a=rsa-sha256; cv=none; b=cDugtxhV7fs4AHCF0y/KaMjI2W7CBGbguYh9guH5Jy1dkMBrINFKSg70uc0/n8cihTvl5x 530iLbYeASPQ7qPM7L0sneN9lhUJ1yPqEqxISjckvLq1KoE07MYD5j9AbZNZQvWan9mbZl PJy0GspugOHk+vKZhn1xoIG6YCwynlgLFlIEcT+nfnFuMsQv8MAHrryuMySQV0f0Sy0I4w YIWKgRfhj+NBNNok2zgmIZkughWIm/hDTX/tDypA5lEP9NQ7cqEsq4cmV2EqRT92a/3hiv b9Gttj9w9HJ2yZBeA5L+lbPEx86ONwOppPA41dNEHz2wDQjjFRdcG4VtE/vhsA== ARC-Authentication-Results: i=1; mx1.freebsd.org; none ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=freebsd.org; s=dkim; t=1741421633; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=e70a3kWaTYQQXk9THXbI0oLPvkV+/f6ZVmhrVXXMOnM=; b=Y5OaPXLuY08qXSditV0YqL9efd4H7FH6CQ9fV+10wijKH0Z5Abh9t+XO0METs6svZcKEXh eYnBtoloEANpwq2ivCOOlmOiSvY2bzowbXkBxE1rENLIb9vG6XNeTbT6yuq8W9wNeWR1u/ mF636ov3Fn9fp2WDZ+vqaK086Lyb/R6cI9i7IDEDSPmudgGK46TNxAs9gM3ryja2Wj3bKZ L6i4mCetW+ALywzuciF4z8u2pM/AZU4lkG3+qsvWjm2H154Keqeji2kKTXWNr49MFkdFhp KIz14u28gtCewi9v4qDggD6pAWgih+d2sGcbyspiO7mr8BkHbyFMs9YuFc6rMg== Received: from gitrepo.freebsd.org (gitrepo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:5]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (Client did not present a certificate) by mxrelay.nyi.freebsd.org (Postfix) with ESMTPS id 4Z8wsY5jX6zsw; Sat, 08 Mar 2025 08:13:53 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from gitrepo.freebsd.org ([127.0.1.44]) by gitrepo.freebsd.org (8.18.1/8.18.1) with ESMTP id 5288Drmq097539; Sat, 8 Mar 2025 08:13:53 GMT (envelope-from git@gitrepo.freebsd.org) Received: (from git@localhost) by gitrepo.freebsd.org (8.18.1/8.18.1/Submit) id 5288Drq7097536; Sat, 8 Mar 2025 08:13:53 GMT (envelope-from git) Date: Sat, 8 Mar 2025 08:13:53 GMT Message-Id: <202503080813.5288Drq7097536@gitrepo.freebsd.org> To: src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org, dev-commits-src-branches@FreeBSD.org From: Mark Johnston Subject: git: 14d4c1845d1b - stable/14 - queue: Add atomic variants for *_EMPTY List-Id: Commit messages for all branches of the src repository List-Archive: https://lists.freebsd.org/archives/dev-commits-src-all List-Help: List-Post: List-Subscribe: List-Unsubscribe: X-BeenThere: dev-commits-src-all@freebsd.org Sender: owner-dev-commits-src-all@FreeBSD.org MIME-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 8bit X-Git-Committer: markj X-Git-Repository: src X-Git-Refname: refs/heads/stable/14 X-Git-Reftype: branch X-Git-Commit: 14d4c1845d1b03e29aa29eaccba1e9677aa13eb1 Auto-Submitted: auto-generated The branch stable/14 has been updated by markj: URL: https://cgit.FreeBSD.org/src/commit/?id=14d4c1845d1b03e29aa29eaccba1e9677aa13eb1 commit 14d4c1845d1b03e29aa29eaccba1e9677aa13eb1 Author: Mark Johnston AuthorDate: 2025-02-14 15:45:11 +0000 Commit: Mark Johnston CommitDate: 2025-03-07 22:51:48 +0000 queue: Add atomic variants for *_EMPTY In some places, these macros are used without a lock, under the assumption that they are naturally atomic. After commit 34740937f7a4 ("queue: New debug macros for STAILQ"), this assumption is false. Provide *_EMPTY_ATOMIC for such cases. This lets us include extra debug checks for the non-atomic case, and gives us a way to explicitly annotate unlocked checks, which generally deserve extra scrutiny and might otherwise raise reports from KCSAN. Reviewed by: kib, olce (previous version) MFC after: 2 weeks Differential Revision: https://reviews.freebsd.org/D48899 (cherry picked from commit d2870b8666f2438af400269c0f6a1a48031bb71e) --- share/man/man3/queue.3 | 26 +++++++++++++++++++++++++- sys/sys/queue.h | 12 ++++++++++++ 2 files changed, 37 insertions(+), 1 deletion(-) diff --git a/share/man/man3/queue.3 b/share/man/man3/queue.3 index ea395d7ffe7f..9fc57a59cf11 100644 --- a/share/man/man3/queue.3 +++ b/share/man/man3/queue.3 @@ -27,7 +27,7 @@ .\" .\" @(#)queue.3 8.2 (Berkeley) 1/24/94 .\" -.Dd April 8, 2024 +.Dd February 10, 2025 .Dt QUEUE 3 .Os .Sh NAME @@ -35,6 +35,7 @@ .Nm SLIST_CLASS_HEAD , .Nm SLIST_CONCAT , .Nm SLIST_EMPTY , +.Nm SLIST_EMPTY_ATOMIC , .Nm SLIST_ENTRY , .Nm SLIST_FIRST , .Nm SLIST_FOREACH , @@ -55,6 +56,7 @@ .Nm STAILQ_CLASS_HEAD , .Nm STAILQ_CONCAT , .Nm STAILQ_EMPTY , +.Nm STAILQ_EMPTY_ATOMIC , .Nm STAILQ_ENTRY , .Nm STAILQ_FIRST , .Nm STAILQ_FOREACH , @@ -77,6 +79,7 @@ .Nm LIST_CLASS_HEAD , .Nm LIST_CONCAT , .Nm LIST_EMPTY , +.Nm LIST_EMPTY_ATOMIC , .Nm LIST_ENTRY , .Nm LIST_FIRST , .Nm LIST_FOREACH , @@ -98,6 +101,7 @@ .Nm TAILQ_CLASS_HEAD , .Nm TAILQ_CONCAT , .Nm TAILQ_EMPTY , +.Nm TAILQ_EMPTY_ATOMIC , .Nm TAILQ_ENTRY , .Nm TAILQ_FIRST , .Nm TAILQ_FOREACH , @@ -130,6 +134,7 @@ lists and tail queues .Fn SLIST_CLASS_HEAD "HEADNAME" "CLASSTYPE" .Fn SLIST_CONCAT "SLIST_HEAD *head1" "SLIST_HEAD *head2" "TYPE" "SLIST_ENTRY NAME" .Fn SLIST_EMPTY "SLIST_HEAD *head" +.Fn SLIST_EMPTY_ATOMIC "SLIST_HEAD *head" .Fn SLIST_ENTRY "TYPE" .Fn SLIST_FIRST "SLIST_HEAD *head" .Fn SLIST_FOREACH "TYPE *var" "SLIST_HEAD *head" "SLIST_ENTRY NAME" @@ -151,6 +156,7 @@ lists and tail queues .Fn STAILQ_CLASS_HEAD "HEADNAME" "CLASSTYPE" .Fn STAILQ_CONCAT "STAILQ_HEAD *head1" "STAILQ_HEAD *head2" .Fn STAILQ_EMPTY "STAILQ_HEAD *head" +.Fn STAILQ_EMPTY_ATOMIC "STAILQ_HEAD *head" .Fn STAILQ_ENTRY "TYPE" .Fn STAILQ_FIRST "STAILQ_HEAD *head" .Fn STAILQ_FOREACH "TYPE *var" "STAILQ_HEAD *head" "STAILQ_ENTRY NAME" @@ -174,6 +180,7 @@ lists and tail queues .Fn LIST_CLASS_HEAD "HEADNAME" "CLASSTYPE" .Fn LIST_CONCAT "LIST_HEAD *head1" "LIST_HEAD *head2" "TYPE" "LIST_ENTRY NAME" .Fn LIST_EMPTY "LIST_HEAD *head" +.Fn LIST_EMPTY_ATOMIC "LIST_HEAD *head" .Fn LIST_ENTRY "TYPE" .Fn LIST_FIRST "LIST_HEAD *head" .Fn LIST_FOREACH "TYPE *var" "LIST_HEAD *head" "LIST_ENTRY NAME" @@ -196,6 +203,7 @@ lists and tail queues .Fn TAILQ_CLASS_HEAD "HEADNAME" "CLASSTYPE" .Fn TAILQ_CONCAT "TAILQ_HEAD *head1" "TAILQ_HEAD *head2" "TAILQ_ENTRY NAME" .Fn TAILQ_EMPTY "TAILQ_HEAD *head" +.Fn TAILQ_EMPTY_ATOMIC "TAILQ_HEAD *head" .Fn TAILQ_ENTRY "TYPE" .Fn TAILQ_FIRST "TAILQ_HEAD *head" .Fn TAILQ_FOREACH "TYPE *var" "TAILQ_HEAD *head" "TAILQ_ENTRY NAME" @@ -427,6 +435,10 @@ high-usage code paths or to operate on long lists. The macro .Nm SLIST_EMPTY evaluates to true if there are no elements in the list. +The +.Nm SLIST_EMPTY_ATOMIC +variant has the same behavior, but can be safely used in contexts where it is +possible that a different thread is concurrently updating the list. .Pp The macro .Nm SLIST_ENTRY @@ -635,6 +647,10 @@ removing all entries from the former. The macro .Nm STAILQ_EMPTY evaluates to true if there are no items on the tail queue. +The +.Nm STAILQ_EMPTY_ATOMIC +variant has the same behavior, but can be safely used in contexts where it is +possible that a different thread is concurrently updating the queue. .Pp The macro .Nm STAILQ_ENTRY @@ -868,6 +884,10 @@ high-usage code paths or to operate on long lists. The macro .Nm LIST_EMPTY evaluates to true if there are no elements in the list. +The +.Nm LIST_EMPTY_ATOMIC +variant has the same behavior, but can be safely used in contexts where it is +possible that a different thread is concurrently updating the list. .Pp The macro .Nm LIST_ENTRY @@ -1086,6 +1106,10 @@ removing all entries from the former. The macro .Nm TAILQ_EMPTY evaluates to true if there are no items on the tail queue. +The +.Nm TAILQ_EMPTY_ATOMIC +variant has the same behavior, but can be safely used in contexts where it is +possible that a different thread is concurrently updating the queue. .Pp The macro .Nm TAILQ_ENTRY diff --git a/sys/sys/queue.h b/sys/sys/queue.h index 38c319704cc4..dd3956d7c111 100644 --- a/sys/sys/queue.h +++ b/sys/sys/queue.h @@ -228,6 +228,9 @@ struct { \ #define SLIST_EMPTY(head) ((head)->slh_first == NULL) +#define SLIST_EMPTY_ATOMIC(head) \ + (atomic_load_ptr(&(head)->slh_first) == NULL) + #define SLIST_FIRST(head) ((head)->slh_first) #define SLIST_FOREACH(var, head, field) \ @@ -389,6 +392,9 @@ struct { \ STAILQ_FIRST(head) == NULL; \ }) +#define STAILQ_EMPTY_ATOMIC(head) \ + (atomic_load_ptr(&(head)->stqh_first) == NULL) + #define STAILQ_FIRST(head) ((head)->stqh_first) #define STAILQ_FOREACH(var, head, field) \ @@ -577,6 +583,9 @@ struct { \ #define LIST_EMPTY(head) ((head)->lh_first == NULL) +#define LIST_EMPTY_ATOMIC(head) \ + (atomic_load_ptr(&(head)->lh_first) == NULL) + #define LIST_FIRST(head) ((head)->lh_first) #define LIST_FOREACH(var, head, field) \ @@ -781,6 +790,9 @@ struct { \ #define TAILQ_EMPTY(head) ((head)->tqh_first == NULL) +#define TAILQ_EMPTY_ATOMIC(head) \ + (atomic_load_ptr(&(head)->tqh_first) == NULL) + #define TAILQ_FIRST(head) ((head)->tqh_first) #define TAILQ_FOREACH(var, head, field) \