blob: 5af6832949757ebae3aea2fdc5968d9622946bbb [file] [log] [blame]
Jason Evansd81e4bd2012-03-06 14:57:45 -08001/******************************************************************************/
2#ifdef JEMALLOC_H_TYPES
3
4/* Size of stack-allocated buffer passed to buferror(). */
5#define BUFERROR_BUF 64
6
7/*
Jason Evanscd9a1342012-03-21 18:33:03 -07008 * Size of stack-allocated buffer used by malloc_{,v,vc}printf(). This must be
9 * large enough for all possible uses within jemalloc.
Jason Evans824d34e2012-03-13 13:19:04 -070010 */
11#define MALLOC_PRINTF_BUFSIZE 4096
12
13/*
Jason Evanscd9a1342012-03-21 18:33:03 -070014 * Wrap a cpp argument that contains commas such that it isn't broken up into
15 * multiple arguments.
16 */
Jason Evansa4f124f2013-12-08 22:28:27 -080017#define JEMALLOC_ARG_CONCAT(...) __VA_ARGS__
Jason Evanscd9a1342012-03-21 18:33:03 -070018
19/*
Jason Evans9225a192012-03-23 15:39:07 -070020 * Silence compiler warnings due to uninitialized values. This is used
21 * wherever the compiler fails to recognize that the variable is never used
22 * uninitialized.
23 */
24#ifdef JEMALLOC_CC_SILENCE
25# define JEMALLOC_CC_SILENCE_INIT(v) = v
26#else
27# define JEMALLOC_CC_SILENCE_INIT(v)
28#endif
29
Daniel Micay6b5609d2014-09-08 22:18:49 -040030#ifdef __GNUC__
31#define likely(x) __builtin_expect(!!(x), 1)
32#define unlikely(x) __builtin_expect(!!(x), 0)
33#else
34#define likely(x) !!(x)
35#define unlikely(x) !!(x)
36#endif
37
Jason Evans9225a192012-03-23 15:39:07 -070038/*
Jason Evansd81e4bd2012-03-06 14:57:45 -080039 * Define a custom assert() in order to reduce the chances of deadlock during
40 * assertion failure.
41 */
42#ifndef assert
43#define assert(e) do { \
Daniel Micay23fdf8b2014-09-09 15:26:05 -040044 if (unlikely(config_debug && !(e))) { \
Jason Evansd81e4bd2012-03-06 14:57:45 -080045 malloc_printf( \
46 "<jemalloc>: %s:%d: Failed assertion: \"%s\"\n", \
47 __FILE__, __LINE__, #e); \
48 abort(); \
49 } \
50} while (0)
51#endif
52
Jason Evansd81e4bd2012-03-06 14:57:45 -080053#ifndef not_reached
54#define not_reached() do { \
55 if (config_debug) { \
56 malloc_printf( \
57 "<jemalloc>: %s:%d: Unreachable code reached\n", \
58 __FILE__, __LINE__); \
59 abort(); \
60 } \
61} while (0)
62#endif
63
64#ifndef not_implemented
65#define not_implemented() do { \
66 if (config_debug) { \
67 malloc_printf("<jemalloc>: %s:%d: Not implemented\n", \
68 __FILE__, __LINE__); \
69 abort(); \
70 } \
71} while (0)
72#endif
73
Jason Evans86abd0d2013-11-30 15:25:42 -080074#ifndef assert_not_implemented
Jason Evansd81e4bd2012-03-06 14:57:45 -080075#define assert_not_implemented(e) do { \
Daniel Micay23fdf8b2014-09-09 15:26:05 -040076 if (unlikely(config_debug && !(e))) \
Jason Evansd81e4bd2012-03-06 14:57:45 -080077 not_implemented(); \
78} while (0)
Jason Evans86abd0d2013-11-30 15:25:42 -080079#endif
Jason Evansd81e4bd2012-03-06 14:57:45 -080080
Jason Evans6556e282013-10-21 14:56:27 -070081/* Use to assert a particular configuration, e.g., cassert(config_debug). */
82#define cassert(c) do { \
Daniel Micay23fdf8b2014-09-09 15:26:05 -040083 if (unlikely(!(c))) \
Jason Evans6556e282013-10-21 14:56:27 -070084 not_reached(); \
85} while (0)
86
Jason Evansd81e4bd2012-03-06 14:57:45 -080087#endif /* JEMALLOC_H_TYPES */
88/******************************************************************************/
89#ifdef JEMALLOC_H_STRUCTS
90
91#endif /* JEMALLOC_H_STRUCTS */
92/******************************************************************************/
93#ifdef JEMALLOC_H_EXTERNS
94
Jason Evans2a83ed02013-12-08 20:52:21 -080095int buferror(int err, char *buf, size_t buflen);
Jason Evanse18c25d2014-01-06 20:33:48 -080096uintmax_t malloc_strtoumax(const char *restrict nptr,
97 char **restrict endptr, int base);
Jason Evans889ec592012-05-02 02:08:03 -070098void malloc_write(const char *s);
Jason Evansd81e4bd2012-03-06 14:57:45 -080099
100/*
101 * malloc_vsnprintf() supports a subset of snprintf(3) that avoids floating
102 * point math.
103 */
104int malloc_vsnprintf(char *str, size_t size, const char *format,
105 va_list ap);
106int malloc_snprintf(char *str, size_t size, const char *format, ...)
107 JEMALLOC_ATTR(format(printf, 3, 4));
Jason Evansd81e4bd2012-03-06 14:57:45 -0800108void malloc_vcprintf(void (*write_cb)(void *, const char *), void *cbopaque,
109 const char *format, va_list ap);
110void malloc_cprintf(void (*write)(void *, const char *), void *cbopaque,
111 const char *format, ...) JEMALLOC_ATTR(format(printf, 3, 4));
112void malloc_printf(const char *format, ...)
113 JEMALLOC_ATTR(format(printf, 1, 2));
114
115#endif /* JEMALLOC_H_EXTERNS */
116/******************************************************************************/
117#ifdef JEMALLOC_H_INLINES
118
119#ifndef JEMALLOC_ENABLE_INLINE
Richard Diamond9c3a10f2014-05-28 21:37:02 -0500120int jemalloc_ffsl(long bitmap);
121int jemalloc_ffs(int bitmap);
Jason Evansd81e4bd2012-03-06 14:57:45 -0800122size_t pow2_ceil(size_t x);
Jason Evansd04047c2014-05-28 16:11:55 -0700123size_t lg_floor(size_t x);
Mike Hommeya14bce82012-04-30 12:38:26 +0200124void set_errno(int errnum);
125int get_errno(void);
Jason Evansd81e4bd2012-03-06 14:57:45 -0800126#endif
127
128#if (defined(JEMALLOC_ENABLE_INLINE) || defined(JEMALLOC_UTIL_C_))
Richard Diamond9c3a10f2014-05-28 21:37:02 -0500129
130/* Sanity check: */
131#if !defined(JEMALLOC_INTERNAL_FFSL) || !defined(JEMALLOC_INTERNAL_FFS)
132# error Both JEMALLOC_INTERNAL_FFSL && JEMALLOC_INTERNAL_FFS should have been defined by configure
133#endif
134
135JEMALLOC_ALWAYS_INLINE int
136jemalloc_ffsl(long bitmap)
137{
138
139 return (JEMALLOC_INTERNAL_FFSL(bitmap));
140}
141
142JEMALLOC_ALWAYS_INLINE int
143jemalloc_ffs(int bitmap)
144{
145
146 return (JEMALLOC_INTERNAL_FFS(bitmap));
147}
148
Jason Evansd81e4bd2012-03-06 14:57:45 -0800149/* Compute the smallest power of 2 that is >= x. */
150JEMALLOC_INLINE size_t
151pow2_ceil(size_t x)
152{
153
154 x--;
155 x |= x >> 1;
156 x |= x >> 2;
157 x |= x >> 4;
158 x |= x >> 8;
159 x |= x >> 16;
160#if (LG_SIZEOF_PTR == 3)
161 x |= x >> 32;
162#endif
163 x++;
164 return (x);
165}
166
Jason Evansd04047c2014-05-28 16:11:55 -0700167#if (defined(__i386__) || defined(__amd64__) || defined(__x86_64__))
168JEMALLOC_INLINE size_t
169lg_floor(size_t x)
170{
171 size_t ret;
172
173 asm ("bsr %1, %0"
174 : "=r"(ret) // Outputs.
175 : "r"(x) // Inputs.
176 );
177 return (ret);
178}
Dave Rigby112704c2014-09-22 15:54:33 +0100179#elif (defined(_MSC_VER))
180JEMALLOC_INLINE size_t
181lg_floor(size_t x)
182{
183 unsigned long ret;
184
185#if (LG_SIZEOF_PTR == 3)
186 _BitScanReverse64(&ret, x);
187#elif (LG_SIZEOF_PTR == 2)
188 _BitScanReverse(&ret, x);
189#else
190# error "Unsupported type sizes for lg_floor()"
191#endif
192 return (ret);
193}
Jason Evansd04047c2014-05-28 16:11:55 -0700194#elif (defined(JEMALLOC_HAVE_BUILTIN_CLZ))
195JEMALLOC_INLINE size_t
196lg_floor(size_t x)
197{
198
199#if (LG_SIZEOF_PTR == LG_SIZEOF_INT)
Jason Evans0b5c9222014-06-01 22:05:08 -0700200 return (((8 << LG_SIZEOF_PTR) - 1) - __builtin_clz(x));
Jason Evansd04047c2014-05-28 16:11:55 -0700201#elif (LG_SIZEOF_PTR == LG_SIZEOF_LONG)
Jason Evans0b5c9222014-06-01 22:05:08 -0700202 return (((8 << LG_SIZEOF_PTR) - 1) - __builtin_clzl(x));
Jason Evansd04047c2014-05-28 16:11:55 -0700203#else
204# error "Unsupported type sizes for lg_floor()"
205#endif
206}
207#else
208JEMALLOC_INLINE size_t
209lg_floor(size_t x)
210{
211
Jason Evans0b5c9222014-06-01 22:05:08 -0700212 x |= (x >> 1);
213 x |= (x >> 2);
214 x |= (x >> 4);
215 x |= (x >> 8);
216 x |= (x >> 16);
Jason Evansd04047c2014-05-28 16:11:55 -0700217#if (LG_SIZEOF_PTR == 3 && LG_SIZEOF_PTR == LG_SIZEOF_LONG)
Jason Evans0b5c9222014-06-01 22:05:08 -0700218 x |= (x >> 32);
219 if (x == KZU(0xffffffffffffffff))
220 return (63);
221 x++;
Richard Diamond9c3a10f2014-05-28 21:37:02 -0500222 return (jemalloc_ffsl(x) - 2);
Jason Evansd04047c2014-05-28 16:11:55 -0700223#elif (LG_SIZEOF_PTR == 2)
Jason Evans0b5c9222014-06-01 22:05:08 -0700224 if (x == KZU(0xffffffff))
225 return (31);
226 x++;
Richard Diamond9c3a10f2014-05-28 21:37:02 -0500227 return (jemalloc_ffs(x) - 2);
Jason Evansd04047c2014-05-28 16:11:55 -0700228#else
229# error "Unsupported type sizes for lg_floor()"
230#endif
231}
232#endif
233
Mike Hommeya14bce82012-04-30 12:38:26 +0200234/* Sets error code */
235JEMALLOC_INLINE void
236set_errno(int errnum)
237{
238
239#ifdef _WIN32
240 SetLastError(errnum);
241#else
242 errno = errnum;
243#endif
244}
245
246/* Get last error code */
247JEMALLOC_INLINE int
248get_errno(void)
249{
250
251#ifdef _WIN32
Mike Hommey7cdea392012-04-30 12:38:27 +0200252 return (GetLastError());
Mike Hommeya14bce82012-04-30 12:38:26 +0200253#else
Mike Hommey7cdea392012-04-30 12:38:27 +0200254 return (errno);
Mike Hommeya14bce82012-04-30 12:38:26 +0200255#endif
256}
Jason Evansd81e4bd2012-03-06 14:57:45 -0800257#endif
258
259#endif /* JEMALLOC_H_INLINES */
260/******************************************************************************/