• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2006 The Android Open Source Project
3  *
4  * Use of this source code is governed by a BSD-style license that can be
5  * found in the LICENSE file.
6  */
7 
8 #ifndef SkPostConfig_DEFINED
9 #define SkPostConfig_DEFINED
10 
11 #if defined(SK_BUILD_FOR_WIN32) || defined(SK_BUILD_FOR_WINCE)
12 #  define SK_BUILD_FOR_WIN
13 #endif
14 
15 #if defined(SK_DEBUG) && defined(SK_RELEASE)
16 #  error "cannot define both SK_DEBUG and SK_RELEASE"
17 #elif !defined(SK_DEBUG) && !defined(SK_RELEASE)
18 #  error "must define either SK_DEBUG or SK_RELEASE"
19 #endif
20 
21 #if defined(SK_SUPPORT_UNITTEST) && !defined(SK_DEBUG)
22 #  error "can't have unittests without debug"
23 #endif
24 
25 /**
26  * Matrix calculations may be float or double.
27  * The default is double, as that is faster given our impl uses doubles
28  * for intermediate calculations.
29  */
30 #if defined(SK_MSCALAR_IS_DOUBLE) && defined(SK_MSCALAR_IS_FLOAT)
31 #  error "cannot define both SK_MSCALAR_IS_DOUBLE and SK_MSCALAR_IS_FLOAT"
32 #elif !defined(SK_MSCALAR_IS_DOUBLE) && !defined(SK_MSCALAR_IS_FLOAT)
33 #  define SK_MSCALAR_IS_DOUBLE
34 #endif
35 
36 #if defined(SK_CPU_LENDIAN) && defined(SK_CPU_BENDIAN)
37 #  error "cannot define both SK_CPU_LENDIAN and SK_CPU_BENDIAN"
38 #elif !defined(SK_CPU_LENDIAN) && !defined(SK_CPU_BENDIAN)
39 #  error "must define either SK_CPU_LENDIAN or SK_CPU_BENDIAN"
40 #endif
41 
42 /**
43  * Ensure the port has defined all of SK_X32_SHIFT, or none of them.
44  */
45 #ifdef SK_A32_SHIFT
46 #  if !defined(SK_R32_SHIFT) || !defined(SK_G32_SHIFT) || !defined(SK_B32_SHIFT)
47 #    error "all or none of the 32bit SHIFT amounts must be defined"
48 #  endif
49 #else
50 #  if defined(SK_R32_SHIFT) || defined(SK_G32_SHIFT) || defined(SK_B32_SHIFT)
51 #    error "all or none of the 32bit SHIFT amounts must be defined"
52 #  endif
53 #endif
54 
55 #if !defined(SK_HAS_COMPILER_FEATURE)
56 #  if defined(__has_feature)
57 #    define SK_HAS_COMPILER_FEATURE(x) __has_feature(x)
58 #  else
59 #    define SK_HAS_COMPILER_FEATURE(x) 0
60 #  endif
61 #endif
62 
63 #if !defined(SK_ATTRIBUTE)
64 #  if defined(__clang__) || defined(__GNUC__)
65 #    define SK_ATTRIBUTE(attr) __attribute__((attr))
66 #  else
67 #    define SK_ATTRIBUTE(attr)
68 #  endif
69 #endif
70 
71 #if !defined(SK_SUPPORT_GPU)
72 #  define SK_SUPPORT_GPU 1
73 #endif
74 
75 /**
76  * The clang static analyzer likes to know that when the program is not
77  * expected to continue (crash, assertion failure, etc). It will notice that
78  * some combination of parameters lead to a function call that does not return.
79  * It can then make appropriate assumptions about the parameters in code
80  * executed only if the non-returning function was *not* called.
81  */
82 #if !defined(SkNO_RETURN_HINT)
83 #  if SK_HAS_COMPILER_FEATURE(attribute_analyzer_noreturn)
84      static inline void SkNO_RETURN_HINT() __attribute__((analyzer_noreturn));
SkNO_RETURN_HINT()85      static inline void SkNO_RETURN_HINT() {}
86 #  else
87 #    define SkNO_RETURN_HINT() do {} while (false)
88 #  endif
89 #endif
90 
91 #if defined(SK_ZLIB_INCLUDE) && defined(SK_SYSTEM_ZLIB)
92 #  error "cannot define both SK_ZLIB_INCLUDE and SK_SYSTEM_ZLIB"
93 #elif defined(SK_ZLIB_INCLUDE) || defined(SK_SYSTEM_ZLIB)
94 #  define SK_HAS_ZLIB
95 #endif
96 
97 ///////////////////////////////////////////////////////////////////////////////
98 
99 #ifndef SkNEW
100 #  define SkNEW(type_name)                           (new type_name)
101 #  define SkNEW_ARGS(type_name, args)                (new type_name args)
102 #  define SkNEW_ARRAY(type_name, count)              (new type_name[(count)])
103 #  define SkNEW_PLACEMENT(buf, type_name)            (new (buf) type_name)
104 #  define SkNEW_PLACEMENT_ARGS(buf, type_name, args) (new (buf) type_name args)
105 #  define SkDELETE(obj)                              (delete (obj))
106 #  define SkDELETE_ARRAY(array)                      (delete[] (array))
107 #endif
108 
109 #ifndef SK_CRASH
110 #  ifdef SK_BUILD_FOR_WIN
111 #    define SK_CRASH() __debugbreak()
112 #  else
113 #    if 1   // set to 0 for infinite loop, which can help connecting gdb
114 #      define SK_CRASH() do { SkNO_RETURN_HINT(); *(int *)(uintptr_t)0xbbadbeef = 0; } while (false)
115 #    else
116 #      define SK_CRASH() do { SkNO_RETURN_HINT(); } while (true)
117 #    endif
118 #  endif
119 #endif
120 
121 ///////////////////////////////////////////////////////////////////////////////
122 
123 /**
124  * SK_ENABLE_INST_COUNT controlls printing how many reference counted objects
125  * are still held on exit.
126  * Defaults to 1 in DEBUG and 0 in RELEASE.
127  */
128 #ifndef SK_ENABLE_INST_COUNT
129 #  ifdef SK_DEBUG
130 // Only enabled for static builds, because instance counting relies on static
131 // variables in functions defined in header files.
132 #    define SK_ENABLE_INST_COUNT !defined(SKIA_DLL)
133 #  else
134 #    define SK_ENABLE_INST_COUNT 0
135 #  endif
136 #endif
137 
138 ///////////////////////////////////////////////////////////////////////////////
139 
140 #ifdef SK_BUILD_FOR_WIN
141 #  ifndef WIN32_LEAN_AND_MEAN
142 #    define WIN32_LEAN_AND_MEAN
143 #    define WIN32_IS_MEAN_WAS_LOCALLY_DEFINED
144 #  endif
145 #  ifndef NOMINMAX
146 #    define NOMINMAX
147 #    define NOMINMAX_WAS_LOCALLY_DEFINED
148 #  endif
149 #
150 #  include <windows.h>
151 #
152 #  ifdef WIN32_IS_MEAN_WAS_LOCALLY_DEFINED
153 #    undef WIN32_IS_MEAN_WAS_LOCALLY_DEFINED
154 #    undef WIN32_LEAN_AND_MEAN
155 #  endif
156 #  ifdef NOMINMAX_WAS_LOCALLY_DEFINED
157 #    undef NOMINMAX_WAS_LOCALLY_DEFINED
158 #    undef NOMINMAX
159 #  endif
160 #
161 #  ifndef SK_A32_SHIFT
162 #    define SK_A32_SHIFT 24
163 #    define SK_R32_SHIFT 16
164 #    define SK_G32_SHIFT 8
165 #    define SK_B32_SHIFT 0
166 #  endif
167 #
168 #endif
169 
170 #ifndef SK_ALWAYSBREAK
171 #  ifdef SK_DEBUG
172 #    define SK_ALWAYSBREAK(cond) do { \
173               if (cond) break; \
174               SkNO_RETURN_HINT(); \
175               SkDebugf("%s:%d: failed assertion \"%s\"\n", __FILE__, __LINE__, #cond); \
176               SK_CRASH(); \
177         } while (false)
178 #  else
179 #    define SK_ALWAYSBREAK(cond) do { if (cond) break; SK_CRASH(); } while (false)
180 #  endif
181 #endif
182 
183 /**
184  *  We check to see if the SHIFT value has already been defined.
185  *  if not, we define it ourself to some default values. We default to OpenGL
186  *  order (in memory: r,g,b,a)
187  */
188 #ifndef SK_A32_SHIFT
189 #  ifdef SK_CPU_BENDIAN
190 #    define SK_R32_SHIFT    24
191 #    define SK_G32_SHIFT    16
192 #    define SK_B32_SHIFT    8
193 #    define SK_A32_SHIFT    0
194 #  else
195 #    define SK_R32_SHIFT    0
196 #    define SK_G32_SHIFT    8
197 #    define SK_B32_SHIFT    16
198 #    define SK_A32_SHIFT    24
199 #  endif
200 #endif
201 
202 /**
203  * SkColor has well defined shift values, but SkPMColor is configurable. This
204  * macro is a convenience that returns true if the shift values are equal while
205  * ignoring the machine's endianness.
206  */
207 #define SK_COLOR_MATCHES_PMCOLOR_BYTE_ORDER \
208     (SK_A32_SHIFT == 24 && SK_R32_SHIFT == 16 && SK_G32_SHIFT == 8 && SK_B32_SHIFT == 0)
209 
210 /**
211  * SK_PMCOLOR_BYTE_ORDER can be used to query the byte order of SkPMColor at compile time. The
212  * relationship between the byte order and shift values depends on machine endianness. If the shift
213  * order is R=0, G=8, B=16, A=24 then ((char*)&pmcolor)[0] will produce the R channel on a little
214  * endian machine and the A channel on a big endian machine. Thus, given those shifts values,
215  * SK_PMCOLOR_BYTE_ORDER(R,G,B,A) will be true on a little endian machine and
216  * SK_PMCOLOR_BYTE_ORDER(A,B,G,R) will be true on a big endian machine.
217  */
218 #ifdef SK_CPU_BENDIAN
219 #  define SK_PMCOLOR_BYTE_ORDER(C0, C1, C2, C3)     \
220         (SK_ ## C3 ## 32_SHIFT == 0  &&             \
221          SK_ ## C2 ## 32_SHIFT == 8  &&             \
222          SK_ ## C1 ## 32_SHIFT == 16 &&             \
223          SK_ ## C0 ## 32_SHIFT == 24)
224 #else
225 #  define SK_PMCOLOR_BYTE_ORDER(C0, C1, C2, C3)     \
226         (SK_ ## C0 ## 32_SHIFT == 0  &&             \
227          SK_ ## C1 ## 32_SHIFT == 8  &&             \
228          SK_ ## C2 ## 32_SHIFT == 16 &&             \
229          SK_ ## C3 ## 32_SHIFT == 24)
230 #endif
231 
232 //////////////////////////////////////////////////////////////////////
233 
234 // TODO: rebaseline as needed so we can remove this flag entirely.
235 //  - all platforms have int64_t now
236 //  - we have slightly different fixed math results because of this check
237 //    since we don't define this for linux/android
238 #if defined(SK_BUILD_FOR_WIN32) || defined(SK_BUILD_FOR_MAC)
239 #  ifndef SkLONGLONG
240 #    define SkLONGLONG int64_t
241 #  endif
242 #endif
243 
244 //////////////////////////////////////////////////////////////////////////////////////////////
245 #ifndef SK_BUILD_FOR_WINCE
246 #  include <string.h>
247 #  include <stdlib.h>
248 #else
249 #  define _CMNINTRIN_DECLARE_ONLY
250 #  include "cmnintrin.h"
251 #endif
252 
253 #if defined SK_DEBUG && defined SK_BUILD_FOR_WIN32
254 #  ifdef free
255 #    undef free
256 #  endif
257 #  include <crtdbg.h>
258 #  undef free
259 #
260 #  ifdef SK_DEBUGx
261 #    if defined(SK_SIMULATE_FAILED_MALLOC) && defined(__cplusplus)
262        void * operator new(
263            size_t cb,
264            int nBlockUse,
265            const char * szFileName,
266            int nLine,
267            int foo
268            );
269        void * operator new[](
270            size_t cb,
271            int nBlockUse,
272            const char * szFileName,
273            int nLine,
274            int foo
275            );
276        void operator delete(
277            void *pUserData,
278            int, const char*, int, int
279            );
280        void operator delete(
281            void *pUserData
282            );
283        void operator delete[]( void * p );
284 #      define DEBUG_CLIENTBLOCK   new( _CLIENT_BLOCK, __FILE__, __LINE__, 0)
285 #    else
286 #      define DEBUG_CLIENTBLOCK   new( _CLIENT_BLOCK, __FILE__, __LINE__)
287 #    endif
288 #    define new DEBUG_CLIENTBLOCK
289 #  else
290 #    define DEBUG_CLIENTBLOCK
291 #  endif
292 #endif
293 
294 //////////////////////////////////////////////////////////////////////
295 
296 #ifndef SK_OVERRIDE
297 #  if defined(_MSC_VER)
298 #    define SK_OVERRIDE override
299 #  elif defined(__clang__)
300      // Using __attribute__((override)) on clang does not appear to always work.
301      // Clang defaults to C++03 and warns about using override. Squelch that. Intentionally no
302      // push/pop here so all users of SK_OVERRIDE ignore the warning too. This is like passing
303      // -Wno-c++11-extensions, except that GCC won't die (because it won't see this pragma).
304 #    pragma clang diagnostic ignored "-Wc++11-extensions"
305 #
306 #    if __has_feature(cxx_override_control)
307 #      define SK_OVERRIDE override
308 #    elif defined(__has_extension) && __has_extension(cxx_override_control)
309 #      define SK_OVERRIDE override
310 #    endif
311 #  endif
312 #  ifndef SK_OVERRIDE
313 #    define SK_OVERRIDE
314 #  endif
315 #endif
316 
317 //////////////////////////////////////////////////////////////////////
318 
319 #if !defined(SK_UNUSED)
320 #  define SK_UNUSED SK_ATTRIBUTE(unused)
321 #endif
322 
323 #if !defined(SK_ATTR_DEPRECATED)
324    // FIXME: we ignore msg for now...
325 #  define SK_ATTR_DEPRECATED(msg) SK_ATTRIBUTE(deprecated)
326 #endif
327 
328 #if !defined(SK_ATTR_EXTERNALLY_DEPRECATED)
329 #  if !defined(SK_INTERNAL)
330 #    define SK_ATTR_EXTERNALLY_DEPRECATED(msg) SK_ATTR_DEPRECATED(msg)
331 #  else
332 #    define SK_ATTR_EXTERNALLY_DEPRECATED(msg)
333 #  endif
334 #endif
335 
336 /**
337  * If your judgment is better than the compiler's (i.e. you've profiled it),
338  * you can use SK_ALWAYS_INLINE to force inlining. E.g.
339  *     inline void someMethod() { ... }             // may not be inlined
340  *     SK_ALWAYS_INLINE void someMethod() { ... }   // should always be inlined
341  */
342 #if !defined(SK_ALWAYS_INLINE)
343 #  if defined(SK_BUILD_FOR_WIN)
344 #    define SK_ALWAYS_INLINE __forceinline
345 #  else
346 #    define SK_ALWAYS_INLINE SK_ATTRIBUTE(always_inline) inline
347 #  endif
348 #endif
349 
350 //////////////////////////////////////////////////////////////////////
351 
352 #if defined(__clang__) || defined(__GNUC__)
353 #  define SK_PREFETCH(ptr) __builtin_prefetch(ptr)
354 #  define SK_WRITE_PREFETCH(ptr) __builtin_prefetch(ptr, 1)
355 #else
356 #  define SK_PREFETCH(ptr)
357 #  define SK_WRITE_PREFETCH(ptr)
358 #endif
359 
360 //////////////////////////////////////////////////////////////////////
361 
362 #ifndef SK_PRINTF_LIKE
363 #  if defined(__clang__) || defined(__GNUC__)
364 #    define SK_PRINTF_LIKE(A, B) __attribute__((format(printf, (A), (B))))
365 #  else
366 #    define SK_PRINTF_LIKE(A, B)
367 #  endif
368 #endif
369 
370 //////////////////////////////////////////////////////////////////////
371 
372 #ifndef SK_SIZE_T_SPECIFIER
373 #  if defined(_MSC_VER)
374 #    define SK_SIZE_T_SPECIFIER "%Iu"
375 #  else
376 #    define SK_SIZE_T_SPECIFIER "%zu"
377 #  endif
378 #endif
379 
380 //////////////////////////////////////////////////////////////////////
381 
382 #ifndef SK_ALLOW_STATIC_GLOBAL_INITIALIZERS
383 #  define SK_ALLOW_STATIC_GLOBAL_INITIALIZERS 1
384 #endif
385 
386 //////////////////////////////////////////////////////////////////////
387 
388 #ifndef SK_ATOMICS_PLATFORM_H
389 #  if defined(_MSC_VER)
390 #    define SK_ATOMICS_PLATFORM_H "../../src/ports/SkAtomics_win.h"
391 #  else
392 #    define SK_ATOMICS_PLATFORM_H "../../src/ports/SkAtomics_sync.h"
393 #  endif
394 #endif
395 
396 #ifndef SK_MUTEX_PLATFORM_H
397 #  if defined(SK_BUILD_FOR_WIN)
398 #    define SK_MUTEX_PLATFORM_H "../../src/ports/SkMutex_win.h"
399 #  else
400 #    define SK_MUTEX_PLATFORM_H "../../src/ports/SkMutex_pthread.h"
401 #  endif
402 #endif
403 
404 #ifndef SK_BARRIERS_PLATFORM_H
405 #  if SK_HAS_COMPILER_FEATURE(thread_sanitizer)
406 #    define SK_BARRIERS_PLATFORM_H "../../src/ports/SkBarriers_tsan.h"
407 #  elif defined(SK_CPU_ARM32) || defined(SK_CPU_ARM64)
408 #    define SK_BARRIERS_PLATFORM_H "../../src/ports/SkBarriers_arm.h"
409 #  else
410 #    define SK_BARRIERS_PLATFORM_H "../../src/ports/SkBarriers_x86.h"
411 #  endif
412 #endif
413 
414 
415 //////////////////////////////////////////////////////////////////////
416 
417 #if defined(SK_GAMMA_EXPONENT) && defined(SK_GAMMA_SRGB)
418 #  error "cannot define both SK_GAMMA_EXPONENT and SK_GAMMA_SRGB"
419 #elif defined(SK_GAMMA_SRGB)
420 #  define SK_GAMMA_EXPONENT (0.0f)
421 #elif !defined(SK_GAMMA_EXPONENT)
422 #  define SK_GAMMA_EXPONENT (2.2f)
423 #endif
424 
425 #endif // SkPostConfig_DEFINED
426