1 | /* |
2 | * Copyright 2016 Google Inc. |
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 SkSafe_math_DEFINED |
9 | #define SkSafe_math_DEFINED |
10 | |
11 | // This file protects against known bugs in ucrt\math.h. |
12 | // Namely, that header defines inline methods without marking them static, |
13 | // which makes it very easy to cause ODR violations and ensuing chaos. |
14 | // |
15 | // TODO: other headers? Here are some potential problem headers: |
16 | // $ grep -R __inline * | grep -v static | cut -f 1 -d: | sort | uniq |
17 | // corecrt.h |
18 | // corecrt_stdio_config.h |
19 | // ctype.h |
20 | // fenv.h |
21 | // locale.h |
22 | // malloc.h |
23 | // math.h |
24 | // tchar.h |
25 | // wchar.h |
26 | // I took a quick look through other headers outside math.h. |
27 | // Nothing looks anywhere near as likely to be used by Skia as math.h. |
28 | |
29 | #if defined(_MSC_VER) && !defined(_INC_MATH) |
30 | // Our strategy here is to simply inject "static" into the headers |
31 | // where it should have been written, just before __inline. |
32 | // |
33 | // Most inline-but-not-static methods in math.h are 32-bit only, |
34 | // but not all of them (see frexpf, hypothf, ldexpf...). So to |
35 | // be safe, 32- and 64-bit builds both get this treatment. |
36 | |
37 | #define __inline static __inline |
38 | #include <math.h> |
39 | #undef __inline |
40 | |
41 | #if !defined(_INC_MATH) |
42 | #error Hmm. Looks like math.h has changed its header guards. |
43 | #endif |
44 | |
45 | #define INC_MATH_IS_SAFE_NOW |
46 | |
47 | #else |
48 | #include <math.h> |
49 | |
50 | #endif |
51 | |
52 | #endif//SkSafe_math_DEFINED |
53 | |