Ignore:
Timestamp:
Oct 4, 2018, 11:16:13 PM (3 years ago)
Author:
alain
Message:

Complete restructuration of kernel spinlocks.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/kernel/libk/rwlock.h

    r457 r563  
    11/*
    2  * rwlock.h - kernel read/write lock definition.
     2 * rwlock.h - kernel local read/write lock definition.
    33 *
    44 * Author   Alain Greiner    (2016,2017,2018)
     
    2727#include <kernel_config.h>
    2828#include <hal_kernel_types.h>
     29#include <busylock.h>
    2930#include <list.h>
    3031
    31 /*******************************************************************************************
    32  * This structure defines a local rwlock, that supports several simultaneous read
    33  * accesses, but only one write access. It implements a ticket based allocation policy.
    34  * Both readers and writers must take a ticket before doing anything else, and access
    35  * are done in same order as requests (for both read an write ).
    36  * - A reader take the lock to atomically increments the registered readers count.
    37  *   Then it release the lock and access the protected structure. It atomically decrement
    38  *   the readers count without taking the lock when access is completed.
    39  * - A writer take the lock and keep it, but must wait completion of all current read
    40  *   accesses before starting its own access.
    41  * As this local lock is only accessed by the local threads, if the lock is taken,
    42  * the new-comers use a busy waiting policy with a delay between retry.
    43  * TODO : Introduce the rwlocks in the list of locks taken by a given thread for debug.
     32/******************************************************************************************n
     33 * This structure defines a kernel, local, read/write lock, supporting several simultaneous
     34 * read accesses, but only one write access to a given locally shared object in a cluster.
     35 * Both readers and writers take the associated busylock before accessing or updating
     36 * the rwlock state, and releases the busylock after rwlock state update.
     37 * - when a reader try to access the object, it increments the readers "count" when the
     38 *   lock is not "taken" by a writer. It registers in the "rd_root" waiting queue, blocks,
     39 *   and deschedules when the lock is taken.
     40 * - when a writer try to take the rwlock, it check the "taken" field. If the lock is already
     41 *   taken, or if the number of readers is non zero, it registers in the "wr_root" waiting
     42 *   queue, blocks, and deschedules. It set "taken" otherwise.
     43 * - when a reader completes its access, it decrement the readers "count", unblock the
     44 *   the first waiting writer if there is no other readers, and unblock all waiting
     45 *   readers if there no write request.
     46 * - when a  writer completes its access, it reset the "taken" field, releases the first
     47 *   waiting writer if queue non empty, or releases all waiting readers if no writer.
    4448 ******************************************************************************************/
    45 
    46 /****     Forward declarations    ****/
    47 
    48 struct thread_s;
    4949
    5050/*******************************************************************************************
    5151 * This structure defines a local rwlock.
    52  * The "owner" and "list" fields are used for debug.
    5352 ******************************************************************************************/
    5453
    5554typedef struct rwlock_s
    5655{
    57         uint32_t            ticket;           /*! first free ticket index                     */
    58     uint32_t            current;          /*! ticket index of current owner               */
    59     uint32_t            count;            /*! number of simultaneous readers threads      */
    60 
    61 #if DEBUG_RWLOCKS
    62         struct thread_s   * owner;            /*! pointer on curent writer thread             */
    63     list_entry_t        list;             /*! member of list of locks taken by owner      */
    64 #endif
    65 
     56    busylock_t          lock;        /*! busylock protecting the rwlock state             */
     57        volatile uint32_t   taken;       /*! lock taken by an exclusive writer if non zero    */
     58    volatile uint32_t   count;       /*! current number of simultaneous readers threads   */
     59    list_entry_t        rd_root;     /*! root of list of waiting readers                  */
     60    list_entry_t        wr_root;     /*! root of list of waiting writers                  */
    6661}
    6762rwlock_t;
     
    6964/*******************************************************************************************
    7065 * This function initializes a local rwlock.
     66 * The <type> argument defines the lock usage and is only used for debug.
     67 * This type is actually stored in the associated busylock descriptor.
    7168 *******************************************************************************************
    72  * @ lock       : pointer on rwlock
     69 * @ lock       : pointer on rwlock.
     70 * @ type       : lock usage for debug.
    7371 ******************************************************************************************/
    74 void rwlock_init( rwlock_t * lock );
     72void rwlock_init( rwlock_t * lock,
     73                  uint32_t   type );
    7574
    7675/*******************************************************************************************
     
    7978 * @ lock       : pointer on rwlock
    8079 ******************************************************************************************/
    81 void rwlock_rd_lock( rwlock_t * lock );
     80void rwlock_rd_acquire( rwlock_t * lock );
    8281
    8382/*******************************************************************************************
     
    8685 * @ lock       : pointer on rwlock
    8786 ******************************************************************************************/
    88 void rwlock_wr_lock( rwlock_t * lock );
     87void rwlock_wr_acquire( rwlock_t * lock );
    8988
    9089/*******************************************************************************************
     
    9392 * @ lock       : pointer on rwlock
    9493 ******************************************************************************************/
    95 void rwlock_rd_unlock( rwlock_t * lock );
     94void rwlock_rd_release( rwlock_t * lock );
    9695
    9796/*******************************************************************************************
     
    10099 * @ lock       : pointer on rwlock
    101100 ******************************************************************************************/
    102 void rwlock_wr_unlock( rwlock_t * lock );
     101void rwlock_wr_release( rwlock_t * lock );
    103102
    104103
Note: See TracChangeset for help on using the changeset viewer.