]>
git.ipfire.org Git - thirdparty/cups.git/blob - cups/snprintf.c
4 * snprintf functions for CUPS.
6 * Copyright 2007-2013 by Apple Inc.
7 * Copyright 1997-2007 by Easy Software Products.
9 * These coded instructions, statements, and computer programs are the
10 * property of Apple Inc. and are protected by Federal copyright
11 * law. Distribution and use rights are outlined in the file "LICENSE.txt"
12 * which should have been included with this file. If this file is
13 * file is missing or damaged, see the license at "http://www.cups.org/".
15 * This file is subject to the Apple OS-Developed Software exception.
19 * _cups_vsnprintf() - Format a string into a fixed size buffer.
20 * _cups_snprintf() - Format a string into a fixed size buffer.
24 * Include necessary headers...
27 #include "string-private.h"
30 #ifndef HAVE_VSNPRINTF
32 * '_cups_vsnprintf()' - Format a string into a fixed size buffer.
35 int /* O - Number of bytes formatted */
36 _cups_vsnprintf(char *buffer
, /* O - Output buffer */
37 size_t bufsize
, /* O - Size of output buffer */
38 const char *format
, /* I - printf-style format string */
39 va_list ap
) /* I - Pointer to additional arguments */
41 char *bufptr
, /* Pointer to position in buffer */
42 *bufend
, /* Pointer to end of buffer */
43 sign
, /* Sign of format width */
44 size
, /* Size character (h, l, L) */
45 type
; /* Format type character */
46 int width
, /* Width of field */
47 prec
; /* Number of characters of precision */
48 char tformat
[100], /* Temporary format string for sprintf() */
49 *tptr
, /* Pointer into temporary format */
50 temp
[1024]; /* Buffer for formatted numbers */
51 size_t templen
; /* Length of "temp" */
52 char *s
; /* Pointer to string */
53 int slen
; /* Length of string */
54 int bytes
; /* Total number of bytes needed */
58 * Loop through the format string, formatting as needed...
62 bufend
= buffer
+ bufsize
- 1;
74 if (bufptr
&& bufptr
< bufend
) *bufptr
++ = *format
;
79 else if (strchr(" -+#\'", *format
))
90 * Get width from argument...
94 width
= va_arg(ap
, int);
96 snprintf(tptr
, sizeof(tformat
) - (tptr
- tformat
), "%d", width
);
103 while (isdigit(*format
& 255))
105 if (tptr
< (tformat
+ sizeof(tformat
) - 1))
108 width
= width
* 10 + *format
++ - '0';
114 if (tptr
< (tformat
+ sizeof(tformat
) - 1))
122 * Get precision from argument...
126 prec
= va_arg(ap
, int);
128 snprintf(tptr
, sizeof(tformat
) - (tptr
- tformat
), "%d", prec
);
129 tptr
+= strlen(tptr
);
135 while (isdigit(*format
& 255))
137 if (tptr
< (tformat
+ sizeof(tformat
) - 1))
140 prec
= prec
* 10 + *format
++ - '0';
147 if (*format
== 'l' && format
[1] == 'l')
151 if (tptr
< (tformat
+ sizeof(tformat
) - 2))
159 else if (*format
== 'h' || *format
== 'l' || *format
== 'L')
161 if (tptr
< (tformat
+ sizeof(tformat
) - 1))
170 if (tptr
< (tformat
+ sizeof(tformat
) - 1))
178 case 'E' : /* Floating point formats */
183 if ((width
+ 2) > sizeof(temp
))
186 sprintf(temp
, tformat
, va_arg(ap
, double));
187 templen
= strlen(temp
):
189 bytes
+= (int)templen
;
193 if ((bufptr
+ templen
) > bufend
)
195 strlcpy(bufptr
, temp
, (size_t)(bufend
- bufptr
));
200 memcpy(bufptr
, temp
, templen
+ 1);
206 case 'B' : /* Integer formats */
214 if ((width
+ 2) > sizeof(temp
))
217 sprintf(temp
, tformat
, va_arg(ap
, int));
218 templen
= strlen(temp
):
220 bytes
+= (int)templen
;
224 if ((bufptr
+ templen
) > bufend
)
226 strlcpy(bufptr
, temp
, (size_t)(bufend
- bufptr
));
231 memcpy(bufptr
, temp
, templen
+ 1);
237 case 'p' : /* Pointer value */
238 if ((width
+ 2) > sizeof(temp
))
241 sprintf(temp
, tformat
, va_arg(ap
, void *));
242 templen
= strlen(temp
):
244 bytes
+= (int)templen
;
248 if ((bufptr
+ templen
) > bufend
)
250 strlcpy(bufptr
, temp
, (size_t)(bufend
- bufptr
));
255 memcpy(bufptr
, temp
, templen
+ 1);
261 case 'c' : /* Character or character array */
267 *bufptr
++ = va_arg(ap
, int);
270 if ((bufptr
+ width
) > bufend
)
271 width
= (int)(bufend
- bufptr
);
273 memcpy(bufptr
, va_arg(ap
, char *), (size_t)width
);
279 case 's' : /* String */
280 if ((s
= va_arg(ap
, char *)) == NULL
)
283 slen
= (int)strlen(s
);
284 if (slen
> width
&& prec
!= width
)
291 if ((bufptr
+ width
) > bufend
)
292 width
= (int)(bufend
- bufptr
);
299 memcpy(bufptr
, s
, (size_t)slen
);
300 memset(bufptr
+ slen
, ' ', (size_t)(width
- slen
));
304 memset(bufptr
, ' ', (size_t)(width
- slen
));
305 memcpy(bufptr
+ width
- slen
, s
, (size_t)slen
);
312 case 'n' : /* Output number of chars so far */
313 *(va_arg(ap
, int *)) = bytes
;
321 if (bufptr
&& bufptr
< bufend
)
329 * Nul-terminate the string and return the number of characters needed.
336 #endif /* !HAVE_VSNPRINT */
339 #ifndef HAVE_SNPRINTF
341 * '_cups_snprintf()' - Format a string into a fixed size buffer.
344 int /* O - Number of bytes formatted */
345 _cups_snprintf(char *buffer
, /* O - Output buffer */
346 size_t bufsize
, /* O - Size of output buffer */
347 const char *format
, /* I - printf-style format string */
348 ...) /* I - Additional arguments as needed */
350 int bytes
; /* Number of bytes formatted */
351 va_list ap
; /* Pointer to additional arguments */
354 va_start(ap
, format
);
355 bytes
= vsnprintf(buffer
, bufsize
, format
, ap
);
360 #endif /* !HAVE_SNPRINTF */