Fix "syntax error: empty declaration" warnings.
[profile/ivi/pixman.git] / pixman / pixman-compiler.h
1 /* Pixman uses some non-standard compiler features. This file ensures
2  * they exist
3  *
4  * The features are:
5  *
6  *    FUNC           must be defined to expand to the current function
7  *    PIXMAN_EXPORT  should be defined to whatever is required to
8  *                   export functions from a shared library
9  *    limits         limits for various types must be defined
10  *    inline         must be defined
11  *    force_inline   must be defined
12  */
13 #if defined (__GNUC__)
14 #  define FUNC     ((const char*) (__PRETTY_FUNCTION__))
15 #elif defined (__sun) || (defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L)
16 #  define FUNC     ((const char*) (__func__))
17 #else
18 #  define FUNC     ((const char*) ("???"))
19 #endif
20
21 #ifndef INT16_MIN
22 # define INT16_MIN              (-32767-1)
23 #endif
24
25 #ifndef INT16_MAX
26 # define INT16_MAX              (32767)
27 #endif
28
29 #ifndef INT32_MIN
30 # define INT32_MIN              (-2147483647-1)
31 #endif
32
33 #ifndef INT32_MAX
34 # define INT32_MAX              (2147483647)
35 #endif
36
37 #ifndef UINT32_MIN
38 # define UINT32_MIN             (0)
39 #endif
40
41 #ifndef UINT32_MAX
42 # define UINT32_MAX             (4294967295U)
43 #endif
44
45 #ifndef M_PI
46 # define M_PI                   3.14159265358979323846
47 #endif
48
49 #ifdef _MSC_VER
50 /* 'inline' is available only in C++ in MSVC */
51 #   define inline __inline
52 #   define force_inline __forceinline
53 #   define noinline __declspec(noinline)
54 #elif defined __GNUC__ || (defined(__SUNPRO_C) && (__SUNPRO_C >= 0x590))
55 #   define inline __inline__
56 #   define force_inline __inline__ __attribute__ ((__always_inline__))
57 #   define noinline __attribute__((noinline))
58 #else
59 #   ifndef force_inline
60 #      define force_inline inline
61 #   endif
62 #   ifndef noinline
63 #      define noinline
64 #   endif
65 #endif
66
67 /* GCC visibility */
68 #if defined(__GNUC__) && __GNUC__ >= 4 && !defined(_WIN32)
69 #   define PIXMAN_EXPORT __attribute__ ((visibility("default")))
70 /* Sun Studio 8 visibility */
71 #elif defined(__SUNPRO_C) && (__SUNPRO_C >= 0x550)
72 #   define PIXMAN_EXPORT __global
73 #else
74 #   define PIXMAN_EXPORT
75 #endif
76
77 /* TLS */
78 #if defined(PIXMAN_NO_TLS)
79
80 #   define PIXMAN_DEFINE_THREAD_LOCAL(type, name)                       \
81     static type name
82 #   define PIXMAN_GET_THREAD_LOCAL(name)                                \
83     (&name)
84
85 #elif defined(TOOLCHAIN_SUPPORTS__THREAD)
86
87 #   define PIXMAN_DEFINE_THREAD_LOCAL(type, name)                       \
88     static __thread type name
89 #   define PIXMAN_GET_THREAD_LOCAL(name)                                \
90     (&name)
91
92 #elif defined(__MINGW32__)
93
94 #   define _NO_W32_PSEUDO_MODIFIERS
95 #   include <windows.h>
96
97 #   define PIXMAN_DEFINE_THREAD_LOCAL(type, name)                       \
98     static volatile int tls_ ## name ## _initialized = 0;               \
99     static void *tls_ ## name ## _mutex = NULL;                         \
100     static unsigned tls_ ## name ## _index;                             \
101                                                                         \
102     static type *                                                       \
103     tls_ ## name ## _alloc (void)                                       \
104     {                                                                   \
105         type *value = calloc (1, sizeof (type));                        \
106         if (value)                                                      \
107             TlsSetValue (tls_ ## name ## _index, value);                \
108         return value;                                                   \
109     }                                                                   \
110                                                                         \
111     static force_inline type *                                          \
112     tls_ ## name ## _get (void)                                         \
113     {                                                                   \
114         type *value;                                                    \
115         if (!tls_ ## name ## _initialized)                              \
116         {                                                               \
117             if (!tls_ ## name ## _mutex)                                \
118             {                                                           \
119                 void *mutex = CreateMutexA (NULL, 0, NULL);             \
120                 if (InterlockedCompareExchangePointer (                 \
121                         &tls_ ## name ## _mutex, mutex, NULL) != NULL)  \
122                 {                                                       \
123                     CloseHandle (mutex);                                \
124                 }                                                       \
125             }                                                           \
126             WaitForSingleObject (tls_ ## name ## _mutex, 0xFFFFFFFF);   \
127             if (!tls_ ## name ## _initialized)                          \
128             {                                                           \
129                 tls_ ## name ## _index = TlsAlloc ();                   \
130                 tls_ ## name ## _initialized = 1;                       \
131             }                                                           \
132             ReleaseMutex (tls_ ## name ## _mutex);                      \
133         }                                                               \
134         if (tls_ ## name ## _index == 0xFFFFFFFF)                       \
135             return NULL;                                                \
136         value = TlsGetValue (tls_ ## name ## _index);                   \
137         if (!value)                                                     \
138             value = tls_ ## name ## _alloc ();                          \
139         return value;                                                   \
140     }
141
142 #   define PIXMAN_GET_THREAD_LOCAL(name)                                \
143     tls_ ## name ## _get ()
144
145 #elif defined(_MSC_VER)
146
147 #   define PIXMAN_DEFINE_THREAD_LOCAL(type, name)                       \
148     static __declspec(thread) type name
149 #   define PIXMAN_GET_THREAD_LOCAL(name)                                \
150     (&name)
151
152 #elif defined(HAVE_PTHREAD_SETSPECIFIC)
153
154 #include <pthread.h>
155
156 #  define PIXMAN_DEFINE_THREAD_LOCAL(type, name)                        \
157     static pthread_once_t tls_ ## name ## _once_control = PTHREAD_ONCE_INIT; \
158     static pthread_key_t tls_ ## name ## _key;                          \
159                                                                         \
160     static void                                                         \
161     tls_ ## name ## _destroy_value (void *value)                        \
162     {                                                                   \
163         free (value);                                                   \
164     }                                                                   \
165                                                                         \
166     static void                                                         \
167     tls_ ## name ## _make_key (void)                                    \
168     {                                                                   \
169         pthread_key_create (&tls_ ## name ## _key,                      \
170                             tls_ ## name ## _destroy_value);            \
171     }                                                                   \
172                                                                         \
173     static type *                                                       \
174     tls_ ## name ## _alloc (void)                                       \
175     {                                                                   \
176         type *value = calloc (1, sizeof (type));                        \
177         if (value)                                                      \
178             pthread_setspecific (tls_ ## name ## _key, value);          \
179         return value;                                                   \
180     }                                                                   \
181                                                                         \
182     static force_inline type *                                          \
183     tls_ ## name ## _get (void)                                         \
184     {                                                                   \
185         type *value = NULL;                                             \
186         if (pthread_once (&tls_ ## name ## _once_control,               \
187                           tls_ ## name ## _make_key) == 0)              \
188         {                                                               \
189             value = pthread_getspecific (tls_ ## name ## _key);         \
190             if (!value)                                                 \
191                 value = tls_ ## name ## _alloc ();                      \
192         }                                                               \
193         return value;                                                   \
194     }                                                                   \
195     extern int no_such_variable                                         
196
197 #   define PIXMAN_GET_THREAD_LOCAL(name)                                \
198     tls_ ## name ## _get ()
199
200 #else
201
202 #    error "Unknown thread local support for this system. Pixman will not work with multiple threads. Define PIXMAN_NO_TLS to acknowledge and accept this limitation and compile pixman without thread-safety support."
203
204 #endif