From nobody Tue Dec 16 07:06:21 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1520982436423357.2303334050839; Tue, 13 Mar 2018 16:07:16 -0700 (PDT) Received: from localhost ([::1]:43383 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1evt0l-0004yI-HG for importer@patchew.org; Tue, 13 Mar 2018 19:07:15 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:58059) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1evsi0-0005je-OD for qemu-devel@nongnu.org; Tue, 13 Mar 2018 18:47:53 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1evshz-0003GJ-LD for qemu-devel@nongnu.org; Tue, 13 Mar 2018 18:47:52 -0400 Received: from mail-wm0-x241.google.com ([2a00:1450:400c:c09::241]:37049) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1evshz-0003FE-CY for qemu-devel@nongnu.org; Tue, 13 Mar 2018 18:47:51 -0400 Received: by mail-wm0-x241.google.com with SMTP id 139so879359wmn.2 for ; Tue, 13 Mar 2018 15:47:51 -0700 (PDT) Received: from donizetti.lan (94-36-191-219.adsl-ull.clienti.tiscali.it. [94.36.191.219]) by smtp.gmail.com with ESMTPSA id x107sm1557951wrb.97.2018.03.13.15.47.48 for (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Tue, 13 Mar 2018 15:47:48 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=sender:from:to:subject:date:message-id:in-reply-to:references; bh=i+9Wg6hajlI5XpxyCpTM/+fFSyFsebW9g9br3zICc9M=; b=jfSX4DMWnOCEyWkeia37vePbCo44LfPdlCopMf6IYkO3spuArft+XrSvE48IC5FSsW 4NbHJrmeWkPdOBaiE0PmYBoafHm7TQ/gFuhf0WHeFNJASrZVCNTsUGctV827SU8i/NS6 3LG8DIq4JZJiOQvP8JleUPX5GL8yBEyEL4gBxJqWuph//6ccBg+cbcujnOT8hXZXr/9s 78slXJa53h8fcRElIkEDRhAyqxY3EIaWIfj7PuDRFmLO7OppIeSZvl78Uac/RdZJ3Amm t0t2ib0NjgV5Kb70bndabTV9ErROHTr6wb1T38/3hPjm3bg/4VZjuPAewOxNSk3jihLy Gz9Q== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:sender:from:to:subject:date:message-id :in-reply-to:references; bh=i+9Wg6hajlI5XpxyCpTM/+fFSyFsebW9g9br3zICc9M=; b=qsO7Emvflku0/mRn9B8n0OnwZFUJfz7Fs31EFp5CPuaOm5VD/a8G16HHfB262uj08C ZQOcahrYpmVjcaSeCEozDgwoxN6fi3ClQw4i6061IE/JlxHBS6zLCw9oMQ/yj9koWiJ7 agzYmWmM4NG4G+hnw5/qdu/ctWDLwI8QEOHbE/uhagjV1CuDACYzRSO3Cn9eb5jmi6GD FQ+VvwxNyoIZxelEZSNMh66rcvlNiWC7WrmbzIzUBMXyvnuUOnvPIzYFWgrRwOnJDJ0N YdWzyx4MQY5Z2i19V2exnE4QS5TNmNL2GaaEg4hlJTKSj5X2g5/+4vddQjUQAERr0M0v zdlA== X-Gm-Message-State: AElRT7Hcj7aVU/3HclXSHAvXL/U+UIS1wrs25tsDv/nGYK558s7bjAPs g8krmj//AxysiU8nnEQViv/hooi8 X-Google-Smtp-Source: AG47ELtBD11zNPOGF+YzRKQ93DmVhSPRWb0ynDdYsR8bMCkTIeCv+mv1BV8b4xprqJwmzn3SwiNtNw== X-Received: by 10.28.51.67 with SMTP id z64mr1965426wmz.59.1520981269406; Tue, 13 Mar 2018 15:47:49 -0700 (PDT) From: Paolo Bonzini To: qemu-devel@nongnu.org Date: Tue, 13 Mar 2018 23:46:33 +0100 Message-Id: <20180313224719.4954-24-pbonzini@redhat.com> X-Mailer: git-send-email 2.14.3 In-Reply-To: <20180313224719.4954-1-pbonzini@redhat.com> References: <20180313224719.4954-1-pbonzini@redhat.com> X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2a00:1450:400c:c09::241 Subject: [Qemu-devel] [PULL 23/69] docs: document atomic_load_acquire and atomic_store_release X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZohoMail: RDKM_2 RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" We will use them in the next patch, document what they do. Signed-off-by: Paolo Bonzini --- docs/devel/atomics.txt | 57 ++++++++++++++++++++++++++--------------------= ---- 1 file changed, 30 insertions(+), 27 deletions(-) diff --git a/docs/devel/atomics.txt b/docs/devel/atomics.txt index 10c5fa37e8..a4db3a4aaa 100644 --- a/docs/devel/atomics.txt +++ b/docs/devel/atomics.txt @@ -122,20 +122,30 @@ In general, if the algorithm you are writing includes= both writes and reads on the same side, it is generally simpler to use sequentially consistent primitives. =20 -When using this model, variables are accessed with atomic_read() and -atomic_set(), and restrictions to the ordering of accesses is enforced +When using this model, variables are accessed with: + +- atomic_read() and atomic_set(); these prevent the compiler from + optimizing accesses out of existence and creating unsolicited + accesses, but do not otherwise impose any ordering on loads and + stores: both the compiler and the processor are free to reorder + them. + +- atomic_load_acquire(), which guarantees the LOAD to appear to + happen, with respect to the other components of the system, + before all the LOAD or STORE operations specified afterwards. + Operations coming before atomic_load_acquire() can still be + reordered after it. + +- atomic_store_release(), which guarantees the STORE to appear to + happen, with respect to the other components of the system, + after all the LOAD or STORE operations specified afterwards. + Operations coming after atomic_store_release() can still be + reordered after it. + +Restrictions to the ordering of accesses can also be specified using the memory barrier macros: smp_rmb(), smp_wmb(), smp_mb(), smp_mb_acquire(), smp_mb_release(), smp_read_barrier_depends(). =20 -atomic_read() and atomic_set() prevents the compiler from using -optimizations that might otherwise optimize accesses out of existence -on the one hand, or that might create unsolicited accesses on the other. -In general this should not have any effect, because the same compiler -barriers are already implied by memory barriers. However, it is useful -to do so, because it tells readers which variables are shared with -other threads, and which are local to the current thread or protected -by other, more mundane means. - Memory barriers control the order of references to shared memory. They come in six kinds: =20 @@ -232,7 +242,7 @@ make atomic_mb_set() the more expensive operation. =20 There are two common cases in which atomic_mb_read and atomic_mb_set generate too many memory barriers, and thus it can be useful to manually -place barriers instead: +place barriers, or use atomic_load_acquire/atomic_store_release instead: =20 - when a data structure has one thread that is always a writer and one thread that is always a reader, manual placement of @@ -243,18 +253,15 @@ place barriers instead: thread 1 thread 1 ------------------------- ------------------------ (other writes) - smp_mb_release() - atomic_mb_set(&a, x) atomic_set(&a, x) - smp_wmb() - atomic_mb_set(&b, y) atomic_set(&b, y) + atomic_mb_set(&a, x) atomic_store_release(&a, x) + atomic_mb_set(&b, y) atomic_store_release(&b, y) =20 =3D> thread 2 thread 2 ------------------------- ------------------------ - y =3D atomic_mb_read(&b) y =3D atomic_read(&b) - smp_rmb() - x =3D atomic_mb_read(&a) x =3D atomic_read(&a) - smp_mb_acquire() + y =3D atomic_mb_read(&b) y =3D atomic_load_acquire(&= b) + x =3D atomic_mb_read(&a) x =3D atomic_load_acquire(&= a) + (other reads) =20 Note that the barrier between the stores in thread 1, and between the loads in thread 2, has been optimized here to a write or a @@ -276,7 +283,6 @@ place barriers instead: smp_mb_acquire(); =20 Similarly, atomic_mb_set() can be transformed as follows: - smp_mb(): =20 smp_mb_release(); for (i =3D 0; i < 10; i++) =3D> for (i =3D 0; i < 10; i++) @@ -284,6 +290,8 @@ place barriers instead: smp_mb(); =20 =20 + The other thread can still use atomic_mb_read()/atomic_mb_set(). + The two tricks can be combined. In this case, splitting a loop in two lets you hoist the barriers out of the loops _and_ eliminate the expensive smp_mb(): @@ -296,8 +304,6 @@ expensive smp_mb(): atomic_set(&a[i], false); smp_mb(); =20 - The other thread can still use atomic_mb_read()/atomic_mb_set() - =20 Memory barrier pairing ---------------------- @@ -386,10 +392,7 @@ and memory barriers, and the equivalents in QEMU: note that smp_store_mb() is a little weaker than atomic_mb_set(). atomic_mb_read() compiles to the same instructions as Linux's smp_load_acquire(), but this should be treated as an implementation - detail. QEMU does have atomic_load_acquire() and atomic_store_release() - macros, but for now they are only used within atomic.h. This may - change in the future. - + detail. =20 SOURCES =3D=3D=3D=3D=3D=3D=3D --=20 2.14.3