StarPU Internal Handbook
starpu_spinlock.h
Go to the documentation of this file.
1 /* StarPU --- Runtime system for heterogeneous multicore architectures.
2  *
3  * Copyright (C) 2009-2021 Université de Bordeaux, CNRS (LaBRI UMR 5800), Inria
4  *
5  * StarPU is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU Lesser General Public License as published by
7  * the Free Software Foundation; either version 2.1 of the License, or (at
8  * your option) any later version.
9  *
10  * StarPU is distributed in the hope that it will be useful, but
11  * WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
13  *
14  * See the GNU Lesser General Public License in COPYING.LGPL for more details.
15  */
16 #ifndef __STARPU_SPINLOCK_H__
17 #define __STARPU_SPINLOCK_H__
18 
21 #include <errno.h>
22 #include <stdint.h>
23 #include <common/config.h>
24 #include <common/fxt.h>
25 #include <common/thread.h>
26 #include <starpu.h>
27 
28 #ifdef STARPU_SPINLOCK_CHECK
29 
30 /* We don't care about performance */
31 
32 struct _starpu_spinlock
33 {
34  starpu_pthread_mutex_t errcheck_lock;
35  const char *last_taker;
36 };
37 
38 int _starpu_spin_init(struct _starpu_spinlock *lock);
39 int _starpu_spin_destroy(struct _starpu_spinlock *lock);
40 
41 static inline int __starpu_spin_lock(struct _starpu_spinlock *lock, const char *file STARPU_ATTRIBUTE_UNUSED, int line STARPU_ATTRIBUTE_UNUSED, const char *func STARPU_ATTRIBUTE_UNUSED)
42 {
43  _STARPU_TRACE_LOCKING_SPINLOCK(file, line);
44  int ret = starpu_pthread_mutex_lock(&lock->errcheck_lock);
45  STARPU_ASSERT(!ret);
46  lock->last_taker = func;
47  _STARPU_TRACE_SPINLOCK_LOCKED(file, line);
48  return ret;
49 }
50 
51 static inline void _starpu_spin_checklocked(struct _starpu_spinlock *lock STARPU_ATTRIBUTE_UNUSED)
52 {
53  STARPU_ASSERT(starpu_pthread_mutex_trylock(&lock->errcheck_lock) != 0);
54 }
55 
56 static inline int __starpu_spin_trylock(struct _starpu_spinlock *lock, const char *file STARPU_ATTRIBUTE_UNUSED, int line STARPU_ATTRIBUTE_UNUSED, const char *func STARPU_ATTRIBUTE_UNUSED)
57 {
58  _STARPU_TRACE_TRYLOCK_SPINLOCK(file, line);
59  int ret = starpu_pthread_mutex_trylock(&lock->errcheck_lock);
60  STARPU_ASSERT(!ret || (ret == EBUSY));
61  if (STARPU_LIKELY(!ret))
62  {
63  lock->last_taker = func;
64  _STARPU_TRACE_SPINLOCK_LOCKED(file, line);
65  }
66  return ret;
67 }
68 
69 static inline int __starpu_spin_unlock(struct _starpu_spinlock *lock, const char *file STARPU_ATTRIBUTE_UNUSED, int line STARPU_ATTRIBUTE_UNUSED, const char *func STARPU_ATTRIBUTE_UNUSED)
70 {
71  _STARPU_TRACE_UNLOCKING_SPINLOCK(file, line);
72  int ret = starpu_pthread_mutex_unlock(&lock->errcheck_lock);
73  STARPU_ASSERT(!ret);
74  _STARPU_TRACE_SPINLOCK_UNLOCKED(file, line);
75  return ret;
76 }
77 #else
78 
79 /* We do care about performance, inline as much as possible */
80 
82 {
83  starpu_pthread_spinlock_t lock;
84 };
85 
86 static inline int _starpu_spin_init(struct _starpu_spinlock *lock)
87 {
88  int ret = starpu_pthread_spin_init(&lock->lock, 0);
89  STARPU_ASSERT(!ret);
90  return ret;
91 }
92 
93 #define _starpu_spin_destroy(_lock) starpu_pthread_spin_destroy(&(_lock)->lock)
94 
95 static inline int __starpu_spin_lock(struct _starpu_spinlock *lock, const char *file STARPU_ATTRIBUTE_UNUSED, int line STARPU_ATTRIBUTE_UNUSED, const char *func STARPU_ATTRIBUTE_UNUSED)
96 {
97  _STARPU_TRACE_LOCKING_SPINLOCK(file, line);
98  int ret = starpu_pthread_spin_lock(&lock->lock);
99  STARPU_ASSERT(!ret);
100  _STARPU_TRACE_SPINLOCK_LOCKED(file, line);
101  return ret;
102 }
103 
104 #define _starpu_spin_checklocked(_lock) _starpu_pthread_spin_checklocked(&(_lock)->lock)
105 
106 static inline int __starpu_spin_trylock(struct _starpu_spinlock *lock, const char *file STARPU_ATTRIBUTE_UNUSED, int line STARPU_ATTRIBUTE_UNUSED, const char *func STARPU_ATTRIBUTE_UNUSED)
107 {
108  _STARPU_TRACE_TRYLOCK_SPINLOCK(file, line);
109  int ret = starpu_pthread_spin_trylock(&lock->lock);
110  STARPU_ASSERT(!ret || (ret == EBUSY));
111  if (STARPU_LIKELY(!ret))
112  _STARPU_TRACE_SPINLOCK_LOCKED(file, line);
113  return ret;
114 }
115 
116 static inline int __starpu_spin_unlock(struct _starpu_spinlock *lock, const char *file STARPU_ATTRIBUTE_UNUSED, int line STARPU_ATTRIBUTE_UNUSED, const char *func STARPU_ATTRIBUTE_UNUSED)
117 {
118  _STARPU_TRACE_UNLOCKING_SPINLOCK(file, line);
119  int ret = starpu_pthread_spin_unlock(&lock->lock);
120  STARPU_ASSERT(!ret);
121  _STARPU_TRACE_SPINLOCK_UNLOCKED(file, line);
122  return ret;
123 }
124 #endif
125 
126 #define _starpu_spin_lock(lock) \
127  __starpu_spin_lock(lock, __FILE__, __LINE__, __starpu_func__)
128 #define _starpu_spin_trylock(lock) \
129  __starpu_spin_trylock(lock, __FILE__, __LINE__, __starpu_func__)
130 #define _starpu_spin_unlock(lock) \
131  __starpu_spin_unlock(lock, __FILE__, __LINE__, __starpu_func__)
132 
133 #define STARPU_SPIN_MAXTRY 10
134 
135 #endif // __STARPU_SPINLOCK_H__
Definition: starpu_spinlock.h:82