Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #define SZINIT 120
- /** getln reads up to n characters from stream into s, (if n=0 no limit).
- * Reading continues until n characters read (or newline or EOF reached).
- * s is initially reallocated n (or SZINIT, if n=0) + 1 bytes. (no overrun).
- * If n=0, s is reallocated as needed to read an entire line. A final call
- * to realloc trims the amount of memory allocated only that required. On
- * success, the length of s is returned, -1 otherwise.
- */
- ssize_t getln (char **s, size_t *n, FILE *stream)
- {
- #ifndef SZINIT
- #define SZINIT 1024
- #endif
- int c = 0;
- size_t maxc = *n ? *n : SZINIT;
- ssize_t nchr = 0;
- if (!(*s = realloc (*s, (maxc + 1) * sizeof **s)))
- return -1;
- while ((size_t)nchr < maxc && (c = fgetc (stream)) != EOF && c != '\n')
- {
- (*s)[nchr++] = c; /* assign char to s, increment nchr */
- if ((size_t)nchr == maxc) /* test if limit is reached */
- {
- if (*n) { /* if reading only *n chars, flush stdin */
- while ((c = fgetc (stream)) != '\n' && c != EOF);
- break;
- }
- else { /* realloc as required, adding SZINIT */
- void *tmp = realloc (*s, (maxc + SZINIT) * sizeof **s);
- if (!tmp)
- return -1; /* return failure on short read */
- *s = tmp;
- maxc += SZINIT;
- }
- }
- }
- (*s)[nchr] = 0; /* nul-terminate */
- /* final realloc to trim allocation to exact amount.
- * validate: update s only on success. (optional)
- */
- void *tmp = realloc (*s, (nchr + 1) * sizeof **s);
- if (tmp)
- *s = tmp;
- return nchr || c != EOF ? nchr : -1;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement