/* * This file contains all of the formatted I/O functions. They * are essentially those from BDS C 1.5 with some alterations * to accomodate the I/O primitives of the standard library. * Last Edit 7/1/83 */ printf(format) char *format; { void fputc(); _spr(&format, &fputc, stdout); /* use "_spr" to form the output */ } sprintf(buffer,format) char *buffer, *format; { int _sspr(); _spr(&format, &_sspr, &buffer); /* call _spr to do all the work */ *buffer = '\0'; } _sspr(c,strptr) char **strptr; { *(*strptr)++ = c; } int fprintf(stream,format) char *format; FILE *stream; { void fputc(); _spr(&format, &fputc, stream); } int scanf(format) char *format; { char line[MAXLINE]; gets(line); /* get a line of input from user */ return _scn(line,&format); /* and scan it with "_scn" */ } int sscanf(line,format) char *line, *format; { return _scn(line,&format); /* let _scn do all the work */ } int fscanf(stream,format) char *format; FILE *stream; { char text[MAXLINE]; if (fgets(text,stream) == NULL) return 0; return _scn(text,&format); } _spr(fmt,putcf,arg1) int (*putcf)(); char **fmt; { char _uspr(), c, base, *sptr, *format; char wbuf[MAXLINE], *wptr, pf, ljflag, zfflag; int width, precision, *args; format = *fmt++; /* fmt first points to the format string */ args = fmt; /* now fmt points to the first arg value */ while (c = *format++) if (c == '%') { wptr = wbuf; precision = 6; ljflag = pf = zfflag = 0; if (*format == '-') { format++; ljflag++; } if (*format == '0') zfflag++; /* test for zero-fill */ width = (isdigit(*format)) ? _gv2(&format) : 0; if ((c = *format++) == '.') { precision = _gv2(&format); pf++; c = *format++; } switch(toupper(c)) { case 'D': if (*args < 0) { *wptr++ = '-'; *args = -*args; width--; } case 'U': base = 10; goto val; case 'X': base = 16; goto val; case 'O': base = 8; goto val; case 'B': base = 2; /* note that arbitrary bases can be added easily before this line */ val: width -= _uspr(&wptr,*args++,base); goto pad; case 'C': *wptr++ = *args++; width--; goto pad; case 'S': if (!pf) precision = 200; sptr = *args++; while (*sptr && precision) { *wptr++ = *sptr++; precision--; width--; } pad: *wptr = '\0'; pad2: wptr = wbuf; if (!ljflag) while (width-- > 0) (*putcf)(zfflag ? '0' : ' ',arg1); while (*wptr) (*putcf)(*wptr++,arg1) ; if (ljflag) while (width-- > 0) (*putcf)(' ',arg1) ; break; default: (*putcf)(c,arg1) ; } } else (*putcf)(c,arg1) ; } /* Internal routine used by "_spr" to perform ascii- to-decimal conversion and update an associated pointer: */ int _gv2(sptr) char **sptr; { int n; n = 0; while (isdigit(**sptr)) n = 10 * n + *(*sptr)++ - '0'; return n; } char _uspr(string, n, base) char **string; unsigned n; { char length; if (n b-1) return ERROR; else return c; }