4 * Userspace RCU - annotation header.
6 * Copyright 2023 - Olivier Dion <odion@efficios.com>
8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public
10 * License as published by the Free Software Foundation; either
11 * version 2.1 of the License, or (at your option) any later version.
13 * This library is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Lesser General Public License for more details.
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with this library; if not, write to the Free Software
20 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
26 * This API is highly experimental. There is zero guarantees of stability
29 * You have been warned.
31 #ifndef _URCU_ANNOTATE_H
32 #define _URCU_ANNOTATE_H
37 #include <urcu/compiler.h>
46 typedef enum cmm_annotate cmm_annotate_t
__attribute__((unused
));
48 #define cmm_annotate_define(name) \
49 cmm_annotate_t name = CMM_ANNOTATE_VOID
51 #ifdef CMM_SANITIZE_THREAD
56 extern void __tsan_acquire(void *);
57 extern void __tsan_release(void *);
62 # define cmm_annotate_die(msg) \
65 "(" __FILE__ ":%s@%u) Annotation ERROR: %s\n", \
66 __func__, __LINE__, msg); \
70 /* Only used for typechecking in macros. */
71 static inline cmm_annotate_t
cmm_annotate_dereference(cmm_annotate_t
*group
)
76 # define cmm_annotate_group_mb_acquire(group) \
78 switch (cmm_annotate_dereference(group)) { \
79 case CMM_ANNOTATE_VOID: \
81 case CMM_ANNOTATE_LOAD: \
83 case CMM_ANNOTATE_STORE: \
84 cmm_annotate_die("store for acquire group"); \
86 case CMM_ANNOTATE_MB: \
88 "redundant mb for acquire group" \
92 *(group) = CMM_ANNOTATE_MB; \
95 # define cmm_annotate_group_mb_release(group) \
97 switch (cmm_annotate_dereference(group)) { \
98 case CMM_ANNOTATE_VOID: \
100 case CMM_ANNOTATE_LOAD: \
101 cmm_annotate_die("load before release group"); \
103 case CMM_ANNOTATE_STORE: \
105 "store before release group" \
108 case CMM_ANNOTATE_MB: \
110 "redundant mb of release group" \
114 *(group) = CMM_ANNOTATE_MB; \
117 # define cmm_annotate_group_mem_acquire(group, mem) \
119 __tsan_acquire((void*)(mem)); \
120 switch (cmm_annotate_dereference(group)) { \
121 case CMM_ANNOTATE_VOID: \
122 *(group) = CMM_ANNOTATE_LOAD; \
124 case CMM_ANNOTATE_MB: \
126 "load after mb for acquire group" \
134 # define cmm_annotate_group_mem_release(group, mem) \
136 __tsan_release((void*)(mem)); \
137 switch (cmm_annotate_dereference(group)) { \
138 case CMM_ANNOTATE_MB: \
142 "missing mb for release group" \
147 # define cmm_annotate_mem_acquire(mem) \
148 __tsan_acquire((void*)(mem))
150 # define cmm_annotate_mem_release(mem) \
151 __tsan_release((void*)(mem))
154 # define cmm_annotate_group_mb_acquire(group) \
157 # define cmm_annotate_group_mb_release(group) \
160 # define cmm_annotate_group_mem_acquire(group, mem) \
163 # define cmm_annotate_group_mem_release(group, mem) \
166 # define cmm_annotate_mem_acquire(mem) \
169 # define cmm_annotate_mem_release(mem) \
172 #endif /* CMM_SANITIZE_THREAD */
174 #endif /* _URCU_ANNOTATE_H */