1 // Copyright 2017 The Fuchsia Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #pragma once
6 
7 // This header defines thread annotation macros to be used everywhere in Zircon
8 // outside of publicly exposed headers. See system/public/zircon/compiler.h for
9 // the publicly exported macros.
10 
11 // The thread safety analysis system is documented at http://clang.llvm.org/docs/ThreadSafetyAnalysis.html
12 // and its use in Zircon is documented at docs/thread_annotations.md.  The macros we
13 // use are:
14 //
15 // TA_CAP(x)                    |x| is the capability this type represents, e.g. "mutex".
16 // TA_GUARDED(x)                the annotated variable is guarded by the capability (e.g. lock) |x|
17 // TA_ACQ(x)                    function acquires the mutex |x|
18 // TA_ACQ_BEFORE(x)             Indicates that if both this mutex and muxex |x| are to be acquired,
19 //                              that this mutex must be acquired before mutex |x|.
20 // TA_ACQ_AFTER(x)              Indicates that if both this mutex and muxex |x| are to be acquired,
21 //                              that this mutex must be acquired after mutex |x|.
22 // TA_TRY_ACQ(bool, x)          function acquires the mutex |x| if the function returns |bool|
23 // TA_REL(x)                    function releases the mutex |x|
24 // TA_REQ(x)                    function requires that the caller hold the mutex |x|
25 // TA_EXCL(x)                   function requires that the caller not be holding the mutex |x|
26 // TA_RET_CAP(x)                function returns a reference to the mutex |x|
27 // TA_SCOPED_CAP                type represents a scoped or RAII-style wrapper around a capability
28 // TA_NO_THREAD_SAFETY_ANALYSIS function is excluded entirely from thread safety analysis
29 
30 #ifdef __clang__
31 #define THREAD_ANNOTATION(x) __attribute__((x))
32 #else
33 #define THREAD_ANNOTATION(x)
34 #endif
35 
36 #define TA_CAP(x) THREAD_ANNOTATION(capability(x))
37 #define TA_GUARDED(x) THREAD_ANNOTATION(guarded_by(x))
38 #define TA_ACQ(...) THREAD_ANNOTATION(acquire_capability(__VA_ARGS__))
39 #define TA_ACQ_BEFORE(...) THREAD_ANNOTATION(acquired_before(__VA_ARGS__))
40 #define TA_ACQ_AFTER(...) THREAD_ANNOTATION(acquired_after(__VA_ARGS__))
41 #define TA_TRY_ACQ(...) THREAD_ANNOTATION(try_acquire_capability(__VA_ARGS__))
42 #define TA_REL(...) THREAD_ANNOTATION(release_capability(__VA_ARGS__))
43 #define TA_REQ(...) THREAD_ANNOTATION(requires_capability(__VA_ARGS__))
44 #define TA_EXCL(...) THREAD_ANNOTATION(locks_excluded(__VA_ARGS__))
45 #define TA_RET_CAP(x) THREAD_ANNOTATION(lock_returned(x))
46 #define TA_SCOPED_CAP THREAD_ANNOTATION(scoped_lockable)
47 #define TA_NO_THREAD_SAFETY_ANALYSIS THREAD_ANNOTATION(no_thread_safety_analysis)
48