From b3bcf33e9f1a9487c0bdbcc0507cc5fd22369af8 Mon Sep 17 00:00:00 2001 From: giraffedata Date: Sun, 7 Oct 2018 02:25:17 +0000 Subject: add pm_getline git-svn-id: http://svn.code.sf.net/p/netpbm/code/trunk@3391 9d0c8265-081b-0410-96cb-a4ca84ce46f8 --- lib/pm.h | 7 ++++++ lib/pmfileio.c | 67 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 74 insertions(+) (limited to 'lib') diff --git a/lib/pm.h b/lib/pm.h index 4f56dc5a..3fc92fb4 100644 --- a/lib/pm.h +++ b/lib/pm.h @@ -373,6 +373,13 @@ char* pm_read_unknown_size(FILE * const ifP, long * const buf); +void +pm_getline(FILE * const ifP, + char ** const bufferP, + size_t * const bufferSzP, + int * const eofP, + size_t * const lineLenP); + short pm_bs_short(short const s); diff --git a/lib/pmfileio.c b/lib/pmfileio.c index 738ba336..33f89110 100644 --- a/lib/pmfileio.c +++ b/lib/pmfileio.c @@ -839,6 +839,73 @@ pm_read_unknown_size(FILE * const file, +void +pm_getline(FILE * const ifP, + char ** const bufferP, + size_t * const bufferSzP, + int * const eofP, + size_t * const lineLenP) { +/*---------------------------------------------------------------------------- + This is like POSIX 'getline'. + + But we don't include the newline in the returned line. +-----------------------------------------------------------------------------*/ + char * buffer; + size_t bufferSz; + bool gotLine; + bool eof; + size_t nReadSoFar; + + buffer = *bufferP; /* initial value */ + bufferSz = *bufferSzP; /* initial value */ + + for (nReadSoFar = 0, gotLine = false, eof = false; + !gotLine && !eof; ) { + + int rc; + + rc = fgetc(ifP); + + if (rc == EOF) { + if (ferror(ifP)) + pm_error("Error reading input file. fgets() failed with " + "errno %d (%s)", errno, strerror(errno)); + + if (nReadSoFar == 0) { + /* Didn't get anything before EOF, so return EOF */ + eof = true; + } else { + /* End of file ends the line */ + gotLine = true; + } + } else { + char const c = (char)rc; + + if (c == '\n') { + /* Newline ends the line, and is not part of it */ + gotLine = true; + } else { + if (nReadSoFar + 2 > bufferSz) { + /* + 2 = 1 for 'c', one for terminating NUL */ + bufferSz += 128; + REALLOCARRAY(buffer, bufferSz); + } + buffer[nReadSoFar++] = c; + } + } + } + + if (gotLine) + buffer[nReadSoFar] = '\0'; + + *eofP = eof; + *bufferP = buffer; + *bufferSzP = bufferSz; + *lineLenP = nReadSoFar; +} + + + union cheat { uint32_t l; short s; -- cgit 1.4.1