extzstd 0.1 → 0.3.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (134) hide show
  1. checksums.yaml +5 -5
  2. data/HISTORY.ja.md +39 -0
  3. data/README.md +38 -56
  4. data/contrib/zstd/CHANGELOG +613 -0
  5. data/contrib/zstd/CODE_OF_CONDUCT.md +5 -0
  6. data/contrib/zstd/CONTRIBUTING.md +406 -0
  7. data/contrib/zstd/COPYING +339 -0
  8. data/contrib/zstd/Makefile +420 -0
  9. data/contrib/zstd/README.md +179 -41
  10. data/contrib/zstd/TESTING.md +44 -0
  11. data/contrib/zstd/appveyor.yml +292 -0
  12. data/contrib/zstd/lib/BUCK +234 -0
  13. data/contrib/zstd/lib/Makefile +451 -0
  14. data/contrib/zstd/lib/README.md +207 -0
  15. data/contrib/zstd/{common → lib/common}/bitstream.h +187 -138
  16. data/contrib/zstd/lib/common/compiler.h +288 -0
  17. data/contrib/zstd/lib/common/cpu.h +213 -0
  18. data/contrib/zstd/lib/common/debug.c +24 -0
  19. data/contrib/zstd/lib/common/debug.h +107 -0
  20. data/contrib/zstd/lib/common/entropy_common.c +362 -0
  21. data/contrib/zstd/{common → lib/common}/error_private.c +25 -12
  22. data/contrib/zstd/{common → lib/common}/error_private.h +14 -10
  23. data/contrib/zstd/{common → lib/common}/fse.h +173 -92
  24. data/contrib/zstd/{common → lib/common}/fse_decompress.c +149 -85
  25. data/contrib/zstd/lib/common/huf.h +361 -0
  26. data/contrib/zstd/{common → lib/common}/mem.h +115 -59
  27. data/contrib/zstd/lib/common/pool.c +350 -0
  28. data/contrib/zstd/lib/common/pool.h +84 -0
  29. data/contrib/zstd/lib/common/threading.c +122 -0
  30. data/contrib/zstd/lib/common/threading.h +155 -0
  31. data/contrib/zstd/{common → lib/common}/xxhash.c +55 -96
  32. data/contrib/zstd/{common → lib/common}/xxhash.h +23 -47
  33. data/contrib/zstd/lib/common/zstd_common.c +83 -0
  34. data/contrib/zstd/lib/common/zstd_deps.h +111 -0
  35. data/contrib/zstd/lib/common/zstd_errors.h +95 -0
  36. data/contrib/zstd/lib/common/zstd_internal.h +478 -0
  37. data/contrib/zstd/{compress → lib/compress}/fse_compress.c +214 -319
  38. data/contrib/zstd/lib/compress/hist.c +181 -0
  39. data/contrib/zstd/lib/compress/hist.h +75 -0
  40. data/contrib/zstd/lib/compress/huf_compress.c +913 -0
  41. data/contrib/zstd/lib/compress/zstd_compress.c +5208 -0
  42. data/contrib/zstd/lib/compress/zstd_compress_internal.h +1203 -0
  43. data/contrib/zstd/lib/compress/zstd_compress_literals.c +158 -0
  44. data/contrib/zstd/lib/compress/zstd_compress_literals.h +29 -0
  45. data/contrib/zstd/lib/compress/zstd_compress_sequences.c +433 -0
  46. data/contrib/zstd/lib/compress/zstd_compress_sequences.h +54 -0
  47. data/contrib/zstd/lib/compress/zstd_compress_superblock.c +849 -0
  48. data/contrib/zstd/lib/compress/zstd_compress_superblock.h +32 -0
  49. data/contrib/zstd/lib/compress/zstd_cwksp.h +561 -0
  50. data/contrib/zstd/lib/compress/zstd_double_fast.c +521 -0
  51. data/contrib/zstd/lib/compress/zstd_double_fast.h +38 -0
  52. data/contrib/zstd/lib/compress/zstd_fast.c +496 -0
  53. data/contrib/zstd/lib/compress/zstd_fast.h +37 -0
  54. data/contrib/zstd/lib/compress/zstd_lazy.c +1412 -0
  55. data/contrib/zstd/lib/compress/zstd_lazy.h +87 -0
  56. data/contrib/zstd/lib/compress/zstd_ldm.c +660 -0
  57. data/contrib/zstd/lib/compress/zstd_ldm.h +116 -0
  58. data/contrib/zstd/lib/compress/zstd_opt.c +1345 -0
  59. data/contrib/zstd/lib/compress/zstd_opt.h +56 -0
  60. data/contrib/zstd/lib/compress/zstdmt_compress.c +1811 -0
  61. data/contrib/zstd/lib/compress/zstdmt_compress.h +110 -0
  62. data/contrib/zstd/lib/decompress/huf_decompress.c +1350 -0
  63. data/contrib/zstd/lib/decompress/zstd_ddict.c +244 -0
  64. data/contrib/zstd/lib/decompress/zstd_ddict.h +44 -0
  65. data/contrib/zstd/lib/decompress/zstd_decompress.c +1930 -0
  66. data/contrib/zstd/lib/decompress/zstd_decompress_block.c +1540 -0
  67. data/contrib/zstd/lib/decompress/zstd_decompress_block.h +62 -0
  68. data/contrib/zstd/lib/decompress/zstd_decompress_internal.h +190 -0
  69. data/contrib/zstd/{common → lib/deprecated}/zbuff.h +68 -45
  70. data/contrib/zstd/lib/deprecated/zbuff_common.c +26 -0
  71. data/contrib/zstd/lib/deprecated/zbuff_compress.c +147 -0
  72. data/contrib/zstd/lib/deprecated/zbuff_decompress.c +75 -0
  73. data/contrib/zstd/lib/dictBuilder/cover.c +1245 -0
  74. data/contrib/zstd/lib/dictBuilder/cover.h +157 -0
  75. data/contrib/zstd/{dictBuilder → lib/dictBuilder}/divsufsort.c +3 -3
  76. data/contrib/zstd/{dictBuilder → lib/dictBuilder}/divsufsort.h +0 -0
  77. data/contrib/zstd/lib/dictBuilder/fastcover.c +758 -0
  78. data/contrib/zstd/{dictBuilder → lib/dictBuilder}/zdict.c +318 -194
  79. data/contrib/zstd/lib/dictBuilder/zdict.h +305 -0
  80. data/contrib/zstd/{legacy → lib/legacy}/zstd_legacy.h +171 -15
  81. data/contrib/zstd/{legacy → lib/legacy}/zstd_v01.c +191 -124
  82. data/contrib/zstd/{legacy → lib/legacy}/zstd_v01.h +19 -5
  83. data/contrib/zstd/{legacy → lib/legacy}/zstd_v02.c +125 -125
  84. data/contrib/zstd/{legacy → lib/legacy}/zstd_v02.h +19 -5
  85. data/contrib/zstd/{legacy → lib/legacy}/zstd_v03.c +125 -124
  86. data/contrib/zstd/{legacy → lib/legacy}/zstd_v03.h +20 -6
  87. data/contrib/zstd/{legacy → lib/legacy}/zstd_v04.c +151 -299
  88. data/contrib/zstd/{legacy → lib/legacy}/zstd_v04.h +19 -5
  89. data/contrib/zstd/{legacy → lib/legacy}/zstd_v05.c +237 -243
  90. data/contrib/zstd/{legacy → lib/legacy}/zstd_v05.h +19 -6
  91. data/contrib/zstd/{legacy → lib/legacy}/zstd_v06.c +130 -143
  92. data/contrib/zstd/{legacy → lib/legacy}/zstd_v06.h +18 -5
  93. data/contrib/zstd/{legacy → lib/legacy}/zstd_v07.c +158 -157
  94. data/contrib/zstd/{legacy → lib/legacy}/zstd_v07.h +19 -5
  95. data/contrib/zstd/lib/libzstd.pc.in +15 -0
  96. data/contrib/zstd/lib/zstd.h +2391 -0
  97. data/ext/depend +2 -0
  98. data/ext/extconf.rb +15 -6
  99. data/ext/extzstd.c +76 -145
  100. data/ext/extzstd.h +80 -31
  101. data/ext/extzstd_stream.c +417 -142
  102. data/ext/libzstd_conf.h +8 -0
  103. data/ext/zstd_common.c +10 -7
  104. data/ext/zstd_compress.c +14 -5
  105. data/ext/zstd_decompress.c +5 -4
  106. data/ext/zstd_dictbuilder.c +9 -4
  107. data/ext/zstd_dictbuilder_fastcover.c +3 -0
  108. data/ext/zstd_legacy_v01.c +3 -1
  109. data/ext/zstd_legacy_v02.c +3 -1
  110. data/ext/zstd_legacy_v03.c +3 -1
  111. data/ext/zstd_legacy_v04.c +3 -1
  112. data/ext/zstd_legacy_v05.c +3 -1
  113. data/ext/zstd_legacy_v06.c +3 -1
  114. data/ext/zstd_legacy_v07.c +3 -1
  115. data/gemstub.rb +10 -24
  116. data/lib/extzstd.rb +64 -179
  117. data/lib/extzstd/version.rb +6 -1
  118. data/test/test_basic.rb +9 -6
  119. metadata +113 -57
  120. data/HISTORY.ja +0 -5
  121. data/contrib/zstd/common/entropy_common.c +0 -225
  122. data/contrib/zstd/common/huf.h +0 -228
  123. data/contrib/zstd/common/zstd_common.c +0 -83
  124. data/contrib/zstd/common/zstd_errors.h +0 -60
  125. data/contrib/zstd/common/zstd_internal.h +0 -267
  126. data/contrib/zstd/compress/huf_compress.c +0 -533
  127. data/contrib/zstd/compress/zbuff_compress.c +0 -319
  128. data/contrib/zstd/compress/zstd_compress.c +0 -3264
  129. data/contrib/zstd/compress/zstd_opt.h +0 -900
  130. data/contrib/zstd/decompress/huf_decompress.c +0 -883
  131. data/contrib/zstd/decompress/zbuff_decompress.c +0 -252
  132. data/contrib/zstd/decompress/zstd_decompress.c +0 -1842
  133. data/contrib/zstd/dictBuilder/zdict.h +0 -111
  134. data/contrib/zstd/zstd.h +0 -640
