master
h 143 lines 7.24 KB
Raw
1 // SPDX-License-Identifier: GPL-3.0-or-later
2
3 #ifndef NETDATA_LOCKS_H
4 #define NETDATA_LOCKS_H 1
5
6 #include "../libnetdata.h"
7 #include "../clocks/clocks.h"
8
9 // #ifdef OS_WINDOWS
10 // #define SPINLOCK_IMPL_WITH_MUTEX
11 // #endif
12
13 typedef uv_mutex_t netdata_mutex_t;
14 typedef uv_cond_t netdata_cond_t;
15
16 #ifdef NETDATA_TRACE_RWLOCKS
17
18 typedef enum {
19 RWLOCK_REQUEST_READ = (1 << 0),
20 RWLOCK_REQUEST_WRITE = (1 << 1),
21 RWLOCK_REQUEST_TRYREAD = (1 << 2),
22 RWLOCK_REQUEST_TRYWRITE = (1 << 3),
23 } LOCKER_REQUEST;
24
25 typedef struct netdata_rwlock_locker {
26 LOCKER_REQUEST lock;
27 bool got_it;
28 pid_t pid;
29 size_t refcount;
30 const char *tag;
31 const char *file;
32 const char *function;
33 unsigned long line;
34 struct netdata_rwlock_locker *next, *prev;
35 } netdata_rwlock_locker;
36
37 typedef struct netdata_rwlock_t {
38 uv_rwlock_t rwlock_t; // the lock
39 size_t readers; // the number of reader on the lock
40 size_t writers; // the number of writers on the lock
41 netdata_mutex_t lockers_mutex; // a mutex to protect the linked list of the lock holding threads
42 netdata_rwlock_locker *lockers; // the linked list of the lock holding threads
43 Pvoid_t lockers_pid_JudyL;
44 } netdata_rwlock_t;
45
46 #define NETDATA_RWLOCK_INITIALIZER { \
47 .rwlock_t = PTHREAD_RWLOCK_INITIALIZER, \
48 .readers = 0, \
49 .writers = 0, \
50 .lockers_mutex = NETDATA_MUTEX_INITIALIZER, \
51 .lockers = NULL, \
52 .lockers_pid_JudyL = NULL, \
53 }
54
55 #else // NETDATA_TRACE_RWLOCKS
56
57 typedef struct netdata_rwlock_t {
58 uv_rwlock_t rwlock_t;
59 } netdata_rwlock_t;
60
61 #endif // NETDATA_TRACE_RWLOCKS
62
63 int __netdata_cond_init(netdata_cond_t *cond);
64 void __netdata_cond_destroy(netdata_cond_t *cond);
65 void __netdata_cond_signal(netdata_cond_t *cond);
66 void __netdata_cond_wait(netdata_cond_t *cond, netdata_mutex_t *mutex);
67 int __netdata_cond_timedwait(netdata_cond_t *cond, netdata_mutex_t *mutex, uint64_t timeout_ns);
68
69 int __netdata_mutex_init(netdata_mutex_t *mutex);
70 void __netdata_mutex_destroy(netdata_mutex_t *mutex);
71 void __netdata_mutex_lock(netdata_mutex_t *mutex);
72 int __netdata_mutex_trylock(netdata_mutex_t *mutex);
73 void __netdata_mutex_unlock(netdata_mutex_t *mutex);
74
75 void __netdata_rwlock_destroy(netdata_rwlock_t *rwlock);
76 int __netdata_rwlock_init(netdata_rwlock_t *rwlock);
77 void __netdata_rwlock_rdlock(netdata_rwlock_t *rwlock);
78 void __netdata_rwlock_wrlock(netdata_rwlock_t *rwlock);
79 void __netdata_rwlock_rdunlock(netdata_rwlock_t *rwlock);
80 void __netdata_rwlock_wrunlock(netdata_rwlock_t *rwlock);
81 int __netdata_rwlock_tryrdlock(netdata_rwlock_t *rwlock);
82 int __netdata_rwlock_trywrlock(netdata_rwlock_t *rwlock);
83 void __netdata_cond_broadcast(netdata_cond_t *cond);
84
85 #ifdef NETDATA_TRACE_RWLOCKS
86
87 int netdata_mutex_init_debug( const char *file, const char *function, const unsigned long line, netdata_mutex_t *mutex);
88 int netdata_mutex_destroy_debug( const char *file, const char *function, const unsigned long line, netdata_mutex_t *mutex);
89 int netdata_mutex_lock_debug( const char *file, const char *function, const unsigned long line, netdata_mutex_t *mutex);
90 int netdata_mutex_trylock_debug( const char *file, const char *function, const unsigned long line, netdata_mutex_t *mutex);
91 int netdata_mutex_unlock_debug( const char *file, const char *function, const unsigned long line, netdata_mutex_t *mutex);
92
93 int netdata_rwlock_destroy_debug( const char *file, const char *function, const unsigned long line, netdata_rwlock_t *rwlock);
94 int netdata_rwlock_init_debug( const char *file, const char *function, const unsigned long line, netdata_rwlock_t *rwlock);
95 int netdata_rwlock_rdlock_debug( const char *file, const char *function, const unsigned long line, netdata_rwlock_t *rwlock);
96 int netdata_rwlock_wrlock_debug( const char *file, const char *function, const unsigned long line, netdata_rwlock_t *rwlock);
97 int netdata_rwlock_rdunlock_debug( const char *file, const char *function, const unsigned long line, netdata_rwlock_t *rwlock);
98 int netdata_rwlock_wrunlock_debug( const char *file, const char *function, const unsigned long line, netdata_rwlock_t *rwlock);
99 int netdata_rwlock_tryrdlock_debug( const char *file, const char *function, const unsigned long line, netdata_rwlock_t *rwlock);
100 int netdata_rwlock_trywrlock_debug( const char *file, const char *function, const unsigned long line, netdata_rwlock_t *rwlock);
101
102 #define netdata_mutex_init(mutex) netdata_mutex_init_debug(__FILE__, __FUNCTION__, __LINE__, mutex)
103 #define netdata_mutex_destroy(mutex) netdata_mutex_destroy_debug(__FILE__, __FUNCTION__, __LINE__, mutex)
104 #define netdata_mutex_lock(mutex) netdata_mutex_lock_debug(__FILE__, __FUNCTION__, __LINE__, mutex)
105 #define netdata_mutex_trylock(mutex) netdata_mutex_trylock_debug(__FILE__, __FUNCTION__, __LINE__, mutex)
106 #define netdata_mutex_unlock(mutex) netdata_mutex_unlock_debug(__FILE__, __FUNCTION__, __LINE__, mutex)
107
108 #define netdata_rwlock_destroy(rwlock) netdata_rwlock_destroy_debug(__FILE__, __FUNCTION__, __LINE__, rwlock)
109 #define netdata_rwlock_init(rwlock) netdata_rwlock_init_debug(__FILE__, __FUNCTION__, __LINE__, rwlock)
110 #define netdata_rwlock_rdlock(rwlock) netdata_rwlock_rdlock_debug(__FILE__, __FUNCTION__, __LINE__, rwlock)
111 #define netdata_rwlock_wrlock(rwlock) netdata_rwlock_wrlock_debug(__FILE__, __FUNCTION__, __LINE__, rwlock)
112 #define netdata_rwlock_rdunlock(rwlock) netdata_rwlock_rdunlock_debug(__FILE__, __FUNCTION__, __LINE__, rwlock)
113 #define netdata_rwlock_wrunlock(rwlock) netdata_rwlock_wrunlock_debug(__FILE__, __FUNCTION__, __LINE__, rwlock)
114 #define netdata_rwlock_tryrdlock(rwlock) netdata_rwlock_tryrdlock_debug(__FILE__, __FUNCTION__, __LINE__, rwlock)
115 #define netdata_rwlock_trywrlock(rwlock) netdata_rwlock_trywrlock_debug(__FILE__, __FUNCTION__, __LINE__, rwlock)
116
117 #else // !NETDATA_TRACE_RWLOCKS
118
119 #define netdata_mutex_init(mutex) __netdata_mutex_init(mutex)
120 #define netdata_mutex_destroy(mutex) __netdata_mutex_destroy(mutex)
121 #define netdata_mutex_lock(mutex) __netdata_mutex_lock(mutex)
122 #define netdata_mutex_trylock(mutex) __netdata_mutex_trylock(mutex)
123 #define netdata_mutex_unlock(mutex) __netdata_mutex_unlock(mutex)
124
125 #define netdata_rwlock_destroy(rwlock) __netdata_rwlock_destroy(rwlock)
126 #define netdata_rwlock_init(rwlock) __netdata_rwlock_init(rwlock)
127 #define netdata_rwlock_rdlock(rwlock) __netdata_rwlock_rdlock(rwlock)
128 #define netdata_rwlock_wrlock(rwlock) __netdata_rwlock_wrlock(rwlock)
129 #define netdata_rwlock_rdunlock(rwlock) __netdata_rwlock_rdunlock(rwlock)
130 #define netdata_rwlock_wrunlock(rwlock) __netdata_rwlock_wrunlock(rwlock)
131 #define netdata_rwlock_tryrdlock(rwlock) __netdata_rwlock_tryrdlock(rwlock)
132 #define netdata_rwlock_trywrlock(rwlock) __netdata_rwlock_trywrlock(rwlock)
133
134 #endif // NETDATA_TRACE_RWLOCKS
135
136 #define netdata_cond_init(cond) __netdata_cond_init(cond)
137 #define netdata_cond_destroy(cond) __netdata_cond_destroy(cond)
138 #define netdata_cond_signal(cond) __netdata_cond_signal(cond)
139 #define netdata_cond_broadcast(cond) __netdata_cond_broadcast(cond)
140 #define netdata_cond_wait(cond, mutex) __netdata_cond_wait(cond, mutex)
141 #define netdata_cond_timedwait(cond, mutex, tp) __netdata_cond_timedwait(cond, mutex, tp)
142
143 #endif //NETDATA_LOCKS_H