Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

locking/seqlock: Split out seqlock_types.h

Trimming down sched.h dependencies: we don't want to include more than
the base types.

Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Ingo Molnar <mingo@redhat.com>
Cc: Will Deacon <will@kernel.org>
Cc: Waiman Long <longman@redhat.com>
Cc: Boqun Feng <boqun.feng@gmail.com>
Signed-off-by: Kent Overstreet <kent.overstreet@linux.dev>

+96 -78
+1 -1
include/linux/sched.h
··· 33 33 #include <linux/task_io_accounting.h> 34 34 #include <linux/posix-timers_types.h> 35 35 #include <linux/rseq.h> 36 - #include <linux/seqlock.h> 36 + #include <linux/seqlock_types.h> 37 37 #include <linux/kcsan.h> 38 38 #include <linux/rv.h> 39 39 #include <linux/livepatch_sched.h>
+2 -77
include/linux/seqlock.h
··· 18 18 #include <linux/lockdep.h> 19 19 #include <linux/mutex.h> 20 20 #include <linux/preempt.h> 21 + #include <linux/seqlock_types.h> 21 22 #include <linux/spinlock.h> 22 23 23 24 #include <asm/processor.h> ··· 37 36 * is not affected. 38 37 */ 39 38 #define KCSAN_SEQLOCK_REGION_MAX 1000 40 - 41 - /* 42 - * Sequence counters (seqcount_t) 43 - * 44 - * This is the raw counting mechanism, without any writer protection. 45 - * 46 - * Write side critical sections must be serialized and non-preemptible. 47 - * 48 - * If readers can be invoked from hardirq or softirq contexts, 49 - * interrupts or bottom halves must also be respectively disabled before 50 - * entering the write section. 51 - * 52 - * This mechanism can't be used if the protected data contains pointers, 53 - * as the writer can invalidate a pointer that a reader is following. 54 - * 55 - * If the write serialization mechanism is one of the common kernel 56 - * locking primitives, use a sequence counter with associated lock 57 - * (seqcount_LOCKNAME_t) instead. 58 - * 59 - * If it's desired to automatically handle the sequence counter writer 60 - * serialization and non-preemptibility requirements, use a sequential 61 - * lock (seqlock_t) instead. 62 - * 63 - * See Documentation/locking/seqlock.rst 64 - */ 65 - typedef struct seqcount { 66 - unsigned sequence; 67 - #ifdef CONFIG_DEBUG_LOCK_ALLOC 68 - struct lockdep_map dep_map; 69 - #endif 70 - } seqcount_t; 71 39 72 40 static inline void __seqcount_init(seqcount_t *s, const char *name, 73 41 struct lock_class_key *key) ··· 102 132 */ 103 133 104 134 /* 105 - * For PREEMPT_RT, seqcount_LOCKNAME_t write side critical sections cannot 106 - * disable preemption. It can lead to higher latencies, and the write side 107 - * sections will not be able to acquire locks which become sleeping locks 108 - * (e.g. spinlock_t). 109 - * 110 - * To remain preemptible while avoiding a possible livelock caused by the 111 - * reader preempting the writer, use a different technique: let the reader 112 - * detect if a seqcount_LOCKNAME_t writer is in progress. If that is the 113 - * case, acquire then release the associated LOCKNAME writer serialization 114 - * lock. This will allow any possibly-preempted writer to make progress 115 - * until the end of its writer serialization lock critical section. 116 - * 117 - * This lock-unlock technique must be implemented for all of PREEMPT_RT 118 - * sleeping locks. See Documentation/locking/locktypes.rst 119 - */ 120 - #if defined(CONFIG_LOCKDEP) || defined(CONFIG_PREEMPT_RT) 121 - #define __SEQ_LOCK(expr) expr 122 - #else 123 - #define __SEQ_LOCK(expr) 124 - #endif 125 - 126 - /* 127 135 * typedef seqcount_LOCKNAME_t - sequence counter with LOCKNAME associated 128 136 * @seqcount: The real sequence counter 129 137 * @lock: Pointer to the associated lock ··· 142 194 * @lockbase: prefix for associated lock/unlock 143 195 */ 144 196 #define SEQCOUNT_LOCKNAME(lockname, locktype, preemptible, lockbase) \ 145 - typedef struct seqcount_##lockname { \ 146 - seqcount_t seqcount; \ 147 - __SEQ_LOCK(locktype *lock); \ 148 - } seqcount_##lockname##_t; \ 149 - \ 150 197 static __always_inline seqcount_t * \ 151 198 __seqprop_##lockname##_ptr(seqcount_##lockname##_t *s) \ 152 199 { \ ··· 227 284 SEQCOUNT_LOCKNAME(spinlock, spinlock_t, __SEQ_RT, spin) 228 285 SEQCOUNT_LOCKNAME(rwlock, rwlock_t, __SEQ_RT, read) 229 286 SEQCOUNT_LOCKNAME(mutex, struct mutex, true, mutex) 287 + #undef SEQCOUNT_LOCKNAME 230 288 231 289 /* 232 290 * SEQCNT_LOCKNAME_ZERO - static initializer for seqcount_LOCKNAME_t ··· 737 793 s->seqcount.sequence++; 738 794 smp_wmb(); /* increment "sequence" before following stores */ 739 795 } 740 - 741 - /* 742 - * Sequential locks (seqlock_t) 743 - * 744 - * Sequence counters with an embedded spinlock for writer serialization 745 - * and non-preemptibility. 746 - * 747 - * For more info, see: 748 - * - Comments on top of seqcount_t 749 - * - Documentation/locking/seqlock.rst 750 - */ 751 - typedef struct { 752 - /* 753 - * Make sure that readers don't starve writers on PREEMPT_RT: use 754 - * seqcount_spinlock_t instead of seqcount_t. Check __SEQ_LOCK(). 755 - */ 756 - seqcount_spinlock_t seqcount; 757 - spinlock_t lock; 758 - } seqlock_t; 759 796 760 797 #define __SEQLOCK_UNLOCKED(lockname) \ 761 798 { \
+93
include/linux/seqlock_types.h
··· 1 + /* SPDX-License-Identifier: GPL-2.0 */ 2 + #ifndef __LINUX_SEQLOCK_TYPES_H 3 + #define __LINUX_SEQLOCK_TYPES_H 4 + 5 + #include <linux/lockdep_types.h> 6 + #include <linux/mutex_types.h> 7 + #include <linux/spinlock_types.h> 8 + 9 + /* 10 + * Sequence counters (seqcount_t) 11 + * 12 + * This is the raw counting mechanism, without any writer protection. 13 + * 14 + * Write side critical sections must be serialized and non-preemptible. 15 + * 16 + * If readers can be invoked from hardirq or softirq contexts, 17 + * interrupts or bottom halves must also be respectively disabled before 18 + * entering the write section. 19 + * 20 + * This mechanism can't be used if the protected data contains pointers, 21 + * as the writer can invalidate a pointer that a reader is following. 22 + * 23 + * If the write serialization mechanism is one of the common kernel 24 + * locking primitives, use a sequence counter with associated lock 25 + * (seqcount_LOCKNAME_t) instead. 26 + * 27 + * If it's desired to automatically handle the sequence counter writer 28 + * serialization and non-preemptibility requirements, use a sequential 29 + * lock (seqlock_t) instead. 30 + * 31 + * See Documentation/locking/seqlock.rst 32 + */ 33 + typedef struct seqcount { 34 + unsigned sequence; 35 + #ifdef CONFIG_DEBUG_LOCK_ALLOC 36 + struct lockdep_map dep_map; 37 + #endif 38 + } seqcount_t; 39 + 40 + /* 41 + * For PREEMPT_RT, seqcount_LOCKNAME_t write side critical sections cannot 42 + * disable preemption. It can lead to higher latencies, and the write side 43 + * sections will not be able to acquire locks which become sleeping locks 44 + * (e.g. spinlock_t). 45 + * 46 + * To remain preemptible while avoiding a possible livelock caused by the 47 + * reader preempting the writer, use a different technique: let the reader 48 + * detect if a seqcount_LOCKNAME_t writer is in progress. If that is the 49 + * case, acquire then release the associated LOCKNAME writer serialization 50 + * lock. This will allow any possibly-preempted writer to make progress 51 + * until the end of its writer serialization lock critical section. 52 + * 53 + * This lock-unlock technique must be implemented for all of PREEMPT_RT 54 + * sleeping locks. See Documentation/locking/locktypes.rst 55 + */ 56 + #if defined(CONFIG_LOCKDEP) || defined(CONFIG_PREEMPT_RT) 57 + #define __SEQ_LOCK(expr) expr 58 + #else 59 + #define __SEQ_LOCK(expr) 60 + #endif 61 + 62 + #define SEQCOUNT_LOCKNAME(lockname, locktype, preemptible, lockbase) \ 63 + typedef struct seqcount_##lockname { \ 64 + seqcount_t seqcount; \ 65 + __SEQ_LOCK(locktype *lock); \ 66 + } seqcount_##lockname##_t; 67 + 68 + SEQCOUNT_LOCKNAME(raw_spinlock, raw_spinlock_t, false, raw_spin) 69 + SEQCOUNT_LOCKNAME(spinlock, spinlock_t, __SEQ_RT, spin) 70 + SEQCOUNT_LOCKNAME(rwlock, rwlock_t, __SEQ_RT, read) 71 + SEQCOUNT_LOCKNAME(mutex, struct mutex, true, mutex) 72 + #undef SEQCOUNT_LOCKNAME 73 + 74 + /* 75 + * Sequential locks (seqlock_t) 76 + * 77 + * Sequence counters with an embedded spinlock for writer serialization 78 + * and non-preemptibility. 79 + * 80 + * For more info, see: 81 + * - Comments on top of seqcount_t 82 + * - Documentation/locking/seqlock.rst 83 + */ 84 + typedef struct { 85 + /* 86 + * Make sure that readers don't starve writers on PREEMPT_RT: use 87 + * seqcount_spinlock_t instead of seqcount_t. Check __SEQ_LOCK(). 88 + */ 89 + seqcount_spinlock_t seqcount; 90 + spinlock_t lock; 91 + } seqlock_t; 92 + 93 + #endif /* __LINUX_SEQLOCK_TYPES_H */