diff options
author | David Lamparter <equinox@diac24.net> | 2019-05-12 21:07:45 +0200 |
---|---|---|
committer | David Lamparter <equinox@diac24.net> | 2019-06-03 16:44:05 +0200 |
commit | 86bfbddf6ed922a755c29f23ffcef00240563a20 (patch) | |
tree | a763144efdbada1bcf59875fdf9d809d28f74bdf | |
parent | lib: import FreeBSD's printf (diff) | |
download | frr-86bfbddf6ed922a755c29f23ffcef00240563a20.tar.xz frr-86bfbddf6ed922a755c29f23ffcef00240563a20.zip |
lib/printf: cut down to size
remove various FreeBSD specific bits, as well as the entirety of locale
support.
Signed-off-by: David Lamparter <equinox@diac24.net>
-rw-r--r-- | lib/printf/printf-pos.c | 8 | ||||
-rw-r--r-- | lib/printf/printfcommon.h | 29 | ||||
-rw-r--r-- | lib/printf/vfprintf.c | 235 |
3 files changed, 29 insertions, 243 deletions
diff --git a/lib/printf/printf-pos.c b/lib/printf/printf-pos.c index 40f91e8af..f4104c52b 100644 --- a/lib/printf/printf-pos.c +++ b/lib/printf/printf-pos.c @@ -32,18 +32,13 @@ * SUCH DAMAGE. */ -#if defined(LIBC_SCCS) && !defined(lint) -static char sccsid[] = "@(#)vfprintf.c 8.1 (Berkeley) 6/4/93"; -#endif /* LIBC_SCCS and not lint */ #include <sys/cdefs.h> -__FBSDID("$FreeBSD$"); /* * This is the code responsible for handling positional arguments * (%m$ and %m$.n$) for vfprintf() and vfwprintf(). */ -#include "namespace.h" #include <sys/types.h> #include <limits.h> @@ -55,7 +50,6 @@ __FBSDID("$FreeBSD$"); #include <string.h> #include <wchar.h> -#include "un-namespace.h" #include "printflocal.h" #ifdef NL_ARGMAX @@ -646,7 +640,7 @@ __grow_type_table(struct typetable *types) u_int n, newsize; /* Detect overflow */ - if (types->nextarg > NL_ARGMAX) + if (types->nextarg > MAX_POSARG) return (-1); newsize = oldsize * 2; diff --git a/lib/printf/printfcommon.h b/lib/printf/printfcommon.h index c120f1eba..68454bce1 100644 --- a/lib/printf/printfcommon.h +++ b/lib/printf/printfcommon.h @@ -52,8 +52,6 @@ #include <float.h> #include <math.h> -#include "floatio.h" -#include "gdtoa.h" #define DEFPREC 6 @@ -68,7 +66,7 @@ static CHAR *__ultoa(u_long, CHAR *, int, int, const char *); struct io_state { FILE *fp; struct __suio uio; /* output information: summary */ - struct __siov iov[NIOV];/* ... and individual io vectors */ + struct iovec iov[NIOV];/* ... and individual io vectors */ }; static inline void @@ -86,16 +84,13 @@ io_init(struct io_state *iop, FILE *fp) * remain valid until io_flush() is called. */ static inline int -io_print(struct io_state *iop, const CHAR * __restrict ptr, int len, locale_t locale) +io_print(struct io_state *iop, const CHAR * __restrict ptr, int len) { iop->iov[iop->uio.uio_iovcnt].iov_base = (char *)ptr; iop->iov[iop->uio.uio_iovcnt].iov_len = len; iop->uio.uio_resid += len; - if (++iop->uio.uio_iovcnt >= NIOV) - return (__sprint(iop->fp, &iop->uio, locale)); - else - return (0); + return (0); } /* @@ -114,14 +109,13 @@ static const CHAR zeroes[PADSIZE] = * or the zeroes array. */ static inline int -io_pad(struct io_state *iop, int howmany, const CHAR * __restrict with, - locale_t locale) +io_pad(struct io_state *iop, int howmany, const CHAR * __restrict with) { int n; while (howmany > 0) { n = (howmany >= PADSIZE) ? PADSIZE : howmany; - if (io_print(iop, with, n, locale)) + if (io_print(iop, with, n)) return (-1); howmany -= n; } @@ -134,7 +128,7 @@ io_pad(struct io_state *iop, int howmany, const CHAR * __restrict with, */ static inline int io_printandpad(struct io_state *iop, const CHAR *p, const CHAR *ep, - int len, const CHAR * __restrict with, locale_t locale) + int len, const CHAR * __restrict with) { int p_len; @@ -142,19 +136,12 @@ io_printandpad(struct io_state *iop, const CHAR *p, const CHAR *ep, if (p_len > len) p_len = len; if (p_len > 0) { - if (io_print(iop, p, p_len, locale)) + if (io_print(iop, p, p_len)) return (-1); } else { p_len = 0; } - return (io_pad(iop, len - p_len, with, locale)); -} - -static inline int -io_flush(struct io_state *iop, locale_t locale) -{ - - return (__sprint(iop->fp, &iop->uio, locale)); + return (io_pad(iop, len - p_len, with)); } /* diff --git a/lib/printf/vfprintf.c b/lib/printf/vfprintf.c index 70f5074e2..69b9e2da9 100644 --- a/lib/printf/vfprintf.c +++ b/lib/printf/vfprintf.c @@ -37,11 +37,7 @@ * SUCH DAMAGE. */ -#if defined(LIBC_SCCS) && !defined(lint) -static char sccsid[] = "@(#)vfprintf.c 8.1 (Berkeley) 6/4/93"; -#endif /* LIBC_SCCS and not lint */ #include <sys/cdefs.h> -__FBSDID("$FreeBSD$"); /* * Actual printf innards. @@ -49,163 +45,38 @@ __FBSDID("$FreeBSD$"); * This code is large and complicated... */ -#include "namespace.h" #include <sys/types.h> +#include <sys/uio.h> #include <ctype.h> #include <errno.h> #include <limits.h> -#include <locale.h> #include <stddef.h> #include <stdint.h> #include <stdio.h> #include <stdlib.h> #include <string.h> #include <wchar.h> -#include <printf.h> #include <stdarg.h> -#include "xlocale_private.h" -#include "un-namespace.h" -#include "libc_private.h" -#include "local.h" -#include "fvwrite.h" -#include "printflocal.h" +#define NO_FLOATING_POINT -static int __sprint(FILE *, struct __suio *, locale_t); -static int __sbprintf(FILE *, locale_t, const char *, va_list) __printflike(3, 0) - __noinline; -static char *__wcsconv(wchar_t *, int); +int __vfprintf(FILE *fp, const char *fmt0, va_list ap); -#define CHAR char -#include "printfcommon.h" +struct __suio { + size_t uio_resid; -struct grouping_state { - char *thousands_sep; /* locale-specific thousands separator */ - int thousep_len; /* length of thousands_sep */ - const char *grouping; /* locale-specific numeric grouping rules */ - int lead; /* sig figs before decimal or group sep */ - int nseps; /* number of group separators with ' */ - int nrepeats; /* number of repeats of the last group */ + struct iovec *uio_iov; + size_t uio_iovcnt; }; -/* - * Initialize the thousands' grouping state in preparation to print a - * number with ndigits digits. This routine returns the total number - * of bytes that will be needed. - */ -static int -grouping_init(struct grouping_state *gs, int ndigits, locale_t loc) -{ - struct lconv *locale; - - locale = localeconv_l(loc); - gs->grouping = locale->grouping; - gs->thousands_sep = locale->thousands_sep; - gs->thousep_len = strlen(gs->thousands_sep); - - gs->nseps = gs->nrepeats = 0; - gs->lead = ndigits; - while (*gs->grouping != CHAR_MAX) { - if (gs->lead <= *gs->grouping) - break; - gs->lead -= *gs->grouping; - if (*(gs->grouping+1)) { - gs->nseps++; - gs->grouping++; - } else - gs->nrepeats++; - } - return ((gs->nseps + gs->nrepeats) * gs->thousep_len); -} - -/* - * Print a number with thousands' separators. - */ -static int -grouping_print(struct grouping_state *gs, struct io_state *iop, - const CHAR *cp, const CHAR *ep, locale_t locale) -{ - const CHAR *cp0 = cp; - - if (io_printandpad(iop, cp, ep, gs->lead, zeroes, locale)) - return (-1); - cp += gs->lead; - while (gs->nseps > 0 || gs->nrepeats > 0) { - if (gs->nrepeats > 0) - gs->nrepeats--; - else { - gs->grouping--; - gs->nseps--; - } - if (io_print(iop, gs->thousands_sep, gs->thousep_len, locale)) - return (-1); - if (io_printandpad(iop, cp, ep, *gs->grouping, zeroes, locale)) - return (-1); - cp += *gs->grouping; - } - if (cp > ep) - cp = ep; - return (cp - cp0); -} - -/* - * Flush out all the vectors defined by the given uio, - * then reset it so that it can be reused. - */ -static int -__sprint(FILE *fp, struct __suio *uio, locale_t locale) -{ - int err; - - if (uio->uio_resid == 0) { - uio->uio_iovcnt = 0; - return (0); - } - err = __sfvwrite(fp, uio); - uio->uio_resid = 0; - uio->uio_iovcnt = 0; - return (err); -} - -/* - * Helper function for `fprintf to unbuffered unix file': creates a - * temporary buffer. We only work on write-only files; this avoids - * worries about ungetc buffers and so forth. - */ -static int -__sbprintf(FILE *fp, locale_t locale, const char *fmt, va_list ap) -{ - int ret; - FILE fake = FAKE_FILE; - unsigned char buf[BUFSIZ]; - - /* XXX This is probably not needed. */ - if (prepwrite(fp) != 0) - return (EOF); - - /* copy the important variables */ - fake._flags = fp->_flags & ~__SNBF; - fake._file = fp->_file; - fake._cookie = fp->_cookie; - fake._write = fp->_write; - fake._orientation = fp->_orientation; - fake._mbstate = fp->_mbstate; +#include "printflocal.h" - /* set up the buffer */ - fake._bf._base = fake._p = buf; - fake._bf._size = fake._w = sizeof(buf); - fake._lbfsize = 0; /* not actually used, but Just In Case */ +static char *__wcsconv(wchar_t *, int); - /* do the work, then copy any error status */ - ret = __vfprintf(&fake, locale, fmt, ap); - if (ret >= 0 && __fflush(&fake)) - ret = EOF; - if (fake._flags & __SERR) - fp->_flags |= __SERR; - return (ret); -} +#define CHAR char +#include "printfcommon.h" /* * Convert a wide character string argument for the %ls format to a multibyte @@ -267,32 +138,6 @@ __wcsconv(wchar_t *wcsarg, int prec) } /* - * MT-safe version - */ -int -vfprintf_l(FILE * __restrict fp, locale_t locale, const char * __restrict fmt0, - va_list ap) -{ - int ret; - FIX_LOCALE(locale); - - FLOCKFILE_CANCELSAFE(fp); - /* optimise fprintf(stderr) (and other unbuffered Unix files) */ - if ((fp->_flags & (__SNBF|__SWR|__SRW)) == (__SNBF|__SWR) && - fp->_file >= 0) - ret = __sbprintf(fp, locale, fmt0, ap); - else - ret = __vfprintf(fp, locale, fmt0, ap); - FUNLOCKFILE_CANCELSAFE(); - return (ret); -} -int -vfprintf(FILE * __restrict fp, const char * __restrict fmt0, va_list ap) -{ - return vfprintf_l(fp, __get_locale(), fmt0, ap); -} - -/* * The size of the buffer we use as scratch space for integer * conversions, among other things. We need enough space to * write a uintmax_t in octal (plus one byte). @@ -307,7 +152,7 @@ vfprintf(FILE * __restrict fp, const char * __restrict fmt0, va_list ap) * Non-MT-safe version */ int -__vfprintf(FILE *fp, locale_t locale, const char *fmt0, va_list ap) +__vfprintf(FILE *fp, const char *fmt0, va_list ap) { char *fmt; /* format string */ int ch; /* character from fmt */ @@ -319,7 +164,6 @@ __vfprintf(FILE *fp, locale_t locale, const char *fmt0, va_list ap) int prec; /* precision from format; <0 for N/A */ int saved_errno; char sign; /* sign prefix (' ', '+', '-', or \0) */ - struct grouping_state gs; /* thousands' grouping info */ #ifndef NO_FLOATING_POINT /* @@ -374,21 +218,18 @@ __vfprintf(FILE *fp, locale_t locale, const char *fmt0, va_list ap) /* BEWARE, these `goto error' on error. */ #define PRINT(ptr, len) { \ - if (io_print(&io, (ptr), (len), locale)) \ + if (io_print(&io, (ptr), (len))) \ goto error; \ } #define PAD(howmany, with) { \ - if (io_pad(&io, (howmany), (with), locale)) \ + if (io_pad(&io, (howmany), (with))) \ goto error; \ } #define PRINTANDPAD(p, ep, len, with) { \ - if (io_printandpad(&io, (p), (ep), (len), (with), locale)) \ - goto error; \ -} -#define FLUSH() { \ - if (io_flush(&io, locale)) \ + if (io_printandpad(&io, (p), (ep), (len), (with))) \ goto error; \ } +#define FLUSH() do { } while (0) /* * Get the argument indexed by nextarg. If the argument table is @@ -453,17 +294,6 @@ __vfprintf(FILE *fp, locale_t locale, const char *fmt0, va_list ap) val = GETARG (int); \ } - if (__use_xprintf == 0 && getenv("USE_XPRINTF")) - __use_xprintf = 1; - if (__use_xprintf > 0) - return (__xvprintf(fp, fmt0, ap)); - - /* sorry, fprintf(read_only_file, "") returns EOF, not 0 */ - if (prepwrite(fp) != 0) { - errno = EBADF; - return (EOF); - } - savserr = fp->_flags & __SERR; fp->_flags &= ~__SERR; @@ -477,7 +307,7 @@ __vfprintf(FILE *fp, locale_t locale, const char *fmt0, va_list ap) ret = 0; #ifndef NO_FLOATING_POINT dtoaresult = NULL; - decimal_point = localeconv_l(locale)->decimal_point; + decimal_point = "."; /* The overwhelmingly common case is decpt_len == 1. */ decpt_len = (decimal_point[1] == '\0' ? 1 : strlen(decimal_point)); #endif @@ -505,7 +335,6 @@ __vfprintf(FILE *fp, locale_t locale, const char *fmt0, va_list ap) dprec = 0; width = 0; prec = -1; - gs.grouping = NULL; sign = '\0'; ox[1] = '\0'; @@ -628,7 +457,6 @@ reswitch: switch (ch) { mbseqlen = wcrtomb(cp = buf, (wchar_t)GETARG(wint_t), &mbs); if (mbseqlen == (size_t)-1) { - fp->_flags |= __SERR; goto error; } size = (int)mbseqlen; @@ -773,8 +601,6 @@ fp_common: /* space for decimal pt and following digits */ if (prec || flags & ALT) size += prec + decpt_len; - if ((flags & GROUPING) && expt > 0) - size += grouping_init(&gs, expt, locale); } break; #endif /* !NO_FLOATING_POINT */ @@ -844,7 +670,6 @@ fp_common: else { convbuf = __wcsconv(wcp, prec); if (convbuf == NULL) { - fp->_flags |= __SERR; goto error; } cp = convbuf; @@ -915,8 +740,6 @@ number: if ((dprec = prec) >= 0) size = buf + BUF - cp; if (size > BUF) /* should never happen */ abort(); - if ((flags & GROUPING) && size != 0) - size += grouping_init(&gs, size, locale); break; default: /* "%?" prints ?, unless ? is NUL */ if (ch == '\0') @@ -979,12 +802,7 @@ number: if ((dprec = prec) >= 0) #endif /* leading zeroes from decimal precision */ PAD(dprec - size, zeroes); - if (gs.grouping) { - if (grouping_print(&gs, &io, cp, buf+BUF, locale) < 0) - goto error; - } else { - PRINT(cp, size); - } + PRINT(cp, size); #ifndef NO_FLOATING_POINT } else { /* glue together f_p fragments */ if (!expchar) { /* %[fF] or sufficiently short %[gG] */ @@ -996,17 +814,8 @@ number: if ((dprec = prec) >= 0) /* already handled initial 0's */ prec += expt; } else { - if (gs.grouping) { - n = grouping_print(&gs, &io, - cp, dtoaend, locale); - if (n < 0) - goto error; - cp += n; - } else { - PRINTANDPAD(cp, dtoaend, - expt, zeroes); - cp += expt; - } + PRINTANDPAD(cp, dtoaend, expt, zeroes); + cp += expt; if (prec || flags & ALT) PRINT(decimal_point,decpt_len); } @@ -1042,10 +851,6 @@ error: #endif if (convbuf != NULL) free(convbuf); - if (__sferror(fp)) - ret = EOF; - else - fp->_flags |= savserr; if ((argtable != NULL) && (argtable != statargtable)) free (argtable); return (ret); |