combine sections of code to print out buffer
SCCS-vsn: lib/libc/stdio/vfprintf.c 5.24
*/
#if defined(LIBC_SCCS) && !defined(lint)
*/
#if defined(LIBC_SCCS) && !defined(lint)
-static char sccsid[] = "@(#)vfprintf.c 5.23 (Berkeley) %G%";
+static char sccsid[] = "@(#)vfprintf.c 5.24 (Berkeley) %G%";
#endif /* LIBC_SCCS and not lint */
#include <sys/types.h>
#endif /* LIBC_SCCS and not lint */
#include <sys/types.h>
#include <stdio.h>
#include <ctype.h>
#include <stdio.h>
#include <ctype.h>
+/* 11-bit exponent (VAX G floating point) is 308 decimal digits */
+#define MAXEXP 308
+/* 128 bit fraction takes up 39 decimal digits; max reasonable precision */
+#define MAXFRACT 39
+
+#define BUF (MAXEXP+MAXFRACT+1) /* + decimal point */
#define PUTC(ch) {++cnt; putc((char)ch, fp);}
#define PUTC(ch) {++cnt; putc((char)ch, fp);}
register char *t;
double _double;
u_long _ulong;
register char *t;
double _double;
u_long _ulong;
- int base, flags, prec, size, width;
- char padc, sign, *digs, buf[MAXBUF], *_cvt();
+ int base, flags, fpprec, prec, size, width;
+ char padc, sign, *digs, buf[BUF], *_cvt();
fmt = fmt0;
digs = "0123456789abcdef";
fmt = fmt0;
digs = "0123456789abcdef";
+ flags = fpprec = width = 0;
prec = -1;
padc = ' ';
sign = '\0';
prec = -1;
padc = ' ';
sign = '\0';
case 'g':
case 'G':
_double = va_arg(argp, double);
case 'g':
case 'G':
_double = va_arg(argp, double);
+ /*
+ * don't bother to do unrealistic precision; just
+ * pad it with zeroes later. This keeps buffer size
+ * rational.
+ */
+ if (prec > MAXFRACT) {
+ fpprec = prec - MAXFRACT;
+ prec = MAXFRACT;
+ }
size = _cvt(_double, prec, flags, *fmt, padc, &sign,
buf, buf + sizeof(buf)) - buf;
t = buf;
size = _cvt(_double, prec, flags, *fmt, padc, &sign,
buf, buf + sizeof(buf)) - buf;
t = buf;
-pforw: if (!(flags&LADJUST) && width)
- for (n = size; n++ < width;)
- PUTC(padc);
- if (fp->_cnt - (n = size) >= 0) {
- cnt += n;
- fp->_cnt -= n;
- bcopy(t, fp->_ptr, n);
- fp->_ptr += n;
- }
- else for (; n--; ++t)
- PUTC(*t);
- if (flags&LADJUST)
- while (width-- > size)
- PUTC(' ');
- break;
case 'u':
ARG();
base = 10;
case 'u':
ARG();
base = 10;
number: if (!_ulong && !prec)
break;
number: if (!_ulong && !prec)
break;
do {
*t-- = digs[_ulong % base];
_ulong /= base;
} while(_ulong);
do {
*t-- = digs[_ulong % base];
_ulong /= base;
} while(_ulong);
- for (size = buf + MAXBUF - 1 - t; size < prec; ++size)
+ for (size = buf + BUF - 1 - t; size < prec; ++size)
+ digs = "0123456789abcdef";
/* alternate mode for hex and octal numbers */
if (flags&ALT)
/* alternate mode for hex and octal numbers */
if (flags&ALT)
if (padc == ' ') {
*t-- = *fmt;
*t-- = '0';
if (padc == ' ') {
*t-- = *fmt;
*t-- = '0';
}
else {
PUTC('0');
PUTC(*fmt);
}
else {
PUTC('0');
PUTC(*fmt);
break;
case 8:
if (t[1] != '0') {
*t-- = '0';
break;
case 8:
if (t[1] != '0') {
*t-- = '0';
}
break;
}
if (sign) {
/* avoid "0000-3" */
}
break;
}
if (sign) {
/* avoid "0000-3" */
- if (!(flags&LADJUST))
- while (size++ < width)
+pforw: if (!(flags&LADJUST) && width)
+ for (n = size + fpprec; n++ < width;)
- while (++t < buf + MAXBUF)
+ if (fp->_cnt - (n = size) >= 0) {
+ cnt += n;
+ fp->_cnt -= n;
+ bcopy(t, fp->_ptr, n);
+ fp->_ptr += n;
+ }
+ else for (; n--; ++t)
- while (width-- > size)
- PUTC(' ');
- digs = "0123456789abcdef";
+ while (fpprec--)
+ PUTC('0');
+ if (flags&LADJUST)
+ for (n = size + fpprec; ++n < width;)
+ PUTC(' ');
break;
case '\0': /* "%?" prints ?, unless ? is NULL */
return(cnt);
break;
case '\0': /* "%?" prints ?, unless ? is NULL */
return(cnt);