summaryrefslogtreecommitdiff
path: root/libyasm/util.h
blob: 71464ed24cd70c56e42dbc72d69abb8ea785602a (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
/**
 * \file util.h
 * \brief YASM utility functions.
 *
 * $IdPath: yasm/libyasm/util.h,v 1.50 2003/05/03 08:02:15 peter Exp $
 *
 * Includes standard headers and defines prototypes for replacement functions
 * if needed.  This is the *only* header file which should include other
 * header files!
 *
 *  Copyright (C) 2001  Peter Johnson
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *  - Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 *  - Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND OTHER CONTRIBUTORS ``AS IS''
 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR OTHER CONTRIBUTORS BE
 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 * POSSIBILITY OF SUCH DAMAGE.
 */
#ifndef YASM_UTIL_H
#define YASM_UTIL_H

#ifdef YASM_LIB_INTERNAL
# define YASM_INTERNAL
# define YASM_AUTOCONF_INTERNAL
# define YASM_LIB_AC_INTERNAL
# define YASM_GETTEXT_INTERNAL
#endif

#ifdef YASM_INTERNAL

#if defined(YASM_LIB_AC_INTERNAL) && defined(HAVE_CONFIG_H)
# include <libyasm/config.h>

/* Work around glibc's non-defining of certain things when using gcc -ansi */
# if defined(HAVE_GNU_C_LIBRARY) && defined(__STRICT_ANSI__)
#  undef __STRICT_ANSI__
# endif
#endif

#endif

#include <stdio.h>

#ifdef YASM_INTERNAL

#if defined(YASM_LIB_AC_INTERNAL) && defined(HAVE_CONFIG_H)
# include <stdarg.h>
#endif

#if !defined(lint) && !defined(NDEBUG)
# define NDEBUG
#endif

#ifdef YASM_AUTOCONF_INTERNAL

# ifdef STDC_HEADERS
#  include <stddef.h>
#  include <stdlib.h>
#  include <string.h>
#  include <assert.h>
# endif

# ifdef YASM_GETTEXT_INTERNAL
#  if defined(lint)
#   define _(String)	String
#  else
#   ifdef HAVE_LOCALE_H
#    include <locale.h>
#   endif

#   ifdef ENABLE_NLS
#    include <libintl.h>
#    define _(String)	gettext(String)
#   else
#    define gettext(Msgid)			    (Msgid)
#    define dgettext(Domainname, Msgid)		    (Msgid)
#    define dcgettext(Domainname, Msgid, Category)  (Msgid)
#    define textdomain(Domainname)		    while (0) /* nothing */
#    define bindtextdomain(Domainname, Dirname)	    while (0) /* nothing */
#    define _(String)	(String)
#   endif
#  endif

#  ifdef gettext_noop
#   define N_(String)	gettext_noop(String)
#  else
#   define N_(String)	(String)
#  endif

# endif	/*YASM_GETTEXT_INTERNAL*/

#endif	/*YASM_AUTOCONF_INTERNAL*/

/** Sort an array using merge sort algorithm.
 * \internal
 * \param base	    base of array
 * \param nmemb	    number of elements in array
 * \param size	    size of each array element
 * \param compar    element comparison function
 */
int yasm__mergesort(void *base, size_t nmemb, size_t size,
		    int (*compar)(const void *, const void *));

#if defined(YASM_AUTOCONF_INTERNAL) && defined(HAVE_MERGESORT)
#define yasm__mergesort(a, b, c, d)	mergesort(a, b, c, d)
#endif

/** Separate string by delimiters.
 * \internal
 * \param stringp   string
 * \param delim	    set of 1 or more delimiters
 * \return First/next substring.
 */
/*@null@*/ char *yasm__strsep(char **stringp, const char *delim);

#if defined(YASM_AUTOCONF_INTERNAL) && defined(HAVE_STRSEP)
#define yasm__strsep(a, b)		strsep(a, b)
#endif

/** Compare two strings, ignoring case differences.
 * \internal
 * \param s1	string 1
 * \param s2	string 2
 * \return 0 if strings are equal, -1 if s1<s2, 1 if s1>s2.
 */
int yasm__strcasecmp(const char *s1, const char *s2);

/** Compare portion of two strings, ignoring case differences.
 * \internal
 * \param s1	string 1
 * \param s2	string 2
 * \param n	maximum number of characters to compare
 * \return 0 if strings are equal, -1 if s1<s2, 1 if s1>s2.
 */
int yasm__strncasecmp(const char *s1, const char *s2, size_t n);

#ifdef YASM_AUTOCONF_INTERNAL

#ifdef HAVE_STRCASECMP
# define yasm__strcasecmp(x, y)		strcasecmp(x, y)
# define yasm__strncasecmp(x, y, n)	strncasecmp(x, y, n)
#elif HAVE_STRICMP
# define yasm__strcasecmp(x, y)		stricmp(x, y)
# define yasm__strncasecmp(x, y, n)	strnicmp(x, y, n)
#elif HAVE_STRCMPI
# define yasm__strcasecmp(x, y)		strcmpi(x, y)
# define yasm__strncasecmp(x, y, n)	strncmpi(x, y, n)
#else
# define USE_OUR_OWN_STRCASECMP
#endif

#if !defined(HAVE_TOASCII) || defined(lint)
# define toascii(c) ((c) & 0x7F)
#endif

#endif	/*YASM_AUTOCONF_INTERNAL*/

#include <libyasm/compat-queue.h>

#if defined(YASM_AUTOCONF_INTERNAL) && defined(HAVE_SYS_CDEFS_H)
# include <sys/cdefs.h>
#endif

#ifdef __RCSID
# define RCSID(s)	__RCSID(s)
#else
# ifdef __GNUC__
#  ifdef __ELF__
#   define RCSID(s)	__asm__(".ident\t\"" s "\"")
#  else
#   define RCSID(s)	static const char rcsid[] = s
#  endif
# else
#  define RCSID(s)	static const char rcsid[] = s
# endif
#endif

/** strdup() implementation using yasm_xmalloc().
 * \internal
 * \param str	string
 * \return Newly allocated duplicate string.
 */
/*@only@*/ char *yasm__xstrdup(const char *str);

/** strndup() implementation using yasm_xmalloc().
 * \internal
 * \param str	string
 * \param len	maximum number of characters to copy
 * \return Newly allocated duplicate string.
 */
/*@only@*/ char *yasm__xstrndup(const char *str, size_t len);

#endif	/*YASM_INTERNAL*/

/** Error-checking memory allocation.  A default implementation is provided
 * that calls yasm_fatal() on allocation errors.
 * A replacement should \em never return NULL.
 * \param size	    number of bytes to allocate
 * \return Allocated memory block.
 */
extern /*@only@*/ /*@out@*/ void * (*yasm_xmalloc) (size_t size);

/** Error-checking memory allocation (with clear-to-0).  A default
 * implementation is provided that calls yasm_fatal() on allocation errors.
 * A replacement should \em never return NULL.
 * \param size	    number of elements to allocate
 * \param elsize    size (in bytes) of each element
 * \return Allocated and cleared memory block.
 */
extern /*@only@*/ void * (*yasm_xcalloc) (size_t nelem, size_t elsize);

/** Error-checking memory reallocation.  A default implementation is provided
 * that calls yasm_fatal() on allocation errors.  A replacement should
 * \em never return NULL.
 * \param oldmem    memory block to resize
 * \param elsize    new size, in bytes
 * \return Re-allocated memory block.
 */
extern /*@only@*/ void * (*yasm_xrealloc)
    (/*@only@*/ /*@out@*/ /*@returned@*/ /*@null@*/ void *oldmem, size_t size)
    /*@modifies oldmem@*/;

/** Error-checking memory deallocation.  A default implementation is provided
 * that calls yasm_fatal() on allocation errors.
 * \param p	memory block to free
 */
extern void (*yasm_xfree) (/*@only@*/ /*@out@*/ /*@null@*/ void *p)
    /*@modifies p@*/;

#ifdef YASM_INTERNAL

#if defined(YASM_AUTOCONF_INTERNAL) && defined(WITH_DMALLOC)
# include <dmalloc.h>

#define yasm__xstrdup(str)		xstrdup(str)
#define yasm_xmalloc(size)		xmalloc(size)
#define yasm_xcalloc(count, size)	xcalloc(count, size)
#define yasm_xrealloc(ptr, size)	xrealloc(ptr, size)
#define yasm_xfree(ptr)			xfree(ptr)
#endif

/* Bit-counting: used primarily by HAMT but also in a few other places. */
#define SK5	0x55555555
#define SK3	0x33333333
#define SKF0	0x0F0F0F0F
#define BitCount(d, s)		do {		\
	d = s;					\
	d -= (d>>1) & SK5;			\
	d = (d & SK3) + ((d>>2) & SK3);		\
	d = (d & SKF0) + ((d>>4) & SKF0);	\
	d += d>>16;				\
	d += d>>8;				\
    } while (0)

#ifndef NELEMS
/** Get the number of elements in an array.
 * \internal
 * \param array	    array
 * \return Number of elements.
 */
#define NELEMS(array)	(sizeof(array) / sizeof(array[0]))
#endif

#endif	/*YASM_INTERNAL*/

#include <libyasm/coretype.h>

#include <libyasm/valparam.h>

#endif