From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 192B6A0503; Fri, 20 May 2022 08:02:11 +0200 (CEST) Received: from [217.70.189.124] (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id ECD8A40156; Fri, 20 May 2022 08:02:10 +0200 (CEST) Received: from mail.lysator.liu.se (mail.lysator.liu.se [130.236.254.3]) by mails.dpdk.org (Postfix) with ESMTP id 0B9BF40151 for ; Fri, 20 May 2022 08:02:09 +0200 (CEST) Received: from mail.lysator.liu.se (localhost [127.0.0.1]) by mail.lysator.liu.se (Postfix) with ESMTP id 472D517FF1 for ; Fri, 20 May 2022 08:02:06 +0200 (CEST) Received: by mail.lysator.liu.se (Postfix, from userid 1004) id 45AB71852A; Fri, 20 May 2022 08:02:06 +0200 (CEST) X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on hermod.lysator.liu.se X-Spam-Level: X-Spam-Status: No, score=-2.5 required=5.0 tests=ALL_TRUSTED, AWL, NICE_REPLY_A, T_SCC_BODY_TEXT_LINE autolearn=disabled version=3.4.6 X-Spam-Score: -2.5 Received: from [192.168.1.59] (unknown [62.63.215.114]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange ECDHE (P-256) server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by mail.lysator.liu.se (Postfix) with ESMTPSA id 1B73018434; Fri, 20 May 2022 08:02:04 +0200 (CEST) Message-ID: <81809953-0b3a-2070-2d7c-d7fc89d28f28@lysator.liu.se> Date: Fri, 20 May 2022 08:02:03 +0200 MIME-Version: 1.0 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:91.0) Gecko/20100101 Thunderbird/91.8.1 Subject: Re: [PATCH v7] eal: add seqlock Content-Language: en-US To: =?UTF-8?Q?Mattias_R=c3=b6nnblom?= , Thomas Monjalon , David Marchand Cc: "dev@dpdk.org" , Onar Olsen , "Honnappa.Nagarahalli@arm.com" , "nd@arm.com" , "konstantin.ananyev@intel.com" , "mb@smartsharesystems.com" , "stephen@networkplumber.org" , Chengwen Feng , Ola Liljedahl References: <20220513103820.3e34fcb9@hermes.local> <20220515122418.335929-1-mattias.ronnblom@ericsson.com> From: =?UTF-8?Q?Mattias_R=c3=b6nnblom?= In-Reply-To: Content-Type: text/plain; charset=UTF-8; format=flowed Content-Transfer-Encoding: 8bit X-Virus-Scanned: ClamAV using ClamSMTP X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org On 2022-05-15 14:39, Mattias Rönnblom wrote: > On 2022-05-15 14:24, Mattias Rönnblom wrote: >> A sequence lock (seqlock) is a synchronization primitive which allows >> for data-race free, low-overhead, high-frequency reads, suitable for >> data structures shared across many cores and which are updated >> relatively infrequently. >> >> A seqlock permits multiple parallel readers. A spinlock is used to >> serialize writers. In cases where there is only a single writer, or >> writer-writer synchronization is done by some external means, the >> "raw" sequence counter type (and accompanying rte_seqcount_*() >> functions) may be used instead. >> >> To avoid resource reclamation and other issues, the data protected by >> a seqlock is best off being self-contained (i.e., no pointers [except >> to constant data]). >> >> One way to think about seqlocks is that they provide means to perform >> atomic operations on data objects larger than what the native atomic >> machine instructions allow for. >> >> DPDK seqlocks (and the underlying sequence counters) are not >> preemption safe on the writer side. A thread preemption affects >> performance, not correctness. >> >> A seqlock contains a sequence number, which can be thought of as the >> generation of the data it protects. >> >> A reader will >> 1. Load the sequence number (sn). >> 2. Load, in arbitrary order, the seqlock-protected data. >> 3. Load the sn again. >> 4. Check if the first and second sn are equal, and even numbered. >> If they are not, discard the loaded data, and restart from 1. >> >> The first three steps need to be ordered using suitable memory fences. >> >> A writer will >> 1. Take the spinlock, to serialize writer access. >> 2. Load the sn. >> 3. Store the original sn + 1 as the new sn. >> 4. Perform load and stores to the seqlock-protected data. >> 5. Store the original sn + 2 as the new sn. >> 6. Release the spinlock. >> >> Proper memory fencing is required to make sure the first sn store, the >> data stores, and the second sn store appear to the reader in the >> mentioned order. >> >> The sn loads and stores must be atomic, but the data loads and stores >> need not be. >> >> The original seqlock design and implementation was done by Stephen >> Hemminger. This is an independent implementation, using C11 atomics. >> >> For more information on seqlocks, see >> https://en.wikipedia.org/wiki/Seqlock >> >> --- >> > > A note to previous reviewers: This split of seqlock into > seqcount+seqlock assumes that the spinlock lock/unlock calls provided no > additional functionality in regards to MT safety, than writer-writer > serialization. I believe that to be the case, but I would feel more > comfortable if someone else re-reviewed this code with this in mind. > > Two questions remain: > > 1) Should the seqlock and the seqcount reside in different header files? Since I received no comments on this, I'll go ahead and make a v8, where the seqcount and seqlock structs and functions are in different header files. > 2) Is it it good enough to provided only a spinlock-protected seqlock? > > Question 1 I don't really have an opinion on. Both ways seems perfectly > reasonable to me. I noted Morten wanted a split, and left to my own > devices this is probably what I would do as well. > > I think the answer to 2 is yes. We can provide other variants in the > future, would the need arise. > > >