1 // Copyright 2014 PDFium 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 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com
6
7 #ifndef CORE_FXCRT_FX_SYSTEM_H_
8 #define CORE_FXCRT_FX_SYSTEM_H_
9
10 #include <assert.h>
11 #include <math.h>
12 #include <stdarg.h>
13 #include <stddef.h>
14 #include <stdint.h>
15 #include <stdio.h>
16 #include <stdlib.h>
17 #include <string.h>
18 #include <wchar.h>
19
20 // _FX_OS_ values:
21 #define _FX_OS_WIN32_ 1
22 #define _FX_OS_WIN64_ 2
23 #define _FX_OS_LINUX_ 4
24 #define _FX_OS_MACOSX_ 7
25 #define _FX_OS_ANDROID_ 12
26 #define _FX_OS_WASM_ 13
27
28 // _FX_PLATFORM_ values;
29 #define _FX_PLATFORM_WINDOWS_ 1 // _FX_OS_WIN32_ or _FX_OS_WIN64_.
30 #define _FX_PLATFORM_LINUX_ 2 // _FX_OS_LINUX_ or _FX_OS_WASM_.
31 #define _FX_PLATFORM_APPLE_ 3 // _FX_OS_MACOSX_ always.
32 #define _FX_PLATFORM_ANDROID_ 4 // _FX_OS_ANDROID_ always.
33
34 #ifndef _FX_OS_
35 #if defined(__ANDROID__)
36 #define _FX_OS_ _FX_OS_ANDROID_
37 #define _FX_PLATFORM_ _FX_PLATFORM_ANDROID_
38 #elif defined(_WIN32)
39 #define _FX_OS_ _FX_OS_WIN32_
40 #define _FX_PLATFORM_ _FX_PLATFORM_WINDOWS_
41 #elif defined(_WIN64)
42 #define _FX_OS_ _FX_OS_WIN64_
43 #define _FX_PLATFORM_ _FX_PLATFORM_WINDOWS_
44 #elif defined(__linux__)
45 #define _FX_OS_ _FX_OS_LINUX_
46 #define _FX_PLATFORM_ _FX_PLATFORM_LINUX_
47 #elif defined(__APPLE__)
48 #define _FX_OS_ _FX_OS_MACOSX_
49 #define _FX_PLATFORM_ _FX_PLATFORM_APPLE_
50 #elif defined(__asmjs__) || defined(__wasm__)
51 #define _FX_OS_ _FX_OS_WASM_
52 #define _FX_PLATFORM_ _FX_PLATFORM_LINUX_
53 #endif
54 #endif // _FX_OS_
55
56 #if !defined(_FX_OS_) || _FX_OS_ == 0
57 #error Sorry, can not figure out target OS. Please specify _FX_OS_ macro.
58 #endif
59
60 #if defined(_MSC_VER) && _MSC_VER < 1900
61 #error Sorry, VC++ 2015 or later is required to compile PDFium.
62 #endif // defined(_MSC_VER) && _MSC_VER < 1900
63
64 #if _FX_OS_ == _FX_OS_WASM_ && defined(PDF_ENABLE_V8)
65 #error Cannot compile v8 with wasm.
66 #endif // PDF_ENABLE_V8
67
68 #if _FX_PLATFORM_ == _FX_PLATFORM_WINDOWS_
69 #include <windows.h>
70 #include <sal.h>
71 #endif // _FX_PLATFORM_ == _FX_PLATFORM_WINDOWS_
72
73 #if _FX_PLATFORM_ == _FX_PLATFORM_APPLE_
74 #include <Carbon/Carbon.h>
75 #include <libkern/OSAtomic.h>
76 #endif // _FX_PLATFORM_ == _FX_PLATFORM_APPLE_
77
78 #ifdef __cplusplus
79 extern "C" {
80 #endif // __cplusplus
81
82 #define IsFloatZero(f) ((f) < 0.0001 && (f) > -0.0001)
83 #define IsFloatBigger(fa, fb) ((fa) > (fb) && !IsFloatZero((fa) - (fb)))
84 #define IsFloatSmaller(fa, fb) ((fa) < (fb) && !IsFloatZero((fa) - (fb)))
85 #define IsFloatEqual(fa, fb) IsFloatZero((fa) - (fb))
86
87 // PDFium file sizes match the platform, but PDFium itself does not support
88 // files larger than 2GB even if the platform does. The value must be signed
89 // to support -1 error returns.
90 // TODO(tsepez): support larger files.
91 #if _FX_PLATFORM_ == _FX_PLATFORM_WINDOWS_
92 #define FX_FILESIZE int32_t
93 #else // _FX_PLATFORM_ == _FX_PLATFORM_WINDOWS_
94 #define FX_FILESIZE off_t
95 #endif // _FX_PLATFORM_ == _FX_PLATFORM_WINDOWS_
96
97 #ifndef ASSERT
98 #ifndef NDEBUG
99 #define ASSERT assert
100 #else
101 #define ASSERT(a)
102 #endif // NDEBUG
103 #endif // ASSERT
104
105 #if defined(__clang__) || defined(__GNUC__)
106 #define PDFIUM_IMMEDIATE_CRASH() __builtin_trap()
107 #else
108 #define PDFIUM_IMMEDIATE_CRASH() ((void)(*(volatile char*)0 = 0))
109 #endif // defined(__clang__) || defined(__GNUC__)
110
111 // M_PI not universally present on all platforms.
112 #define FX_PI 3.1415926535897932384626433832795f
113 #define FX_BEZIER 0.5522847498308f
114
115 // NOTE: prevent use of the return value from snprintf() since some platforms
116 // have different return values.
117 #define FXSYS_snprintf (void)snprintf
118 #define FXSYS_vsnprintf (void)vsnprintf
119 #define FXSYS_sprintf DO_NOT_USE_SPRINTF_DIE_DIE_DIE
120 #define FXSYS_vsprintf DO_NOT_USE_VSPRINTF_DIE_DIE_DIE
121
122 #ifdef __cplusplus
123 } // extern "C"
124
125 #include "third_party/base/numerics/safe_conversions.h"
126
127 // Overloaded functions for C++ templates
FXSYS_len(const char * ptr)128 inline size_t FXSYS_len(const char* ptr) {
129 return strlen(ptr);
130 }
131
FXSYS_len(const wchar_t * ptr)132 inline size_t FXSYS_len(const wchar_t* ptr) {
133 return wcslen(ptr);
134 }
135
FXSYS_cmp(const char * ptr1,const char * ptr2,size_t len)136 inline int FXSYS_cmp(const char* ptr1, const char* ptr2, size_t len) {
137 return memcmp(ptr1, ptr2, len);
138 }
139
FXSYS_cmp(const wchar_t * ptr1,const wchar_t * ptr2,size_t len)140 inline int FXSYS_cmp(const wchar_t* ptr1, const wchar_t* ptr2, size_t len) {
141 return wmemcmp(ptr1, ptr2, len);
142 }
143
FXSYS_chr(const char * ptr,char ch,size_t len)144 inline const char* FXSYS_chr(const char* ptr, char ch, size_t len) {
145 return reinterpret_cast<const char*>(memchr(ptr, ch, len));
146 }
147
FXSYS_chr(const wchar_t * ptr,wchar_t ch,size_t len)148 inline const wchar_t* FXSYS_chr(const wchar_t* ptr, wchar_t ch, size_t len) {
149 return wmemchr(ptr, ch, len);
150 }
151
152 extern "C" {
153 #endif // __cplusplus
154
155 #if _FX_PLATFORM_ == _FX_PLATFORM_WINDOWS_
156 #define FXSYS_GetACP GetACP
157 #define FXSYS_itoa _itoa
158 #define FXSYS_strlwr _strlwr
159 #define FXSYS_strupr _strupr
160 #define FXSYS_stricmp _stricmp
161 #define FXSYS_pow(a, b) (float)powf(a, b)
162 size_t FXSYS_wcsftime(wchar_t* strDest,
163 size_t maxsize,
164 const wchar_t* format,
165 const struct tm* timeptr);
166 #ifdef _NATIVE_WCHAR_T_DEFINED
167 #define FXSYS_wcsicmp(str1, str2) _wcsicmp((wchar_t*)(str1), (wchar_t*)(str2))
168 #define FXSYS_WideCharToMultiByte(p1, p2, p3, p4, p5, p6, p7, p8) \
169 WideCharToMultiByte(p1, p2, (const wchar_t*)(p3), p4, p5, p6, p7, p8)
170 #define FXSYS_MultiByteToWideChar(p1, p2, p3, p4, p5, p6) \
171 MultiByteToWideChar(p1, p2, p3, p4, (wchar_t*)(p5), p6)
172 #define FXSYS_wcslwr(str) _wcslwr((wchar_t*)(str))
173 #define FXSYS_wcsupr(str) _wcsupr((wchar_t*)(str))
174 #else // _NATIVE_WCHAR_T_DEFINED
175 #define FXSYS_wcsicmp _wcsicmp
176 #define FXSYS_WideCharToMultiByte WideCharToMultiByte
177 #define FXSYS_MultiByteToWideChar MultiByteToWideChar
178 #define FXSYS_wcslwr _wcslwr
179 #define FXSYS_wcsupr _wcsupr
180 #endif // _NATIVE_WCHAR_T_DEFINED
181
182 #else // _FX_PLATFORM_ == _FX_PLATFORM_WINDOWS_
183
184 int FXSYS_GetACP();
185 char* FXSYS_itoa(int value, char* str, int radix);
186 int FXSYS_WideCharToMultiByte(uint32_t codepage,
187 uint32_t dwFlags,
188 const wchar_t* wstr,
189 int wlen,
190 char* buf,
191 int buflen,
192 const char* default_str,
193 int* pUseDefault);
194 int FXSYS_MultiByteToWideChar(uint32_t codepage,
195 uint32_t dwFlags,
196 const char* bstr,
197 int blen,
198 wchar_t* buf,
199 int buflen);
200 char* FXSYS_strlwr(char* str);
201 char* FXSYS_strupr(char* str);
202 int FXSYS_stricmp(const char*, const char*);
203 int FXSYS_wcsicmp(const wchar_t* str1, const wchar_t* str2);
204 wchar_t* FXSYS_wcslwr(wchar_t* str);
205 wchar_t* FXSYS_wcsupr(wchar_t* str);
206 #define FXSYS_pow(a, b) (float)pow(a, b)
207 #define FXSYS_wcsftime wcsftime
208 #endif // _FX_PLATFORM_ == _FX_PLATFORM_WINDOWS_
209
210 #define FXWORD_GET_LSBFIRST(p) \
211 (static_cast<uint16_t>((static_cast<uint16_t>(p[1]) << 8) | \
212 (static_cast<uint16_t>(p[0]))))
213 #define FXWORD_GET_MSBFIRST(p) \
214 (static_cast<uint16_t>((static_cast<uint16_t>(p[0]) << 8) | \
215 (static_cast<uint16_t>(p[1]))))
216 #define FXDWORD_GET_LSBFIRST(p) \
217 ((static_cast<uint32_t>(p[3]) << 24) | (static_cast<uint32_t>(p[2]) << 16) | \
218 (static_cast<uint32_t>(p[1]) << 8) | (static_cast<uint32_t>(p[0])))
219 #define FXDWORD_GET_MSBFIRST(p) \
220 ((static_cast<uint32_t>(p[0]) << 24) | (static_cast<uint32_t>(p[1]) << 16) | \
221 (static_cast<uint32_t>(p[2]) << 8) | (static_cast<uint32_t>(p[3])))
222 int32_t FXSYS_atoi(const char* str);
223 uint32_t FXSYS_atoui(const char* str);
224 int32_t FXSYS_wtoi(const wchar_t* str);
225 int64_t FXSYS_atoi64(const char* str);
226 const char* FXSYS_i64toa(int64_t value, char* str, int radix);
227 int FXSYS_round(float f);
228 #define FXSYS_sqrt2(a, b) (float)sqrt((a) * (a) + (b) * (b))
229 #ifdef __cplusplus
230 } // extern C
231 #endif // __cplusplus
232
233 // To print a size_t value in a portable way:
234 // size_t size;
235 // printf("xyz: %" PRIuS, size);
236 // The "u" in the macro corresponds to %u, and S is for "size".
237 #if _FX_PLATFORM_ != _FX_PLATFORM_WINDOWS_
238
239 #if (defined(_INTTYPES_H) || defined(_INTTYPES_H_)) && !defined(PRId64)
240 #error "inttypes.h has already been included before this header file, but "
241 #error "without __STDC_FORMAT_MACROS defined."
242 #endif
243
244 #if !defined(__STDC_FORMAT_MACROS)
245 #define __STDC_FORMAT_MACROS
246 #endif
247
248 #include <inttypes.h>
249
250 #if !defined(PRIuS)
251 #define PRIuS "zu"
252 #endif
253
254 #else // _FX_PLATFORM_ != _FX_PLATFORM_WINDOWS_
255
256 #if !defined(PRIuS)
257 #define PRIuS "Iu"
258 #endif
259
260 #endif // _FX_PLATFORM_ != _FX_PLATFORM_WINDOWS_
261
262 // Prevent a function from ever being inlined, typically because we'd
263 // like it to appear in stack traces.
264 #if _FX_PLATFORM_ == _FX_PLATFORM_WINDOWS_
265 #define NEVER_INLINE __declspec(noinline)
266 #else // _FX_PLATFORM_ == _FX_PLATFORM_WINDOWS_
267 #define NEVER_INLINE __attribute__((__noinline__))
268 #endif // _FX_PLATFORM_ == _FX_PLATFORM_WINDOWS_
269
270 #endif // CORE_FXCRT_FX_SYSTEM_H_
271