@@ -0,0 +1,288 @@
1
+ /*
2
+ * Copyright (c) 2016-2020, Yann Collet, Facebook, Inc.
3
+ * All rights reserved.
4
+ *
5
+ * This source code is licensed under both the BSD-style license (found in the
6
+ * LICENSE file in the root directory of this source tree) and the GPLv2 (found
7
+ * in the COPYING file in the root directory of this source tree).
8
+ * You may select, at your option, one of the above-listed licenses.
9
+ */
10
+
11
+ #ifndef ZSTD_COMPILER_H
12
+ #define ZSTD_COMPILER_H
13
+
14
+ /*-*******************************************************
15
+ * Compiler specifics
16
+ *********************************************************/
17
+ /* force inlining */
18
+
19
+ #if !defined(ZSTD_NO_INLINE)
20
+ #if (defined(__GNUC__) && !defined(__STRICT_ANSI__)) || defined(__cplusplus) || defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L /* C99 */
21
+ # define INLINE_KEYWORD inline
22
+ #else
23
+ # define INLINE_KEYWORD
24
+ #endif
25
+
26
+ #if defined(__GNUC__) || defined(__ICCARM__)
27
+ # define FORCE_INLINE_ATTR __attribute__((always_inline))
28
+ #elif defined(_MSC_VER)
29
+ # define FORCE_INLINE_ATTR __forceinline
30
+ #else
31
+ # define FORCE_INLINE_ATTR
32
+ #endif
33
+
34
+ #else
35
+
36
+ #define INLINE_KEYWORD
37
+ #define FORCE_INLINE_ATTR
38
+
39
+ #endif
40
+
41
+ /**
42
+ On MSVC qsort requires that functions passed into it use the __cdecl calling conversion(CC).
43
+ This explictly marks such functions as __cdecl so that the code will still compile
44
+ if a CC other than __cdecl has been made the default.
45
+ */
46
+ #if defined(_MSC_VER)
47
+ # define WIN_CDECL __cdecl
48
+ #else
49
+ # define WIN_CDECL
50
+ #endif
51
+
52
+ /**
53
+ * FORCE_INLINE_TEMPLATE is used to define C "templates", which take constant
54
+ * parameters. They must be inlined for the compiler to eliminate the constant
55
+ * branches.
56
+ */
57
+ #define FORCE_INLINE_TEMPLATE static INLINE_KEYWORD FORCE_INLINE_ATTR
58
+ /**
59
+ * HINT_INLINE is used to help the compiler generate better code. It is *not*
60
+ * used for "templates", so it can be tweaked based on the compilers
61
+ * performance.
62
+ *
63
+ * gcc-4.8 and gcc-4.9 have been shown to benefit from leaving off the
64
+ * always_inline attribute.
65
+ *
66
+ * clang up to 5.0.0 (trunk) benefit tremendously from the always_inline
67
+ * attribute.
68
+ */
69
+ #if !defined(__clang__) && defined(__GNUC__) && __GNUC__ >= 4 && __GNUC_MINOR__ >= 8 && __GNUC__ < 5
70
+ # define HINT_INLINE static INLINE_KEYWORD
71
+ #else
72
+ # define HINT_INLINE static INLINE_KEYWORD FORCE_INLINE_ATTR
73
+ #endif
74
+
75
+ /* UNUSED_ATTR tells the compiler it is okay if the function is unused. */
76
+ #if defined(__GNUC__)
77
+ # define UNUSED_ATTR __attribute__((unused))
78
+ #else
79
+ # define UNUSED_ATTR
80
+ #endif
81
+
82
+ /* force no inlining */
83
+ #ifdef _MSC_VER
84
+ # define FORCE_NOINLINE static __declspec(noinline)
85
+ #else
86
+ # if defined(__GNUC__) || defined(__ICCARM__)
87
+ # define FORCE_NOINLINE static __attribute__((__noinline__))
88
+ # else
89
+ # define FORCE_NOINLINE static
90
+ # endif
91
+ #endif
92
+
93
+ /* target attribute */
94
+ #ifndef __has_attribute
95
+ #define __has_attribute(x) 0 /* Compatibility with non-clang compilers. */
96
+ #endif
97
+ #if defined(__GNUC__) || defined(__ICCARM__)
98
+ # define TARGET_ATTRIBUTE(target) __attribute__((__target__(target)))
99
+ #else
100
+ # define TARGET_ATTRIBUTE(target)
101
+ #endif
102
+
103
+ /* Enable runtime BMI2 dispatch based on the CPU.
104
+ * Enabled for clang & gcc >=4.8 on x86 when BMI2 isn't enabled by default.
105
+ */
106
+ #ifndef DYNAMIC_BMI2
107
+ #if ((defined(__clang__) && __has_attribute(__target__)) \
108
+ || (defined(__GNUC__) \
109
+ && (__GNUC__ >= 5 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 8)))) \
110
+ && (defined(__x86_64__) || defined(_M_X86)) \
111
+ && !defined(__BMI2__)
112
+ # define DYNAMIC_BMI2 1
113
+ #else
114
+ # define DYNAMIC_BMI2 0
115
+ #endif
116
+ #endif
117
+
118
+ /* prefetch
119
+ * can be disabled, by declaring NO_PREFETCH build macro */
120
+ #if defined(NO_PREFETCH)
121
+ # define PREFETCH_L1(ptr) (void)(ptr) /* disabled */
122
+ # define PREFETCH_L2(ptr) (void)(ptr) /* disabled */
123
+ #else
124
+ # if defined(_MSC_VER) && (defined(_M_X64) || defined(_M_I86)) /* _mm_prefetch() is not defined outside of x86/x64 */
125
+ # include <mmintrin.h> /* https://msdn.microsoft.com/fr-fr/library/84szxsww(v=vs.90).aspx */
126
+ # define PREFETCH_L1(ptr) _mm_prefetch((const char*)(ptr), _MM_HINT_T0)
127
+ # define PREFETCH_L2(ptr) _mm_prefetch((const char*)(ptr), _MM_HINT_T1)
128
+ # elif defined(__GNUC__) && ( (__GNUC__ >= 4) || ( (__GNUC__ == 3) && (__GNUC_MINOR__ >= 1) ) )
129
+ # define PREFETCH_L1(ptr) __builtin_prefetch((ptr), 0 /* rw==read */, 3 /* locality */)
130
+ # define PREFETCH_L2(ptr) __builtin_prefetch((ptr), 0 /* rw==read */, 2 /* locality */)
131
+ # elif defined(__aarch64__)
132
+ # define PREFETCH_L1(ptr) __asm__ __volatile__("prfm pldl1keep, %0" ::"Q"(*(ptr)))
133
+ # define PREFETCH_L2(ptr) __asm__ __volatile__("prfm pldl2keep, %0" ::"Q"(*(ptr)))
134
+ # else
135
+ # define PREFETCH_L1(ptr) (void)(ptr) /* disabled */
136
+ # define PREFETCH_L2(ptr) (void)(ptr) /* disabled */
137
+ # endif
138
+ #endif /* NO_PREFETCH */
139
+
140
+ #define CACHELINE_SIZE 64
141
+
142
+ #define PREFETCH_AREA(p, s) { \
143
+ const char* const _ptr = (const char*)(p); \
144
+ size_t const _size = (size_t)(s); \
145
+ size_t _pos; \
146
+ for (_pos=0; _pos<_size; _pos+=CACHELINE_SIZE) { \
147
+ PREFETCH_L2(_ptr + _pos); \
148
+ } \
149
+ }
150
+
151
+ /* vectorization
152
+ * older GCC (pre gcc-4.3 picked as the cutoff) uses a different syntax */
153
+ #if !defined(__INTEL_COMPILER) && !defined(__clang__) && defined(__GNUC__)
154
+ # if (__GNUC__ == 4 && __GNUC_MINOR__ > 3) || (__GNUC__ >= 5)
155
+ # define DONT_VECTORIZE __attribute__((optimize("no-tree-vectorize")))
156
+ # else
157
+ # define DONT_VECTORIZE _Pragma("GCC optimize(\"no-tree-vectorize\")")
158
+ # endif
159
+ #else
160
+ # define DONT_VECTORIZE
161
+ #endif
162
+
163
+ /* Tell the compiler that a branch is likely or unlikely.
164
+ * Only use these macros if it causes the compiler to generate better code.
165
+ * If you can remove a LIKELY/UNLIKELY annotation without speed changes in gcc
166
+ * and clang, please do.
167
+ */
168
+ #if defined(__GNUC__)
169
+ #define LIKELY(x) (__builtin_expect((x), 1))
170
+ #define UNLIKELY(x) (__builtin_expect((x), 0))
171
+ #else
172
+ #define LIKELY(x) (x)
173
+ #define UNLIKELY(x) (x)
174
+ #endif
175
+
176
+ /* disable warnings */
177
+ #ifdef _MSC_VER /* Visual Studio */
178
+ # include <intrin.h> /* For Visual 2005 */
179
+ # pragma warning(disable : 4100) /* disable: C4100: unreferenced formal parameter */
180
+ # pragma warning(disable : 4127) /* disable: C4127: conditional expression is constant */
181
+ # pragma warning(disable : 4204) /* disable: C4204: non-constant aggregate initializer */
182
+ # pragma warning(disable : 4214) /* disable: C4214: non-int bitfields */
183
+ # pragma warning(disable : 4324) /* disable: C4324: padded structure */
184
+ #endif
185
+
186
+ /*Like DYNAMIC_BMI2 but for compile time determination of BMI2 support*/
187
+ #ifndef STATIC_BMI2
188
+ # if defined(_MSC_VER) && (defined(_M_X64) || defined(_M_I86))
189
+ # ifdef __AVX2__ //MSVC does not have a BMI2 specific flag, but every CPU that supports AVX2 also supports BMI2
190
+ # define STATIC_BMI2 1
191
+ # endif
192
+ # endif
193
+ #endif
194
+
195
+ #ifndef STATIC_BMI2
196
+ #define STATIC_BMI2 0
197
+ #endif
198
+
199
+ /* compat. with non-clang compilers */
200
+ #ifndef __has_builtin
201
+ # define __has_builtin(x) 0
202
+ #endif
203
+
204
+ /* compat. with non-clang compilers */
205
+ #ifndef __has_feature
206
+ # define __has_feature(x) 0
207
+ #endif
208
+
209
+ /* detects whether we are being compiled under msan */
210
+ #ifndef ZSTD_MEMORY_SANITIZER
211
+ # if __has_feature(memory_sanitizer)
212
+ # define ZSTD_MEMORY_SANITIZER 1
213
+ # else
214
+ # define ZSTD_MEMORY_SANITIZER 0
215
+ # endif
216
+ #endif
217
+
218
+ #if ZSTD_MEMORY_SANITIZER
219
+ /* Not all platforms that support msan provide sanitizers/msan_interface.h.
220
+ * We therefore declare the functions we need ourselves, rather than trying to
221
+ * include the header file... */
222
+ #include <stddef.h> /* size_t */
223
+ #define ZSTD_DEPS_NEED_STDINT
224
+ #include "zstd_deps.h" /* intptr_t */
225
+
226
+ /* Make memory region fully initialized (without changing its contents). */
227
+ void __msan_unpoison(const volatile void *a, size_t size);
228
+
229
+ /* Make memory region fully uninitialized (without changing its contents).
230
+ This is a legacy interface that does not update origin information. Use
231
+ __msan_allocated_memory() instead. */
232
+ void __msan_poison(const volatile void *a, size_t size);
233
+
234
+ /* Returns the offset of the first (at least partially) poisoned byte in the
235
+ memory range, or -1 if the whole range is good. */
236
+ intptr_t __msan_test_shadow(const volatile void *x, size_t size);
237
+ #endif
238
+
239
+ /* detects whether we are being compiled under asan */
240
+ #ifndef ZSTD_ADDRESS_SANITIZER
241
+ # if __has_feature(address_sanitizer)
242
+ # define ZSTD_ADDRESS_SANITIZER 1
243
+ # elif defined(__SANITIZE_ADDRESS__)
244
+ # define ZSTD_ADDRESS_SANITIZER 1
245
+ # else
246
+ # define ZSTD_ADDRESS_SANITIZER 0
247
+ # endif
248
+ #endif
249
+
250
+ #if ZSTD_ADDRESS_SANITIZER
251
+ /* Not all platforms that support asan provide sanitizers/asan_interface.h.
252
+ * We therefore declare the functions we need ourselves, rather than trying to
253
+ * include the header file... */
254
+ #include <stddef.h> /* size_t */
255
+
256
+ /**
257
+ * Marks a memory region (<c>[addr, addr+size)</c>) as unaddressable.
258
+ *
259
+ * This memory must be previously allocated by your program. Instrumented
260
+ * code is forbidden from accessing addresses in this region until it is
261
+ * unpoisoned. This function is not guaranteed to poison the entire region -
262
+ * it could poison only a subregion of <c>[addr, addr+size)</c> due to ASan
263
+ * alignment restrictions.
264
+ *
265
+ * \note This function is not thread-safe because no two threads can poison or
266
+ * unpoison memory in the same memory region simultaneously.
267
+ *
268
+ * \param addr Start of memory region.
269
+ * \param size Size of memory region. */
270
+ void __asan_poison_memory_region(void const volatile *addr, size_t size);
271
+
272
+ /**
273
+ * Marks a memory region (<c>[addr, addr+size)</c>) as addressable.
274
+ *
275
+ * This memory must be previously allocated by your program. Accessing
276
+ * addresses in this region is allowed until this region is poisoned again.
277
+ * This function could unpoison a super-region of <c>[addr, addr+size)</c> due
278
+ * to ASan alignment restrictions.
279
+ *
280
+ * \note This function is not thread-safe because no two threads can
281
+ * poison or unpoison memory in the same memory region simultaneously.
282
+ *
283
+ * \param addr Start of memory region.
284
+ * \param size Size of memory region. */
285
+ void __asan_unpoison_memory_region(void const volatile *addr, size_t size);
286
+ #endif
287
+
288
+ #endif /* ZSTD_COMPILER_H */
@@ -0,0 +1,213 @@
1
+ /*
2
+ * Copyright (c) 2018-2020, Facebook, Inc.
3
+ * All rights reserved.
4
+ *
5
+ * This source code is licensed under both the BSD-style license (found in the
6
+ * LICENSE file in the root directory of this source tree) and the GPLv2 (found
7
+ * in the COPYING file in the root directory of this source tree).
8
+ * You may select, at your option, one of the above-listed licenses.
9
+ */
10
+
11
+ #ifndef ZSTD_COMMON_CPU_H
12
+ #define ZSTD_COMMON_CPU_H
13
+
14
+ /**
15
+ * Implementation taken from folly/CpuId.h
16
+ * https://github.com/facebook/folly/blob/master/folly/CpuId.h
17
+ */
18
+
19
+ #include "mem.h"
20
+
21
+ #ifdef _MSC_VER
22
+ #include <intrin.h>
23
+ #endif
24
+
25
+ typedef struct {
26
+ U32 f1c;
27
+ U32 f1d;
28
+ U32 f7b;
29
+ U32 f7c;
30
+ } ZSTD_cpuid_t;
31
+
32
+ MEM_STATIC ZSTD_cpuid_t ZSTD_cpuid(void) {
33
+ U32 f1c = 0;
34
+ U32 f1d = 0;
35
+ U32 f7b = 0;
36
+ U32 f7c = 0;
37
+ #if defined(_MSC_VER) && (defined(_M_X64) || defined(_M_IX86))
38
+ int reg[4];
39
+ __cpuid((int*)reg, 0);
40
+ {
41
+ int const n = reg[0];
42
+ if (n >= 1) {
43
+ __cpuid((int*)reg, 1);
44
+ f1c = (U32)reg[2];
45
+ f1d = (U32)reg[3];
46
+ }
47
+ if (n >= 7) {
48
+ __cpuidex((int*)reg, 7, 0);
49
+ f7b = (U32)reg[1];
50
+ f7c = (U32)reg[2];
51
+ }
52
+ }
53
+ #elif defined(__i386__) && defined(__PIC__) && !defined(__clang__) && defined(__GNUC__)
54
+ /* The following block like the normal cpuid branch below, but gcc
55
+ * reserves ebx for use of its pic register so we must specially
56
+ * handle the save and restore to avoid clobbering the register
57
+ */
58
+ U32 n;
59
+ __asm__(
60
+ "pushl %%ebx\n\t"
61
+ "cpuid\n\t"
62
+ "popl %%ebx\n\t"
63
+ : "=a"(n)
64
+ : "a"(0)
65
+ : "ecx", "edx");
66
+ if (n >= 1) {
67
+ U32 f1a;
68
+ __asm__(
69
+ "pushl %%ebx\n\t"
70
+ "cpuid\n\t"
71
+ "popl %%ebx\n\t"
72
+ : "=a"(f1a), "=c"(f1c), "=d"(f1d)
73
+ : "a"(1));
74
+ }
75
+ if (n >= 7) {
76
+ __asm__(
77
+ "pushl %%ebx\n\t"
78
+ "cpuid\n\t"
79
+ "movl %%ebx, %%eax\n\t"
80
+ "popl %%ebx"
81
+ : "=a"(f7b), "=c"(f7c)
82
+ : "a"(7), "c"(0)
83
+ : "edx");
84
+ }
85
+ #elif defined(__x86_64__) || defined(_M_X64) || defined(__i386__)
86
+ U32 n;
87
+ __asm__("cpuid" : "=a"(n) : "a"(0) : "ebx", "ecx", "edx");
88
+ if (n >= 1) {
89
+ U32 f1a;
90
+ __asm__("cpuid" : "=a"(f1a), "=c"(f1c), "=d"(f1d) : "a"(1) : "ebx");
91
+ }
92
+ if (n >= 7) {
93
+ U32 f7a;
94
+ __asm__("cpuid"
95
+ : "=a"(f7a), "=b"(f7b), "=c"(f7c)
96
+ : "a"(7), "c"(0)
97
+ : "edx");
98
+ }
99
+ #endif
100
+ {
101
+ ZSTD_cpuid_t cpuid;
102
+ cpuid.f1c = f1c;
103
+ cpuid.f1d = f1d;
104
+ cpuid.f7b = f7b;
105
+ cpuid.f7c = f7c;
106
+ return cpuid;
107
+ }
108
+ }
109
+
110
+ #define X(name, r, bit) \
111
+ MEM_STATIC int ZSTD_cpuid_##name(ZSTD_cpuid_t const cpuid) { \
112
+ return ((cpuid.r) & (1U << bit)) != 0; \
113
+ }
114
+
115
+ /* cpuid(1): Processor Info and Feature Bits. */
116
+ #define C(name, bit) X(name, f1c, bit)
117
+ C(sse3, 0)
118
+ C(pclmuldq, 1)
119
+ C(dtes64, 2)
120
+ C(monitor, 3)
121
+ C(dscpl, 4)
122
+ C(vmx, 5)
123
+ C(smx, 6)
124
+ C(eist, 7)
125
+ C(tm2, 8)
126
+ C(ssse3, 9)
127
+ C(cnxtid, 10)
128
+ C(fma, 12)
129
+ C(cx16, 13)
130
+ C(xtpr, 14)
131
+ C(pdcm, 15)
132
+ C(pcid, 17)
133
+ C(dca, 18)
134
+ C(sse41, 19)
135
+ C(sse42, 20)
136
+ C(x2apic, 21)
137
+ C(movbe, 22)
138
+ C(popcnt, 23)
139
+ C(tscdeadline, 24)
140
+ C(aes, 25)
141
+ C(xsave, 26)
142
+ C(osxsave, 27)
143
+ C(avx, 28)
144
+ C(f16c, 29)
145
+ C(rdrand, 30)
146
+ #undef C
147
+ #define D(name, bit) X(name, f1d, bit)
148
+ D(fpu, 0)
149
+ D(vme, 1)
150
+ D(de, 2)
151
+ D(pse, 3)
152
+ D(tsc, 4)
153
+ D(msr, 5)
154
+ D(pae, 6)
155
+ D(mce, 7)
156
+ D(cx8, 8)
157
+ D(apic, 9)
158
+ D(sep, 11)
159
+ D(mtrr, 12)
160
+ D(pge, 13)
161
+ D(mca, 14)
162
+ D(cmov, 15)
163
+ D(pat, 16)
164
+ D(pse36, 17)
165
+ D(psn, 18)
166
+ D(clfsh, 19)
167
+ D(ds, 21)
168
+ D(acpi, 22)
169
+ D(mmx, 23)
170
+ D(fxsr, 24)
171
+ D(sse, 25)
172
+ D(sse2, 26)
173
+ D(ss, 27)
174
+ D(htt, 28)
175
+ D(tm, 29)
176
+ D(pbe, 31)
177
+ #undef D
178
+
179
+ /* cpuid(7): Extended Features. */
180
+ #define B(name, bit) X(name, f7b, bit)
181
+ B(bmi1, 3)
182
+ B(hle, 4)
183
+ B(avx2, 5)
184
+ B(smep, 7)
185
+ B(bmi2, 8)
186
+ B(erms, 9)
187
+ B(invpcid, 10)
188
+ B(rtm, 11)
189
+ B(mpx, 14)
190
+ B(avx512f, 16)
191
+ B(avx512dq, 17)
192
+ B(rdseed, 18)
193
+ B(adx, 19)
194
+ B(smap, 20)
195
+ B(avx512ifma, 21)
196
+ B(pcommit, 22)
197
+ B(clflushopt, 23)
198
+ B(clwb, 24)
199
+ B(avx512pf, 26)
200
+ B(avx512er, 27)
201
+ B(avx512cd, 28)
202
+ B(sha, 29)
203
+ B(avx512bw, 30)
204
+ B(avx512vl, 31)
205
+ #undef B
206
+ #define C(name, bit) X(name, f7c, bit)
207
+ C(prefetchwt1, 0)
208
+ C(avx512vbmi, 1)
209
+ #undef C
210
+
211
+ #undef X
212
+
213
+ #endif /* ZSTD_COMMON_CPU_H */