From a5ae899a48709d1afaa297470322364e4c5b1b0e Mon Sep 17 00:00:00 2001 From: FRIGN Date: Wed, 11 Feb 2015 20:13:43 +0100 Subject: [PATCH] Scrap readrune(), introducing fgetrune() Interface as proposed by cls, but internally rewritten after a few considerations. The code is much shorter and to the point, aligning itself with other standard functions. It should also be much faster, which is not bad. --- Makefile | 2 +- expand.c | 2 +- libutf/fgetrune.c | 34 ++++++++++++++++++++++++++++++++++ libutf/readrune.c | 47 ----------------------------------------------- paste.c | 4 ++-- tail.c | 4 ++-- tr.c | 2 +- unexpand.c | 2 +- utf.h | 3 ++- wc.c | 2 +- 10 files changed, 45 insertions(+), 57 deletions(-) create mode 100644 libutf/fgetrune.c delete mode 100644 libutf/readrune.c diff --git a/Makefile b/Makefile index d70df20..9d969d3 100644 --- a/Makefile +++ b/Makefile @@ -23,7 +23,7 @@ LIBUTFSRC =\ libutf/runetype.c\ libutf/utf.c\ libutf/chartorunearr.c\ - libutf/readrune.c\ + libutf/fgetrune.c\ libutf/writerune.c\ libutf/isalnumrune.c\ libutf/isalpharune.c\ diff --git a/expand.c b/expand.c index 2d1cc84..8adaa24 100644 --- a/expand.c +++ b/expand.c @@ -39,7 +39,7 @@ expand(const char *file, FILE *fp) size_t bol = 1, col = 0, i; Rune r; - while (readrune(file, fp, &r)) { + while (efgetrune(&r, fp, file)) { switch (r) { case '\t': if (tablistlen == 1) diff --git a/libutf/fgetrune.c b/libutf/fgetrune.c new file mode 100644 index 0000000..d8ca712 --- /dev/null +++ b/libutf/fgetrune.c @@ -0,0 +1,34 @@ +/* See LICENSE file for copyright and license details. */ +#include +#include +#include +#include + +#include "../utf.h" + +int +fgetrune(Rune *p, FILE *fp) +{ + char buf[UTFmax]; + int i; + + for (i = 0; i < UTFmax && (buf[i] = fgetc(fp)) != EOF && ++i ;) + if (charntorune(p, buf, i) > 0) + break; + if (ferror(fp)) + return -1; + + return i; +} + +int +efgetrune(Rune *p, FILE *fp, const char *file) +{ + int ret; + + if ((ret = fgetrune(p, fp)) < 0) { + fprintf(stderr, "fgetrune %s: %s\n", file, strerror(errno)); + exit(1); + } + return ret; +} diff --git a/libutf/readrune.c b/libutf/readrune.c deleted file mode 100644 index 3fda9ef..0000000 --- a/libutf/readrune.c +++ /dev/null @@ -1,47 +0,0 @@ -/* See LICENSE file for copyright and license details. */ -#include -#include -#include -#include - -#include "../utf.h" - -int -readrune(const char *file, FILE *fp, Rune *r) -{ - char buf[UTFmax]; - int c, i; - - if ((c = fgetc(fp)) == EOF) { - if (ferror(fp)) { - fprintf(stderr, "%s: read error: %s\n", - file, strerror(errno)); - exit(1); - } - return 0; - } - - if (c < Runeself) { - *r = (Rune)c; - return 1; - } - - buf[0] = c; - for (i = 1; i < UTFmax; ) { - if ((c = fgetc(fp)) == EOF) { - if (ferror(fp)) { - fprintf(stderr, "%s: read error: %s\n", - file, strerror(errno)); - exit(1); - } - *r = Runeerror; - return i; - } - buf[i++] = c; - if (fullrune(buf, i)) { - chartorune(r, buf); - break; - } - } - return i; -} diff --git a/paste.c b/paste.c index fd8ca77..32832d7 100644 --- a/paste.c +++ b/paste.c @@ -23,7 +23,7 @@ sequential(struct fdescr *dsc, int fdescrlen, Rune *delim, size_t delimlen) d = 0; last = 0; - while (readrune(dsc[i].name, dsc[i].fp, &c)) { + while (efgetrune(&c, dsc[i].fp, dsc[i].name)) { if (last == '\n') { if (delim[d] != '\0') writerune("", stdout, &delim[d]); @@ -54,7 +54,7 @@ nextline: d = delim[i % delimlen]; c = 0; - for (; readrune(dsc[i].name, dsc[i].fp, &c) ;) { + for (; efgetrune(&c, dsc[i].fp, dsc[i].name) ;) { for (m = last + 1; m < i; m++) writerune("", stdout, &(delim[m % delimlen])); last = i; diff --git a/tail.c b/tail.c index 9063656..8b8dc38 100644 --- a/tail.c +++ b/tail.c @@ -29,7 +29,7 @@ dropinit(FILE *fp, const char *str) if (len > 0 && buf[len - 1] == '\n') i++; } else { - while (i < num && (len = readrune(str, fp, &r))) + while (i < num && (len = efgetrune(&r, fp, str))) i++; } free(buf); @@ -52,7 +52,7 @@ taketail(FILE *fp, const char *str) } else { r = ecalloc(num, sizeof *r); - for (i = j = 0; readrune(str, fp, &r[i]); ) + for (i = j = 0; efgetrune(&r[i], fp, str); ) i = j = (i + 1) % num; } if (ferror(fp)) diff --git a/tr.c b/tr.c index 47ce6c7..2d6d37b 100644 --- a/tr.c +++ b/tr.c @@ -204,7 +204,7 @@ main(int argc, char *argv[]) if (set2check && cflag && !dflag) eprintf("set2 can't be imaged to from a complement.\n"); read: - if (!readrune("", stdin, &r)) + if (!efgetrune(&r, stdin, "")) return 0; off1 = off2 = 0; for (i = 0; i < set1ranges; i++) { diff --git a/unexpand.c b/unexpand.c index 26573f4..0b16f74 100644 --- a/unexpand.c +++ b/unexpand.c @@ -73,7 +73,7 @@ unexpand(const char *file, FILE *fp) size_t last = 0, col = 0, i; int bol = 1; - while (readrune(file, fp, &r)) { + while (efgetrune(&r, fp, file)) { switch (r) { case ' ': if (!bol && !aflag) diff --git a/utf.h b/utf.h index 663b4ed..bd58f0a 100644 --- a/utf.h +++ b/utf.h @@ -59,6 +59,7 @@ int isxdigitrune(Rune); Rune tolowerrune(Rune); Rune toupperrune(Rune); -int readrune(const char *, FILE *, Rune *); +int fgetrune(Rune *, FILE *); +int efgetrune(Rune *, FILE *, const char *); void writerune(const char *, FILE *, Rune *); int chartorunearr(const char*, Rune **); diff --git a/wc.c b/wc.c index e782950..2a881a5 100644 --- a/wc.c +++ b/wc.c @@ -34,7 +34,7 @@ wc(FILE *fp, const char *str) Rune c; size_t nc = 0, nl = 0, nw = 0; - while ((rlen = readrune(str, fp, &c))) { + while ((rlen = efgetrune(&c, fp, str))) { nc += (cmode == 'c') ? rlen : (c != Runeerror) ? 1 : 0; if (c == '\n')