From 078b4ccf0b65d655d81e9f4fc6e1284773e1dda4 Mon Sep 17 00:00:00 2001 From: Pixel Date: Sat, 5 Feb 2011 13:05:37 -0800 Subject: Re-structured the *scanf and *printf functions. --- libc/src/xprintf.c | 94 +++--------------------------------------------------- libc/src/xscanf.c | 4 +-- libc/src/yscanf.c | 55 ++++++++++++++++++++++++++++++++ 3 files changed, 61 insertions(+), 92 deletions(-) create mode 100644 libc/src/yscanf.c (limited to 'libc/src') diff --git a/libc/src/xprintf.c b/libc/src/xprintf.c index 30659f7..269d77c 100644 --- a/libc/src/xprintf.c +++ b/libc/src/xprintf.c @@ -213,7 +213,7 @@ static int getdigit(long double *val, int *cnt){ ** seems to make a big difference in determining how fast this beast ** will run. */ -static int vxprintf(func,arg,format,ap) +int vxprintf(func,arg,format,ap) void (*func)(const char*,int,void*); void *arg; const char *format; @@ -664,20 +664,6 @@ static int vxprintf(func,arg,format,ap) return errorflag ? -1 : count; } /* End of function */ -/* -** This non-standard function is still occasionally useful.... -*/ -int xprintf( - void (*func)(char*,int,void*), - void *arg, - const char *format, - ... -){ - va_list ap; - va_start(ap,format); - return vxprintf(func,arg,format,ap); -} - /* ** Now for string-print, also as found in any standard library. ** Add to this the snprint function which stops added characters @@ -713,19 +699,6 @@ static void sout(txt,amt,arg) ((struct s_strargument*)arg)->next = head; } -int sprintf(char *buf, const char *fmt, ...){ - int rc; - va_list ap; - struct s_strargument arg; - - va_start(ap,fmt); - arg.next = buf; - arg.last = 0; - *arg.next = 0; - rc = vxprintf(sout,&arg,fmt,ap); - va_end(ap); - return rc; -} int vsprintf(char *buf,const char *fmt,va_list ap){ struct s_strargument arg; arg.next = buf; @@ -733,19 +706,6 @@ int vsprintf(char *buf,const char *fmt,va_list ap){ *buf = 0; return vxprintf(sout,&arg,fmt,ap); } -int snprintf(char *buf, size_t n, const char *fmt, ...){ - int rc; - va_list ap; - struct s_strargument arg; - - va_start(ap,fmt); - arg.next = buf; - arg.last = &arg.next[n-1]; - *arg.next = 0; - rc = vxprintf(sout,&arg,fmt,ap); - va_end(ap); - return rc; -} int vsnprintf(char *buf, size_t n, const char *fmt, va_list ap){ struct s_strargument arg; arg.next = buf; @@ -799,31 +759,6 @@ static void mout(zNewText,nNewChar,arg) ** We changed the name to TclMPrint() to conform with the Tcl private ** routine naming conventions. */ -int asprintf(char ** out, const char *zFormat, ...){ - va_list ap; - struct sgMprintf sMprintf; - char *zNew; - char zBuf[200]; - int r; - - va_start(ap,zFormat); - sMprintf.nChar = 0; - sMprintf.nAlloc = sizeof(zBuf); - sMprintf.zText = zBuf; - sMprintf.zBase = zBuf; - r = vxprintf(mout,&sMprintf,zFormat,ap); - va_end(ap); - if( sMprintf.zText==sMprintf.zBase ){ - zNew = malloc( sMprintf.nChar+1 ); - if( zNew ) strcpy(zNew,zBuf); - }else{ - zNew = realloc(sMprintf.zText,sMprintf.nChar+1); - } - - *out = zNew; - - return r; -} /* This is the varargs version of mprintf. ** @@ -860,31 +795,10 @@ static void fout(zNewText,nNewChar,arg) int nNewChar; void *arg; { - fwrite(zNewText,1,nNewChar,(FILE*)arg); + write(*(int*)arg,zNewText,nNewChar); } /* The public interface routines */ -int fprintf(FILE *pOut, const char *zFormat, ...){ - va_list ap; - int retc; - - va_start(ap,zFormat); - retc = vxprintf(fout,pOut,zFormat,ap); - va_end(ap); - return retc; -} -int vfprintf(FILE *pOut, const char *zFormat, va_list ap){ - return vxprintf(fout,pOut,zFormat,ap); -} -int printf(const char *zFormat, ...){ - va_list ap; - int retc; - - va_start(ap,zFormat); - retc = vxprintf(fout,stdout,zFormat,ap); - va_end(ap); - return retc; -} -int vprintf(const char *zFormat, va_list ap){ - return vxprintf(fout,stdout,zFormat,ap); +int vdprintf(int fd, const char *zFormat, va_list ap){ + return vxprintf(fout,&fd,zFormat,ap); } diff --git a/libc/src/xscanf.c b/libc/src/xscanf.c index ad6f190..d121722 100755 --- a/libc/src/xscanf.c +++ b/libc/src/xscanf.c @@ -11,7 +11,7 @@ * VAL(a) leads to 1 if a is true and valid */ #define NEXT(c) ((c)=xgetc(opaque),size++,incount++) -#define PREV(c) do{if((c)!=EOF)xungetc((c),opaque);size--;incount--;}while(0) +#define PREV(c) do{if((c)!=EOF)xungetc(opaque,(c));size--;incount--;}while(0) #define VAL(a) ((a)&&size<=width) #ifdef NOFLOATINGPOINT @@ -30,7 +30,7 @@ static const unsigned char undef[3][sizeof(double)]= /* Undefined numeric values }; #endif -int vxscanf(int (*xgetc)(void *),void (*xungetc)(int,void*),void *opaque,const char *format,va_list args) +int vxscanf(int (*xgetc)(void *),void (*xungetc)(void*,int),void *opaque,const char *format,va_list args) { size_t blocks=0,incount=0; int c=0; diff --git a/libc/src/yscanf.c b/libc/src/yscanf.c new file mode 100644 index 0000000..3d2a488 --- /dev/null +++ b/libc/src/yscanf.c @@ -0,0 +1,55 @@ +#include "stdio.h" + +struct opaque_t { + union { + const char * p; + int fd; + }; + uint8_t bsize; + char backbuffer[3]; +}; + +static int str_getc(void * _opaque) { + struct opaque_t * opaque = (struct opaque_t *) _opaque; + int r; + + if (opaque->bsize) + return opaque->backbuffer[--(opaque->bsize)]; + + r = *(opaque->p++); + + return r ? r : EOF; +} + +static int file_getc(void * _opaque) { + struct opaque_t * opaque = (struct opaque_t *) _opaque; + uint8_t v; + + if (opaque->bsize) + return opaque->backbuffer[--(opaque->bsize)]; + + if (read(opaque->fd, &v, 1) != 1) + return EOF; + return v; +} + +static void scanf_ungetc(void * _opaque, int c) { + struct opaque_t * opaque = (struct opaque_t *) _opaque; + + if (opaque->bsize < sizeof(opaque->backbuffer)) + opaque->backbuffer[opaque->bsize++] = c; +} + +int vsscanf(const char * str, const char * format, va_list ap) { + struct opaque_t opaque; + opaque.p = str; + opaque.bsize = 0; + return vxscanf(str_getc, scanf_ungetc, &opaque, format, ap); +} + +int vdscanf(int fd, const char * format, va_list ap) { + struct opaque_t opaque; + opaque.fd = fd; + opaque.bsize = 0; + return vxscanf(file_getc, scanf_ungetc, &opaque, format, ap); +} -- cgit v1.2.3