File: | build/../misc.c |
Location: | line 300, column 4 |
Description: | Value stored to 'size' is never read |
1 | |
2 | /* |
3 | * $Id$ |
4 | * |
5 | * by JH <jheinonen@users.sourceforge.net> |
6 | * |
7 | * Copyright (C) Jaakko Heinonen |
8 | * getaline() Copyright (C) Lars Wirzenius |
9 | * sprintf and snprintf copyright is owned by various people |
10 | */ |
11 | |
12 | #include <stdio.h> |
13 | #include <string.h> |
14 | #include <stdlib.h> |
15 | #include <ctype.h> |
16 | #include <unistd.h> |
17 | #include <errno(*__errno_location ()).h> |
18 | #ifdef HAVE_CONFIG_H1 |
19 | # include "config.h" |
20 | #endif |
21 | #include <mbswidthgnu_mbswidth.h> |
22 | #include "abook.h" |
23 | #include "misc.h" |
24 | #include "xmalloc.h" |
25 | |
26 | #ifndef DEBUG |
27 | # define NDEBUG1 1 |
28 | #else |
29 | # undef NDEBUG1 |
30 | #endif |
31 | |
32 | #include <assert.h> |
33 | |
34 | char * |
35 | strlower(char *str) |
36 | { |
37 | char *tmp = str; |
38 | |
39 | assert(str != NULL)((void) (0)); |
40 | |
41 | while( ( *str = tolower ( *str )(__extension__ ({ int __res; if (sizeof (*str) > 1) { if ( __builtin_constant_p (*str)) { int __c = (*str); __res = __c < -128 || __c > 255 ? __c : (*__ctype_tolower_loc ())[__c]; } else __res = tolower (*str); } else __res = (*__ctype_tolower_loc ())[(int) (*str)]; __res; })) ) ) |
42 | str++; |
43 | |
44 | return tmp; |
45 | } |
46 | |
47 | char * |
48 | strtrim(char *s) |
49 | { |
50 | char *t, *tt; |
51 | |
52 | assert(s != NULL)((void) (0)); |
53 | |
54 | for(t = s; isspace(*t)((*__ctype_b_loc ())[(int) ((*t))] & (unsigned short int) _ISspace); t++); |
55 | |
56 | memmove(s, t, strlen(t)+1); |
57 | |
58 | for (tt = t = s; *t != '\0'; t++) |
59 | if(!isspace(*t)((*__ctype_b_loc ())[(int) ((*t))] & (unsigned short int) _ISspace)) |
60 | tt = t+1; |
61 | |
62 | *tt = '\0'; |
63 | |
64 | return s; |
65 | } |
66 | |
67 | int |
68 | is_number(char *p) |
69 | { |
70 | if(!p || !*p || (*p == '-' && !*++p)) |
71 | return 0; |
72 | |
73 | for(; *p; p++) |
74 | if(!isdigit(*p)((*__ctype_b_loc ())[(int) ((*p))] & (unsigned short int) _ISdigit)) |
75 | return 0; |
76 | |
77 | return 1; |
78 | } |
79 | |
80 | #ifndef HAVE_STRCASESTR1 |
81 | char * |
82 | strcasestr(const char *haystack, const char *needle) |
83 | { |
84 | int i; |
85 | int k; |
86 | |
87 | assert(haystack != NULL)((void) (0)); |
88 | assert(needle != NULL)((void) (0)); |
89 | |
90 | for(i=0; i<strlen(haystack)-strlen(needle)+1; i++) { |
91 | for(k=0; k<strlen(needle); k++, i++) { |
92 | if (tolower(haystack[i])(__extension__ ({ int __res; if (sizeof (haystack[i]) > 1) { if (__builtin_constant_p (haystack[i])) { int __c = (haystack [i]); __res = __c < -128 || __c > 255 ? __c : (*__ctype_tolower_loc ())[__c]; } else __res = tolower (haystack[i]); } else __res = (*__ctype_tolower_loc ())[(int) (haystack[i])]; __res; })) != tolower(needle[k])(__extension__ ({ int __res; if (sizeof (needle[k]) > 1) { if (__builtin_constant_p (needle[k])) { int __c = (needle[k] ); __res = __c < -128 || __c > 255 ? __c : (*__ctype_tolower_loc ())[__c]; } else __res = tolower (needle[k]); } else __res = (*__ctype_tolower_loc ())[(int) (needle[k])]; __res; }))) |
93 | break; |
94 | else if ((k+1) == strlen(needle)) |
95 | return &haystack[i]; |
96 | } |
97 | } |
98 | |
99 | return NULL((void*)0); |
100 | } |
101 | #endif |
102 | |
103 | #ifdef HAVE_CONFIG_H1 |
104 | # include "config.h" |
105 | #endif |
106 | |
107 | /* varargs declarations: */ |
108 | |
109 | #ifdef HAVE_STDARG_H1 |
110 | # define MY_VA_LOCAL_DECLva_list ap va_list ap |
111 | # define MY_VA_START(f)__builtin_va_start(ap, f) va_start(ap, f)__builtin_va_start(ap, f) |
112 | # define MY_VA_SHIFT(v,t)v = __builtin_va_arg(ap, t) v = va_arg(ap, t)__builtin_va_arg(ap, t) |
113 | # define MY_VA_END__builtin_va_end(ap) va_end(ap)__builtin_va_end(ap) |
114 | #else |
115 | # error HAVE_STDARG_H1 not defined |
116 | #endif |
117 | |
118 | char * |
119 | strdup_printf (const char *format, ... ) |
120 | { |
121 | MY_VA_LOCAL_DECLva_list ap; |
122 | size_t size = 100; |
123 | char *buffer = xmalloc_xmalloc_xmalloc (size); |
124 | |
125 | assert(format != NULL)((void) (0)); |
126 | |
127 | for(;;) { |
128 | int n; |
129 | MY_VA_START(format)__builtin_va_start(ap, format); |
130 | n = vsnprintf (buffer, size, |
131 | format, ap); |
132 | MY_VA_END__builtin_va_end(ap); |
133 | |
134 | if (n > -1 && n < size) |
135 | return buffer; |
136 | |
137 | if (n > -1) |
138 | size = n + 1; |
139 | else |
140 | size *= 2; |
141 | |
142 | buffer = xrealloc_xmalloc_xrealloc(buffer, size); |
143 | } |
144 | } |
145 | |
146 | |
147 | char* |
148 | strconcat (const char *str, ...) |
149 | { |
150 | unsigned long l; |
151 | MY_VA_LOCAL_DECLva_list ap; |
152 | char *s, *concat; |
153 | |
154 | assert(str != NULL)((void) (0)); |
155 | |
156 | l = 1 + strlen (str); |
157 | MY_VA_START(str)__builtin_va_start(ap, str); |
158 | MY_VA_SHIFT(s, char*)s = __builtin_va_arg(ap, char*); |
159 | while (s) { |
160 | l += strlen (s); |
161 | MY_VA_SHIFT(s, char*)s = __builtin_va_arg(ap, char*); |
162 | } |
163 | MY_VA_END__builtin_va_end(ap); |
164 | |
165 | concat = xmalloc_xmalloc_xmalloc(l); |
166 | |
167 | strcpy (concat, str); |
168 | MY_VA_START(str)__builtin_va_start(ap, str); |
169 | MY_VA_SHIFT(s, char*)s = __builtin_va_arg(ap, char*); |
170 | while (s) { |
171 | strcat (concat, s); |
172 | MY_VA_SHIFT(s, char*)s = __builtin_va_arg(ap, char*); |
173 | } |
174 | MY_VA_END__builtin_va_end(ap); |
175 | |
176 | return concat; |
177 | } |
178 | |
179 | |
180 | int |
181 | safe_strcmp(const char *s1, const char *s2) |
182 | { |
183 | if (s1 == NULL((void*)0) && s2 == NULL((void*)0)) return 0; |
184 | if (s1 == NULL((void*)0)) return -1; |
185 | if (s2 == NULL((void*)0)) return 1; |
186 | |
187 | return strcmp(s1, s2)__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (s1) && __builtin_constant_p (s2) && (__s1_len = strlen (s1), __s2_len = strlen (s2), (!((size_t)(const void *)((s1) + 1) - (size_t)(const void *)(s1) == 1) || __s1_len >= 4) && (!((size_t)(const void *)((s2) + 1) - (size_t) (const void *)(s2) == 1) || __s2_len >= 4)) ? __builtin_strcmp (s1, s2) : (__builtin_constant_p (s1) && ((size_t)(const void *)((s1) + 1) - (size_t)(const void *)(s1) == 1) && (__s1_len = strlen (s1), __s1_len < 4) ? (__builtin_constant_p (s2) && ((size_t)(const void *)((s2) + 1) - (size_t) (const void *)(s2) == 1) ? __builtin_strcmp (s1, s2) : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (s2); int __result = (((const unsigned char *) (const char *) (s1))[0] - __s2[0]); if (__s1_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) ( s1))[1] - __s2[1]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (s1 ))[2] - __s2[2]); if (__s1_len > 2 && __result == 0 ) __result = (((const unsigned char *) (const char *) (s1))[3 ] - __s2[3]); } } __result; }))) : (__builtin_constant_p (s2) && ((size_t)(const void *)((s2) + 1) - (size_t)(const void *)(s2) == 1) && (__s2_len = strlen (s2), __s2_len < 4) ? (__builtin_constant_p (s1) && ((size_t)(const void *)((s1) + 1) - (size_t)(const void *)(s1) == 1) ? __builtin_strcmp (s1, s2) : (- (__extension__ ({ const unsigned char *__s2 = ( const unsigned char *) (const char *) (s1); int __result = (( (const unsigned char *) (const char *) (s2))[0] - __s2[0]); if (__s2_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (s2))[1] - __s2[1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (s2))[2] - __s2[2]); if (__s2_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (s2))[3] - __s2[3]); } } __result; })))) : __builtin_strcmp (s1, s2)))); }); |
188 | } |
189 | |
190 | int |
191 | safe_strcoll(const char *s1, const char *s2) |
192 | { |
193 | #ifdef HAVE_STRCOLL1 |
194 | if (s1 == NULL((void*)0) && s2 == NULL((void*)0)) return 0; |
195 | if (s1 == NULL((void*)0)) return -1; |
196 | if (s2 == NULL((void*)0)) return 1; |
197 | |
198 | return strcoll(s1, s2); |
199 | #else /* fall back to strcmp */ |
200 | return safe_strcmp(s1, s2); |
201 | #endif |
202 | } |
203 | |
204 | char * |
205 | my_getcwd() |
206 | { |
207 | char *dir = NULL((void*)0); |
208 | size_t size = 100; |
209 | |
210 | if( (dir = xmalloc_xmalloc_xmalloc(size)) == NULL((void*)0)) |
211 | return NULL((void*)0); |
212 | |
213 | *dir = 0; |
214 | |
215 | while( getcwd(dir, size) == NULL((void*)0) && errno(*__errno_location ()) == ERANGE34 ) |
216 | if( (dir = xrealloc_xmalloc_xrealloc(dir, size *=2)) == NULL((void*)0)) |
217 | return NULL((void*)0); |
218 | |
219 | return dir; |
220 | } |
221 | |
222 | /* |
223 | * getaline() |
224 | * |
225 | * Copyright (c) 1994 Lars Wirzenius |
226 | * All rights reserved. |
227 | * |
228 | * Redistribution and use in source and binary forms, with or without |
229 | * modification, are permitted provided that the following conditions |
230 | * are met: |
231 | * 1. Redistributions of source code must retain the above copyright |
232 | * notice, this list of conditions and the following disclaimer |
233 | * in this position and unchanged. |
234 | * 2. Redistributions in binary form must reproduce the above copyright |
235 | * notice, this list of conditions and the following disclaimer in the |
236 | * documentation and/or other materials provided with the distribution. |
237 | * |
238 | * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS OR |
239 | * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES |
240 | * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. |
241 | * IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT, INDIRECT, |
242 | * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT |
243 | * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
244 | * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
245 | * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
246 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF |
247 | * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
248 | */ |
249 | |
250 | char * |
251 | getaline(FILE *f) |
252 | { |
253 | char *buf; /* buffer for line */ |
254 | size_t size; /* size of buffer */ |
255 | size_t inc; /* how much to enlarge buffer */ |
256 | size_t len; /* # of chars stored into buf before '\0' */ |
257 | char *p; |
258 | const size_t thres = 128; /* initial buffer size (most lines should |
259 | fit into this size, so think of this as |
260 | the "long line threshold"). */ |
261 | const size_t mucho = 128; /* if there is at least this much wasted |
262 | space when the whole buffer has been |
263 | read, try to reclaim it. Don't make |
264 | this too small, else there is too much |
265 | time wasted trying to reclaim a couple |
266 | of bytes. */ |
267 | const size_t mininc = 64; /* minimum number of bytes by which |
268 | to increase the allocated memory */ |
269 | |
270 | len = 0; |
271 | size = thres; |
272 | buf = xmalloc_xmalloc_xmalloc(size); |
273 | |
274 | while (fgets(buf+len, size-len, f) != NULL((void*)0)) { |
275 | len += strlen(buf+len); |
276 | if (len > 0 && buf[len-1] == '\n') |
277 | break; /* the whole line has been read */ |
278 | |
279 | for (inc = size, p = NULL((void*)0); inc > mininc; inc /= 2) |
280 | if ((p = xrealloc_inc(buf, size, inc)) != |
281 | NULL((void*)0)) |
282 | break; |
283 | |
284 | size += inc; |
285 | buf = p; |
286 | } |
287 | |
288 | if (len == 0) { |
289 | xfree(buf)do { free(buf); buf = ((void*)0); } while(0); |
290 | return NULL((void*)0); /* nothing read (eof or error) */ |
291 | } |
292 | |
293 | if (buf[len-1] == '\n') /* remove newline, if there */ |
294 | buf[--len] = '\0'; |
295 | |
296 | if (size - len > mucho) { /* a plenitude of unused memory? */ |
297 | p = xrealloc_inc(buf, len, 1); |
298 | if (p != NULL((void*)0)) { |
299 | buf = p; |
300 | size = len+1; |
Value stored to 'size' is never read | |
301 | } |
302 | } |
303 | |
304 | return buf; |
305 | } |
306 | |
307 | int |
308 | strwidth(const char *s) |
309 | { |
310 | assert(s)((void) (0)); |
311 | return mbswidthgnu_mbswidth(s, 0); |
312 | } |
313 | |
314 | int |
315 | bytes2width(const char *s, int width) |
316 | { |
317 | assert(s)((void) (0)); |
318 | #ifdef HANDLE_MULTIBYTE1 |
319 | return mbsnbytes(s, strlen(s), width, 0); |
320 | #else |
321 | return width; |
322 | #endif |
323 | } |
324 | |
325 | /************************************************************** |
326 | * Original: |
327 | * Patrick Powell Tue Apr 11 09:48:21 PDT 1995 |
328 | * A bombproof version of doprnt (dopr) included. |
329 | * Sigh. This sort of thing is always nasty do deal with. Note that |
330 | * the version here does not include floating point... |
331 | * |
332 | * snprintf() is used instead of sprintf() as it does limit checks |
333 | * for string length. This covers a nasty loophole. |
334 | * |
335 | * The other functions are there to prevent NULL pointers from |
336 | * causing nast effects. |
337 | * |
338 | * More Recently: |
339 | * Brandon Long <blong@fiction.net> 9/15/96 for mutt 0.43 |
340 | * This was ugly. It is still ugly. I opted out of floating point |
341 | * numbers, but the formatter understands just about everything |
342 | * from the normal C string format, at least as far as I can tell from |
343 | * the Solaris 2.5 printf(3S) man page. |
344 | * |
345 | * Brandon Long <blong@fiction.net> 10/22/97 for mutt 0.87.1 |
346 | * Ok, added some minimal floating point support, which means this |
347 | * probably requires libm on most operating systems. Don't yet |
348 | * support the exponent (e,E) and sigfig (g,G). Also, fmtint() |
349 | * was pretty badly broken, it just wasn't being exercised in ways |
350 | * which showed it, so that's been fixed. Also, formated the code |
351 | * to mutt conventions, and removed dead code left over from the |
352 | * original. Also, there is now a builtin-test, just compile with: |
353 | * gcc -DTEST_SNPRINTF -o snprintf snprintf.c -lm |
354 | * and run snprintf for results. |
355 | * |
356 | * Thomas Roessler <roessler@guug.de> 01/27/98 for mutt 0.89i |
357 | * The PGP code was using unsigned hexadecimal formats. |
358 | * Unfortunately, unsigned formats simply didn't work. |
359 | * |
360 | * Michael Elkins <me@cs.hmc.edu> 03/05/98 for mutt 0.90.8 |
361 | * The original code assumed that both snprintf() and vsnprintf() were |
362 | * missing. Some systems only have snprintf() but not vsnprintf(), so |
363 | * the code is now broken down under HAVE_SNPRINTF and HAVE_VSNPRINTF. |
364 | * |
365 | **************************************************************/ |
366 | |
367 | #include "config.h" |
368 | |
369 | #if !defined(HAVE_SNPRINTF1) || !defined(HAVE_VSNPRINTF1) |
370 | |
371 | #include <string.h> |
372 | # include <ctype.h> |
373 | #include <sys/types.h> |
374 | |
375 | /* Define this as a fall through, HAVE_STDARG_H is probably already set */ |
376 | |
377 | #if !defined(HAVE_STDARG_H1) && !defined(HAVE_VARARGS_H) |
378 | # define HAVE_VARARGS_H 1 |
379 | #endif |
380 | |
381 | /* varargs declarations: */ |
382 | |
383 | #if defined(HAVE_STDARG_H1) |
384 | /*# include <stdarg.h>*/ |
385 | # define HAVE_STDARGS /* let's hope that works everywhere (mj) */ |
386 | # define VA_LOCAL_DECL va_list ap |
387 | # define VA_START(f) va_start(ap, f)__builtin_va_start(ap, f) |
388 | # define VA_SHIFT(v,t) ; /* no-op for ANSI */ |
389 | # define VA_END va_end(ap)__builtin_va_end(ap) |
390 | #else |
391 | # if defined(HAVE_VARARGS_H) |
392 | # include <varargs.h> |
393 | # undef HAVE_STDARGS |
394 | # define VA_LOCAL_DECL va_list ap |
395 | # define VA_START(f) va_start(ap) /* f is ignored! */ |
396 | # define VA_SHIFT(v,t) v = va_arg(ap,t)__builtin_va_arg(ap, t) |
397 | # define VA_END va_end(ap)__builtin_va_end(ap) |
398 | # else |
399 | /*XX ** NO VARARGS ** XX*/ |
400 | # endif |
401 | #endif |
402 | |
403 | /*int snprintf (char *str, size_t count, const char *fmt, ...);*/ |
404 | /*int vsnprintf (char *str, size_t count, const char *fmt, va_list arg);*/ |
405 | |
406 | static void dopr (char *buffer, size_t maxlen, const char *format, |
407 | va_list args); |
408 | static void fmtstr (char *buffer, size_t *currlen, size_t maxlen, |
409 | char *value, int flags, int min, int max); |
410 | static void fmtint (char *buffer, size_t *currlen, size_t maxlen, |
411 | long value, int base, int min, int max, int flags); |
412 | static void fmtfp (char *buffer, size_t *currlen, size_t maxlen, |
413 | long double fvalue, int min, int max, int flags); |
414 | static void dopr_outch (char *buffer, size_t *currlen, size_t maxlen, char c ); |
415 | |
416 | /* |
417 | * dopr(): poor man's version of doprintf |
418 | */ |
419 | |
420 | /* format read states */ |
421 | #define DP_S_DEFAULT 0 |
422 | #define DP_S_FLAGS 1 |
423 | #define DP_S_MIN 2 |
424 | #define DP_S_DOT 3 |
425 | #define DP_S_MAX 4 |
426 | #define DP_S_MOD 5 |
427 | #define DP_S_CONV 6 |
428 | #define DP_S_DONE 7 |
429 | |
430 | /* format flags - Bits */ |
431 | #define DP_F_MINUS (1 << 0) |
432 | #define DP_F_PLUS (1 << 1) |
433 | #define DP_F_SPACE (1 << 2) |
434 | #define DP_F_NUM (1 << 3) |
435 | #define DP_F_ZERO (1 << 4) |
436 | #define DP_F_UP (1 << 5) |
437 | #define DP_F_UNSIGNED (1 << 6) |
438 | |
439 | /* Conversion Flags */ |
440 | #define DP_C_SHORT 1 |
441 | #define DP_C_LONG 2 |
442 | #define DP_C_LDOUBLE 3 |
443 | |
444 | #define char_to_int(p) (p - '0') |
445 | #define MAX(p,q) ((p >= q) ? p : q) |
446 | |
447 | static void dopr (char *buffer, size_t maxlen, const char *format, va_list args) |
448 | { |
449 | char ch; |
450 | long value; |
451 | long double fvalue; |
452 | char *strvalue; |
453 | int min; |
454 | int max; |
455 | int state; |
456 | int flags; |
457 | int cflags; |
458 | size_t currlen; |
459 | |
460 | state = DP_S_DEFAULT; |
461 | currlen = flags = cflags = min = 0; |
462 | max = -1; |
463 | ch = *format++; |
464 | |
465 | while (state != DP_S_DONE) |
466 | { |
467 | if ((ch == '\0') || (currlen >= maxlen)) |
468 | state = DP_S_DONE; |
469 | |
470 | switch(state) |
471 | { |
472 | case DP_S_DEFAULT: |
473 | if (ch == '%') |
474 | state = DP_S_FLAGS; |
475 | else |
476 | dopr_outch (buffer, &currlen, maxlen, ch); |
477 | ch = *format++; |
478 | break; |
479 | case DP_S_FLAGS: |
480 | switch (ch) |
481 | { |
482 | case '-': |
483 | flags |= DP_F_MINUS; |
484 | ch = *format++; |
485 | break; |
486 | case '+': |
487 | flags |= DP_F_PLUS; |
488 | ch = *format++; |
489 | break; |
490 | case ' ': |
491 | flags |= DP_F_SPACE; |
492 | ch = *format++; |
493 | break; |
494 | case '#': |
495 | flags |= DP_F_NUM; |
496 | ch = *format++; |
497 | break; |
498 | case '0': |
499 | flags |= DP_F_ZERO; |
500 | ch = *format++; |
501 | break; |
502 | default: |
503 | state = DP_S_MIN; |
504 | break; |
505 | } |
506 | break; |
507 | case DP_S_MIN: |
508 | if (isdigit((unsigned char)ch)((*__ctype_b_loc ())[(int) (((unsigned char)ch))] & (unsigned short int) _ISdigit)) |
509 | { |
510 | min = 10*min + char_to_int (ch); |
511 | ch = *format++; |
512 | } |
513 | else if (ch == '*') |
514 | { |
515 | min = va_arg (args, int)__builtin_va_arg(args, int); |
516 | ch = *format++; |
517 | state = DP_S_DOT; |
518 | } |
519 | else |
520 | state = DP_S_DOT; |
521 | break; |
522 | case DP_S_DOT: |
523 | if (ch == '.') |
524 | { |
525 | state = DP_S_MAX; |
526 | ch = *format++; |
527 | } |
528 | else |
529 | state = DP_S_MOD; |
530 | break; |
531 | case DP_S_MAX: |
532 | if (isdigit((unsigned char)ch)((*__ctype_b_loc ())[(int) (((unsigned char)ch))] & (unsigned short int) _ISdigit)) |
533 | { |
534 | if (max < 0) |
535 | max = 0; |
536 | max = 10*max + char_to_int (ch); |
537 | ch = *format++; |
538 | } |
539 | else if (ch == '*') |
540 | { |
541 | max = va_arg (args, int)__builtin_va_arg(args, int); |
542 | ch = *format++; |
543 | state = DP_S_MOD; |
544 | } |
545 | else |
546 | state = DP_S_MOD; |
547 | break; |
548 | case DP_S_MOD: |
549 | /* Currently, we don't support Long Long, bummer */ |
550 | switch (ch) |
551 | { |
552 | case 'h': |
553 | cflags = DP_C_SHORT; |
554 | ch = *format++; |
555 | break; |
556 | case 'l': |
557 | cflags = DP_C_LONG; |
558 | ch = *format++; |
559 | break; |
560 | case 'L': |
561 | cflags = DP_C_LDOUBLE; |
562 | ch = *format++; |
563 | break; |
564 | default: |
565 | break; |
566 | } |
567 | state = DP_S_CONV; |
568 | break; |
569 | case DP_S_CONV: |
570 | switch (ch) |
571 | { |
572 | case 'd': |
573 | case 'i': |
574 | if (cflags == DP_C_SHORT) |
575 | value = va_arg (args, short int)__builtin_va_arg(args, short int); |
576 | else if (cflags == DP_C_LONG) |
577 | value = va_arg (args, long int)__builtin_va_arg(args, long int); |
578 | else |
579 | value = va_arg (args, int)__builtin_va_arg(args, int); |
580 | fmtint (buffer, &currlen, maxlen, value, 10, min, max, flags); |
581 | break; |
582 | case 'o': |
583 | flags |= DP_F_UNSIGNED; |
584 | if (cflags == DP_C_SHORT) |
585 | value = va_arg (args, unsigned short int)__builtin_va_arg(args, unsigned short int); |
586 | else if (cflags == DP_C_LONG) |
587 | value = va_arg (args, unsigned long int)__builtin_va_arg(args, unsigned long int); |
588 | else |
589 | value = va_arg (args, unsigned int)__builtin_va_arg(args, unsigned int); |
590 | fmtint (buffer, &currlen, maxlen, value, 8, min, max, flags); |
591 | break; |
592 | case 'u': |
593 | flags |= DP_F_UNSIGNED; |
594 | if (cflags == DP_C_SHORT) |
595 | value = va_arg (args, unsigned short int)__builtin_va_arg(args, unsigned short int); |
596 | else if (cflags == DP_C_LONG) |
597 | value = va_arg (args, unsigned long int)__builtin_va_arg(args, unsigned long int); |
598 | else |
599 | value = va_arg (args, unsigned int)__builtin_va_arg(args, unsigned int); |
600 | fmtint (buffer, &currlen, maxlen, value, 10, min, max, flags); |
601 | break; |
602 | case 'X': |
603 | flags |= DP_F_UP; |
604 | case 'x': |
605 | flags |= DP_F_UNSIGNED; |
606 | if (cflags == DP_C_SHORT) |
607 | value = va_arg (args, unsigned short int)__builtin_va_arg(args, unsigned short int); |
608 | else if (cflags == DP_C_LONG) |
609 | value = va_arg (args, unsigned long int)__builtin_va_arg(args, unsigned long int); |
610 | else |
611 | value = va_arg (args, unsigned int)__builtin_va_arg(args, unsigned int); |
612 | fmtint (buffer, &currlen, maxlen, value, 16, min, max, flags); |
613 | break; |
614 | case 'f': |
615 | if (cflags == DP_C_LDOUBLE) |
616 | fvalue = va_arg (args, long double)__builtin_va_arg(args, long double); |
617 | else |
618 | fvalue = va_arg (args, double)__builtin_va_arg(args, double); |
619 | /* um, floating point? */ |
620 | fmtfp (buffer, &currlen, maxlen, fvalue, min, max, flags); |
621 | break; |
622 | case 'E': |
623 | flags |= DP_F_UP; |
624 | case 'e': |
625 | if (cflags == DP_C_LDOUBLE) |
626 | fvalue = va_arg (args, long double)__builtin_va_arg(args, long double); |
627 | else |
628 | fvalue = va_arg (args, double)__builtin_va_arg(args, double); |
629 | break; |
630 | case 'G': |
631 | flags |= DP_F_UP; |
632 | case 'g': |
633 | if (cflags == DP_C_LDOUBLE) |
634 | fvalue = va_arg (args, long double)__builtin_va_arg(args, long double); |
635 | else |
636 | fvalue = va_arg (args, double)__builtin_va_arg(args, double); |
637 | break; |
638 | case 'c': |
639 | dopr_outch (buffer, &currlen, maxlen, va_arg (args, int)__builtin_va_arg(args, int)); |
640 | break; |
641 | case 's': |
642 | strvalue = va_arg (args, char *)__builtin_va_arg(args, char *); |
643 | if (max < 0) |
644 | max = maxlen; /* ie, no max */ |
645 | fmtstr (buffer, &currlen, maxlen, strvalue, flags, min, max); |
646 | break; |
647 | case 'p': |
648 | strvalue = va_arg (args, void *)__builtin_va_arg(args, void *); |
649 | fmtint (buffer, &currlen, maxlen, (long) strvalue, 16, min, max, flags); |
650 | break; |
651 | case 'n': |
652 | if (cflags == DP_C_SHORT) |
653 | { |
654 | short int *num; |
655 | num = va_arg (args, short int *)__builtin_va_arg(args, short int *); |
656 | *num = currlen; |
657 | } |
658 | else if (cflags == DP_C_LONG) |
659 | { |
660 | long int *num; |
661 | num = va_arg (args, long int *)__builtin_va_arg(args, long int *); |
662 | *num = currlen; |
663 | } |
664 | else |
665 | { |
666 | int *num; |
667 | num = va_arg (args, int *)__builtin_va_arg(args, int *); |
668 | *num = currlen; |
669 | } |
670 | break; |
671 | case '%': |
672 | dopr_outch (buffer, &currlen, maxlen, ch); |
673 | break; |
674 | case 'w': |
675 | /* not supported yet, treat as next char */ |
676 | ch = *format++; |
677 | break; |
678 | default: |
679 | /* Unknown, skip */ |
680 | break; |
681 | } |
682 | ch = *format++; |
683 | state = DP_S_DEFAULT; |
684 | flags = cflags = min = 0; |
685 | max = -1; |
686 | break; |
687 | case DP_S_DONE: |
688 | break; |
689 | default: |
690 | /* hmm? */ |
691 | break; /* some picky compilers need this */ |
692 | } |
693 | } |
694 | if (currlen < maxlen - 1) |
695 | buffer[currlen] = '\0'; |
696 | else |
697 | buffer[maxlen - 1] = '\0'; |
698 | } |
699 | |
700 | static void fmtstr (char *buffer, size_t *currlen, size_t maxlen, |
701 | char *value, int flags, int min, int max) |
702 | { |
703 | int padlen, strln; /* amount to pad */ |
704 | int cnt = 0; |
705 | |
706 | if (value == 0) |
707 | { |
708 | value = "<NULL>"; |
709 | } |
710 | |
711 | for (strln = 0; value[strln]; ++strln); /* strlen */ |
712 | padlen = min - strln; |
713 | if (padlen < 0) |
714 | padlen = 0; |
715 | if (flags & DP_F_MINUS) |
716 | padlen = -padlen; /* Left Justify */ |
717 | |
718 | while ((padlen > 0) && (cnt < max)) |
719 | { |
720 | dopr_outch (buffer, currlen, maxlen, ' '); |
721 | --padlen; |
722 | ++cnt; |
723 | } |
724 | while (*value && (cnt < max)) |
725 | { |
726 | dopr_outch (buffer, currlen, maxlen, *value++); |
727 | ++cnt; |
728 | } |
729 | while ((padlen < 0) && (cnt < max)) |
730 | { |
731 | dopr_outch (buffer, currlen, maxlen, ' '); |
732 | ++padlen; |
733 | ++cnt; |
734 | } |
735 | } |
736 | |
737 | /* Have to handle DP_F_NUM (ie 0x and 0 alternates) */ |
738 | |
739 | static void fmtint (char *buffer, size_t *currlen, size_t maxlen, |
740 | long value, int base, int min, int max, int flags) |
741 | { |
742 | int signvalue = 0; |
743 | unsigned long uvalue; |
744 | char convert[20]; |
745 | int place = 0; |
746 | int spadlen = 0; /* amount to space pad */ |
747 | int zpadlen = 0; /* amount to zero pad */ |
748 | int caps = 0; |
749 | |
750 | if (max < 0) |
751 | max = 0; |
752 | |
753 | uvalue = value; |
754 | |
755 | if(!(flags & DP_F_UNSIGNED)) |
756 | { |
757 | if( value < 0 ) { |
758 | signvalue = '-'; |
759 | uvalue = -value; |
760 | } |
761 | else |
762 | if (flags & DP_F_PLUS) /* Do a sign (+/i) */ |
763 | signvalue = '+'; |
764 | else |
765 | if (flags & DP_F_SPACE) |
766 | signvalue = ' '; |
767 | } |
768 | |
769 | if (flags & DP_F_UP) caps = 1; /* Should characters be upper case? */ |
770 | |
771 | do { |
772 | convert[place++] = |
773 | (caps? "0123456789ABCDEF":"0123456789abcdef") |
774 | [uvalue % (unsigned)base ]; |
775 | uvalue = (uvalue / (unsigned)base ); |
776 | } while(uvalue && (place < 20)); |
777 | if (place == 20) place--; |
778 | convert[place] = 0; |
779 | |
780 | zpadlen = max - place; |
781 | spadlen = min - MAX (max, place) - (signvalue ? 1 : 0); |
782 | if (zpadlen < 0) zpadlen = 0; |
783 | if (spadlen < 0) spadlen = 0; |
784 | if (flags & DP_F_ZERO) |
785 | { |
786 | zpadlen = MAX(zpadlen, spadlen); |
787 | spadlen = 0; |
788 | } |
789 | if (flags & DP_F_MINUS) |
790 | spadlen = -spadlen; /* Left Justifty */ |
791 | |
792 | #ifdef DEBUG_SNPRINTF |
793 | dprint (1, (debugfile, "zpad: %d, spad: %d, min: %d, max: %d, place: %d\n", |
794 | zpadlen, spadlen, min, max, place)); |
795 | #endif |
796 | |
797 | /* Spaces */ |
798 | while (spadlen > 0) |
799 | { |
800 | dopr_outch (buffer, currlen, maxlen, ' '); |
801 | --spadlen; |
802 | } |
803 | |
804 | /* Sign */ |
805 | if (signvalue) |
806 | dopr_outch (buffer, currlen, maxlen, signvalue); |
807 | |
808 | /* Zeros */ |
809 | if (zpadlen > 0) |
810 | { |
811 | while (zpadlen > 0) |
812 | { |
813 | dopr_outch (buffer, currlen, maxlen, '0'); |
814 | --zpadlen; |
815 | } |
816 | } |
817 | |
818 | /* Digits */ |
819 | while (place > 0) |
820 | dopr_outch (buffer, currlen, maxlen, convert[--place]); |
821 | |
822 | /* Left Justified spaces */ |
823 | while (spadlen < 0) { |
824 | dopr_outch (buffer, currlen, maxlen, ' '); |
825 | ++spadlen; |
826 | } |
827 | } |
828 | |
829 | static long double abs_val (long double value) |
830 | { |
831 | long double result = value; |
832 | |
833 | if (value < 0) |
834 | result = -value; |
835 | |
836 | return result; |
837 | } |
838 | |
839 | static long double pow10 (int exp) |
840 | { |
841 | long double result = 1; |
842 | |
843 | while (exp) |
844 | { |
845 | result *= 10; |
846 | exp--; |
847 | } |
848 | |
849 | return result; |
850 | } |
851 | |
852 | static long round (long double value) |
853 | { |
854 | long intpart; |
855 | |
856 | intpart = value; |
857 | value = value - intpart; |
858 | if (value >= 0.5) |
859 | intpart++; |
860 | |
861 | return intpart; |
862 | } |
863 | |
864 | static void fmtfp (char *buffer, size_t *currlen, size_t maxlen, |
865 | long double fvalue, int min, int max, int flags) |
866 | { |
867 | int signvalue = 0; |
868 | long double ufvalue; |
869 | char iconvert[20]; |
870 | char fconvert[20]; |
871 | int iplace = 0; |
872 | int fplace = 0; |
873 | int padlen = 0; /* amount to pad */ |
874 | int zpadlen = 0; |
875 | int caps = 0; |
876 | long intpart; |
877 | long fracpart; |
878 | |
879 | /* |
880 | * AIX manpage says the default is 0, but Solaris says the default |
881 | * is 6, and sprintf on AIX defaults to 6 |
882 | */ |
883 | if (max < 0) |
884 | max = 6; |
885 | |
886 | ufvalue = abs_val (fvalue); |
887 | |
888 | if (fvalue < 0) |
889 | signvalue = '-'; |
890 | else |
891 | if (flags & DP_F_PLUS) /* Do a sign (+/i) */ |
892 | signvalue = '+'; |
893 | else |
894 | if (flags & DP_F_SPACE) |
895 | signvalue = ' '; |
896 | |
897 | #if 0 |
898 | if (flags & DP_F_UP) caps = 1; /* Should characters be upper case? */ |
899 | #endif |
900 | |
901 | intpart = ufvalue; |
902 | |
903 | /* |
904 | * Sorry, we only support 9 digits past the decimal because of our |
905 | * conversion method |
906 | */ |
907 | if (max > 9) |
908 | max = 9; |
909 | |
910 | /* We "cheat" by converting the fractional part to integer by |
911 | * multiplying by a factor of 10 |
912 | */ |
913 | fracpart = round ((pow10 (max)) * (ufvalue - intpart)); |
914 | |
915 | if (fracpart >= pow10 (max)) |
916 | { |
917 | intpart++; |
918 | fracpart -= pow10 (max); |
919 | } |
920 | |
921 | #ifdef DEBUG_SNPRINTF |
922 | dprint (1, (debugfile, "fmtfp: %f =? %d.%d\n", fvalue, intpart, fracpart)); |
923 | #endif |
924 | |
925 | /* Convert integer part */ |
926 | do { |
927 | iconvert[iplace++] = |
928 | (caps? "0123456789ABCDEF":"0123456789abcdef")[intpart % 10]; |
929 | intpart = (intpart / 10); |
930 | } while(intpart && (iplace < 20)); |
931 | if (iplace == 20) iplace--; |
932 | iconvert[iplace] = 0; |
933 | |
934 | /* Convert fractional part */ |
935 | do { |
936 | fconvert[fplace++] = |
937 | (caps? "0123456789ABCDEF":"0123456789abcdef")[fracpart % 10]; |
938 | fracpart = (fracpart / 10); |
939 | } while(fracpart && (fplace < 20)); |
940 | if (fplace == 20) fplace--; |
941 | fconvert[fplace] = 0; |
942 | |
943 | /* -1 for decimal point, another -1 if we are printing a sign */ |
944 | padlen = min - iplace - max - 1 - ((signvalue) ? 1 : 0); |
945 | zpadlen = max - fplace; |
946 | if (zpadlen < 0) |
947 | zpadlen = 0; |
948 | if (padlen < 0) |
949 | padlen = 0; |
950 | if (flags & DP_F_MINUS) |
951 | padlen = -padlen; /* Left Justifty */ |
952 | |
953 | if ((flags & DP_F_ZERO) && (padlen > 0)) |
954 | { |
955 | if (signvalue) |
956 | { |
957 | dopr_outch (buffer, currlen, maxlen, signvalue); |
958 | --padlen; |
959 | signvalue = 0; |
960 | } |
961 | while (padlen > 0) |
962 | { |
963 | dopr_outch (buffer, currlen, maxlen, '0'); |
964 | --padlen; |
965 | } |
966 | } |
967 | while (padlen > 0) |
968 | { |
969 | dopr_outch (buffer, currlen, maxlen, ' '); |
970 | --padlen; |
971 | } |
972 | if (signvalue) |
973 | dopr_outch (buffer, currlen, maxlen, signvalue); |
974 | |
975 | while (iplace > 0) |
976 | dopr_outch (buffer, currlen, maxlen, iconvert[--iplace]); |
977 | |
978 | /* |
979 | * Decimal point. This should probably use locale to find the correct |
980 | * char to print out. |
981 | */ |
982 | dopr_outch (buffer, currlen, maxlen, '.'); |
983 | |
984 | while (fplace > 0) |
985 | dopr_outch (buffer, currlen, maxlen, fconvert[--fplace]); |
986 | |
987 | while (zpadlen > 0) |
988 | { |
989 | dopr_outch (buffer, currlen, maxlen, '0'); |
990 | --zpadlen; |
991 | } |
992 | |
993 | while (padlen < 0) |
994 | { |
995 | dopr_outch (buffer, currlen, maxlen, ' '); |
996 | ++padlen; |
997 | } |
998 | } |
999 | |
1000 | static void dopr_outch (char *buffer, size_t *currlen, size_t maxlen, char c) |
1001 | { |
1002 | if (*currlen < maxlen) |
1003 | buffer[(*currlen)++] = c; |
1004 | } |
1005 | #endif /* !defined(HAVE_SNPRINTF) || !defined(HAVE_VSNPRINTF) */ |
1006 | |
1007 | #ifndef HAVE_VSNPRINTF1 |
1008 | int vsnprintf (char *str, size_t count, const char *fmt, va_list args) |
1009 | { |
1010 | str[0] = 0; |
1011 | dopr(str, count, fmt, args); |
1012 | return(strlen(str)); |
1013 | } |
1014 | #endif /* !HAVE_VSNPRINTF */ |
1015 | |
1016 | #ifndef HAVE_SNPRINTF1 |
1017 | /* VARARGS3 */ |
1018 | #ifdef HAVE_STDARGS |
1019 | int snprintf (char *str,size_t count,const char *fmt,...) |
1020 | #else |
1021 | int snprintf (va_alist) va_dcl |
1022 | #endif |
1023 | { |
1024 | #ifndef HAVE_STDARGS |
1025 | char *str; |
1026 | size_t count; |
1027 | char *fmt; |
1028 | #endif |
1029 | VA_LOCAL_DECL; |
1030 | |
1031 | VA_START (fmt); |
1032 | VA_SHIFT (str, char *); |
1033 | VA_SHIFT (count, size_t ); |
1034 | VA_SHIFT (fmt, char *); |
1035 | (void) vsnprintf(str, count, fmt, ap); |
1036 | VA_END; |
1037 | return(strlen(str)); |
1038 | } |
1039 | |
1040 | #ifdef TEST_SNPRINTF |
1041 | #ifndef LONG_STRING |
1042 | #define LONG_STRING 1024 |
1043 | #endif |
1044 | int main (void) |
1045 | { |
1046 | char buf1[LONG_STRING]; |
1047 | char buf2[LONG_STRING]; |
1048 | char *fp_fmt[] = { |
1049 | "%-1.5f", |
1050 | "%1.5f", |
1051 | "%123.9f", |
1052 | "%10.5f", |
1053 | "% 10.5f", |
1054 | "%+22.9f", |
1055 | "%+4.9f", |
1056 | "%01.3f", |
1057 | "%4f", |
1058 | "%3.1f", |
1059 | "%3.2f", |
1060 | NULL((void*)0) |
1061 | }; |
1062 | double fp_nums[] = { -1.5, 134.21, 91340.2, 341.1234, 0203.9, 0.96, 0.996, |
1063 | 0.9996, 1.996, 4.136, 0}; |
1064 | char *int_fmt[] = { |
1065 | "%-1.5d", |
1066 | "%1.5d", |
1067 | "%123.9d", |
1068 | "%5.5d", |
1069 | "%10.5d", |
1070 | "% 10.5d", |
1071 | "%+22.33d", |
1072 | "%01.3d", |
1073 | "%4d", |
1074 | NULL((void*)0) |
1075 | }; |
1076 | long int_nums[] = { -1, 134, 91340, 341, 0203, 0}; |
1077 | int x, y; |
1078 | int fail = 0; |
1079 | int num = 0; |
1080 | |
1081 | printf ("Testing snprintf format codes against system sprintf...\n"); |
1082 | |
1083 | for (x = 0; fp_fmt[x] != NULL((void*)0) ; x++) |
1084 | for (y = 0; fp_nums[y] != 0 ; y++) |
1085 | { |
1086 | snprintf (buf1, sizeof (buf1), fp_fmt[x], fp_nums[y]); |
1087 | sprintf (buf2, fp_fmt[x], fp_nums[y]); |
1088 | if (strcmp (buf1, buf2)__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (buf1) && __builtin_constant_p (buf2) && (__s1_len = strlen (buf1), __s2_len = strlen (buf2), (!((size_t)(const void *)((buf1) + 1) - (size_t)(const void *)(buf1) == 1) || __s1_len >= 4) && (!((size_t)(const void *)((buf2) + 1) - ( size_t)(const void *)(buf2) == 1) || __s2_len >= 4)) ? __builtin_strcmp (buf1, buf2) : (__builtin_constant_p (buf1) && ((size_t )(const void *)((buf1) + 1) - (size_t)(const void *)(buf1) == 1) && (__s1_len = strlen (buf1), __s1_len < 4) ? ( __builtin_constant_p (buf2) && ((size_t)(const void * )((buf2) + 1) - (size_t)(const void *)(buf2) == 1) ? __builtin_strcmp (buf1, buf2) : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (buf2); int __result = (((const unsigned char *) (const char *) (buf1))[0] - __s2[0 ]); if (__s1_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (buf1))[1] - __s2[1 ]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (buf1))[2] - __s2[2 ]); if (__s1_len > 2 && __result == 0) __result = ( ((const unsigned char *) (const char *) (buf1))[3] - __s2[3]) ; } } __result; }))) : (__builtin_constant_p (buf2) && ((size_t)(const void *)((buf2) + 1) - (size_t)(const void *) (buf2) == 1) && (__s2_len = strlen (buf2), __s2_len < 4) ? (__builtin_constant_p (buf1) && ((size_t)(const void *)((buf1) + 1) - (size_t)(const void *)(buf1) == 1) ? __builtin_strcmp (buf1, buf2) : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (buf1); int __result = (((const unsigned char *) (const char *) (buf2))[0] - __s2 [0]); if (__s2_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (buf2))[1] - __s2 [1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (buf2))[2] - __s2 [2]); if (__s2_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (buf2))[3] - __s2[3 ]); } } __result; })))) : __builtin_strcmp (buf1, buf2)))); } )) |
1089 | { |
1090 | printf("snprintf doesn't match Format: %s\n\tsnprintf = %s\n\tsprintf = %s\n", |
1091 | fp_fmt[x], buf1, buf2); |
1092 | fail++; |
1093 | } |
1094 | num++; |
1095 | } |
1096 | |
1097 | for (x = 0; int_fmt[x] != NULL((void*)0) ; x++) |
1098 | for (y = 0; int_nums[y] != 0 ; y++) |
1099 | { |
1100 | snprintf (buf1, sizeof (buf1), int_fmt[x], int_nums[y]); |
1101 | sprintf (buf2, int_fmt[x], int_nums[y]); |
1102 | if (strcmp (buf1, buf2)__extension__ ({ size_t __s1_len, __s2_len; (__builtin_constant_p (buf1) && __builtin_constant_p (buf2) && (__s1_len = strlen (buf1), __s2_len = strlen (buf2), (!((size_t)(const void *)((buf1) + 1) - (size_t)(const void *)(buf1) == 1) || __s1_len >= 4) && (!((size_t)(const void *)((buf2) + 1) - ( size_t)(const void *)(buf2) == 1) || __s2_len >= 4)) ? __builtin_strcmp (buf1, buf2) : (__builtin_constant_p (buf1) && ((size_t )(const void *)((buf1) + 1) - (size_t)(const void *)(buf1) == 1) && (__s1_len = strlen (buf1), __s1_len < 4) ? ( __builtin_constant_p (buf2) && ((size_t)(const void * )((buf2) + 1) - (size_t)(const void *)(buf2) == 1) ? __builtin_strcmp (buf1, buf2) : (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (buf2); int __result = (((const unsigned char *) (const char *) (buf1))[0] - __s2[0 ]); if (__s1_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (buf1))[1] - __s2[1 ]); if (__s1_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (buf1))[2] - __s2[2 ]); if (__s1_len > 2 && __result == 0) __result = ( ((const unsigned char *) (const char *) (buf1))[3] - __s2[3]) ; } } __result; }))) : (__builtin_constant_p (buf2) && ((size_t)(const void *)((buf2) + 1) - (size_t)(const void *) (buf2) == 1) && (__s2_len = strlen (buf2), __s2_len < 4) ? (__builtin_constant_p (buf1) && ((size_t)(const void *)((buf1) + 1) - (size_t)(const void *)(buf1) == 1) ? __builtin_strcmp (buf1, buf2) : (- (__extension__ ({ const unsigned char *__s2 = (const unsigned char *) (const char *) (buf1); int __result = (((const unsigned char *) (const char *) (buf2))[0] - __s2 [0]); if (__s2_len > 0 && __result == 0) { __result = (((const unsigned char *) (const char *) (buf2))[1] - __s2 [1]); if (__s2_len > 1 && __result == 0) { __result = (((const unsigned char *) (const char *) (buf2))[2] - __s2 [2]); if (__s2_len > 2 && __result == 0) __result = (((const unsigned char *) (const char *) (buf2))[3] - __s2[3 ]); } } __result; })))) : __builtin_strcmp (buf1, buf2)))); } )) |
1103 | { |
1104 | printf("snprintf doesn't match Format: %s\n\tsnprintf = %s\n\tsprintf = %s\n", |
1105 | int_fmt[x], buf1, buf2); |
1106 | fail++; |
1107 | } |
1108 | num++; |
1109 | } |
1110 | printf ("%d tests failed out of %d.\n", fail, num); |
1111 | } |
1112 | #endif /* SNPRINTF_TEST */ |
1113 | |
1114 | #endif /* !HAVE_SNPRINTF */ |
1115 | |
1116 | |
1117 | |
1118 | |
1119 | /* |
1120 | * List handling functions |
1121 | */ |
1122 | |
1123 | void |
1124 | abook_list_append(abook_list **list, char *str) |
1125 | { |
1126 | abook_list *tmp; |
1127 | |
1128 | if(!str) |
1129 | return; |
1130 | |
1131 | for(tmp = *list; tmp && tmp->next; tmp = tmp->next) |
1132 | ; |
1133 | |
1134 | if(tmp) { |
1135 | tmp->next = xmalloc_xmalloc_xmalloc(sizeof(abook_list)); |
1136 | tmp = tmp->next; |
1137 | } else |
1138 | tmp = *list = xmalloc_xmalloc_xmalloc(sizeof(abook_list)); |
1139 | |
1140 | tmp->data = xstrdup(str); |
1141 | tmp->next = NULL((void*)0); |
1142 | } |
1143 | |
1144 | void |
1145 | abook_list_free(abook_list **list) |
1146 | { |
1147 | abook_list *prev = NULL((void*)0), *tmp = *list; |
1148 | |
1149 | if(!list) |
1150 | return; |
1151 | |
1152 | while(tmp) { |
1153 | xfree(tmp->data)do { free(tmp->data); tmp->data = ((void*)0); } while(0 ); |
1154 | prev = tmp; |
1155 | tmp = tmp->next; |
1156 | xfree(prev)do { free(prev); prev = ((void*)0); } while(0); |
1157 | } |
1158 | |
1159 | *list = NULL((void*)0); |
1160 | } |
1161 | |
1162 | abook_list * |
1163 | csv_to_abook_list(char *str) |
1164 | { |
1165 | char *start, *p = str, *end; |
1166 | abook_list *list = NULL((void*)0); |
1167 | |
1168 | if(!str) |
1169 | return NULL((void*)0); |
1170 | |
1171 | SKIPWS(p)while(*(p) && ((*__ctype_b_loc ())[(int) (((unsigned char )*(p)))] & (unsigned short int) _ISspace)) p++; |
1172 | start = end = p; |
1173 | |
1174 | while(*p) { |
1175 | if(!strchr(", ", *p)(__extension__ (__builtin_constant_p (*p) && !__builtin_constant_p (", ") && (*p) == '\0' ? (char *) __rawmemchr (", ", *p) : __builtin_strchr (", ", *p)))) { |
1176 | end = ++p; |
1177 | continue; |
1178 | } |
1179 | |
1180 | if((*p == ',') && (end - start)) { |
1181 | abook_list_append(&list, xstrndup(start, end - start)); |
1182 | p++; |
1183 | SKIPWS(p)while(*(p) && ((*__ctype_b_loc ())[(int) (((unsigned char )*(p)))] & (unsigned short int) _ISspace)) p++; |
1184 | start = end = p; |
1185 | continue; |
1186 | } |
1187 | |
1188 | p++; |
1189 | } |
1190 | if(end - start) |
1191 | abook_list_append(&list, xstrndup(start, end - start)); |
1192 | |
1193 | return list; |
1194 | } |
1195 | |
1196 | char * |
1197 | abook_list_to_csv(abook_list *list) |
1198 | { |
1199 | abook_list *tmp; |
1200 | char *res = NULL((void*)0); |
1201 | |
1202 | for(tmp = list; tmp; tmp = tmp->next) { |
1203 | if(tmp == list) |
1204 | res = xstrdup(tmp->data); |
1205 | else { |
1206 | res = xrealloc_xmalloc_xrealloc(res, strlen(res)+strlen(tmp->data)+2); |
1207 | strcat(res, ","); |
1208 | strcat(res, tmp->data); |
1209 | } |
1210 | } |
1211 | |
1212 | return res; |
1213 | } |
1214 | |
1215 | void |
1216 | abook_list_rotate(abook_list **list, enum rotate_dir dir) |
1217 | { |
1218 | abook_list *tmp = *list; |
1219 | |
1220 | if(!tmp || !tmp->next) |
1221 | return; |
1222 | |
1223 | switch(dir) { |
1224 | case ROTATE_LEFT: |
1225 | for(; tmp && tmp->next; tmp = tmp->next) |
1226 | ; |
1227 | |
1228 | tmp->next = *list; |
1229 | tmp = *list; |
1230 | *list = (*list)->next; |
1231 | tmp->next = NULL((void*)0); |
1232 | break; |
1233 | case ROTATE_RIGHT: |
1234 | for(; tmp && tmp->next && tmp->next->next; |
1235 | tmp = tmp->next) |
1236 | ; |
1237 | |
1238 | tmp->next->next = *list; |
1239 | *list = tmp->next; |
1240 | tmp->next = NULL((void*)0); |
1241 | break; |
1242 | default: |
1243 | assert(0)((void) (0)); |
1244 | } |
1245 | } |
1246 | |
1247 | /* if str == NULL, deleting the list element */ |
1248 | void |
1249 | abook_list_replace(abook_list **list, int index, char *str) |
1250 | { |
1251 | abook_list *cur, *prev; |
1252 | int i = 0; |
1253 | |
1254 | cur = prev = *list; |
1255 | |
1256 | if((index == 0) && !str) { |
1257 | *list = cur->next; |
1258 | free(cur->data); |
1259 | free(cur); |
1260 | return; |
1261 | } |
1262 | |
1263 | while(1) { |
1264 | if(!cur) |
1265 | return; |
1266 | |
1267 | if(i == index) |
1268 | break; |
1269 | |
1270 | prev = cur; |
1271 | cur = cur->next; |
1272 | i++; |
1273 | } |
1274 | |
1275 | if(str) { |
1276 | free(cur->data); |
1277 | cur->data = xstrdup(str); |
1278 | } else { |
1279 | prev->next = cur->next; |
1280 | free(cur->data); |
1281 | free(cur); |
1282 | } |
1283 | } |
1284 | |
1285 | abook_list * |
1286 | abook_list_get(abook_list *list, int index) |
1287 | { |
1288 | int i = 0; |
1289 | |
1290 | while(1) { |
1291 | if(!list) |
1292 | return NULL((void*)0); |
1293 | |
1294 | if(i == index) |
1295 | return list; |
1296 | |
1297 | i++; |
1298 | list = list->next; |
1299 | } |
1300 | } |