#include #include #include #include #include "stdio-util.h" typedef struct ws WS; typedef struct as AS; struct ws { FILE *inner; WRAP_W *wrapper; void *priv; } ; struct as { char *b; int a; int l; char **sp; int *lp; } ; static int wrap_w_w(void *sv, const char *buf, int len) { WS *s; int i; s = sv; for (i=0;iwrapper->put)(s->priv,buf[i]); return(len); } static int wrap_w_c(void *sv) { WS *s; s = sv; (*s->wrapper->done)(s->priv); free(s); return(0); } static void wrap_put_inner(unsigned char ch, void *sv) { putc(ch,((WS *)sv)->inner); } FILE *open_wrap_w(FILE *inner, WRAP_W *wrapper) { WS *s; FILE *f; int e; void *p; s = malloc(sizeof(WS)); if (! s) return(0); f = funopen(s,0,&wrap_w_w,0,&wrap_w_c); if (! f) { e = errno; free(s); errno = e; return(0); } p = (*wrapper->init)(&wrap_put_inner,s); if (! p) { e = errno; s->inner = 0; s->wrapper = 0; s->priv = 0; fclose(f); free(s); errno = e; return(0); } s->inner = inner; s->wrapper = wrapper; s->priv = p; return(f); } static int accum_w(void *sv, const char *data, int len) { AS *s; s = sv; if (s->sp) { if (s->l+len > s->a) s->b = realloc(s->b,s->a=s->l+len); bcopy(data,s->b+s->l,len); } s->l += len; return(len); } static int accum_c(void *sv) { AS *s; s = sv; if (s->sp) *s->sp = s->b; if (s->lp) *s->lp = s->l; free(s); return(0); } FILE *open_accum(char **sp, int *lp) { AS *s; FILE *f; int e; s = malloc(sizeof(AS)); if (! s) return(0); f = funopen(s,0,&accum_w,0,&accum_c); if (! f) { e = errno; free(s); errno = e; return(0); } s->b = 0; s->a = 0; s->l = 0; s->sp = sp; s->lp = lp; return(f); }