The prototype of ggets is "int ggets(char **ln);"
and for fggets is "int fggets(char **ln, FILE *f);"
My theory is that, having gotten complete lines, we are not in the
least interested in the terminating \n. The routine is written in
standard C, so is available anywhere. Returning the linelength
would be possible, but would complicate the simplified interface,
and thus could lead to errors. The return differentiates between
file errors/EOF and memory exhaustion.
The user has no control of trailing space stripping, that is
entirely up to the file system, not the interface routines. If the
blanks are there, ggets will return them.
What are the prototypes for fgetln and fparseln?
char *fgetln(FILE *stream, size_t *len);
char *fparseln(FILE *stream, size_t *len, size_t *lineno,
const char delim[3], int flags);
It's been awhile since I used fgetln(). As somebody else pointed
out--by e-mail--fgetln() returns a pointer that you don't own (the space
isn't immutable, but to persist the data you have to copy out). Also,
fgetln() doesn't return a true, NUL-terminated string. But, for most of my
purposes having the line length is far more useful than have an altered
string that I have to free (since sometimes you just want to parse
in-place and move on).
GNU getline(), I think, is a great compromise between
fgetln() and ggets(): ssize_t getline(char **buf, size_t *bufsiz, FILE *).
It's one of the rare GNU extensions that does most everything you want in
a more-or-less elegant manner:
getline() reads an entire line, storing the address of the buffer
containing the text into *lineptr. The buffer is null-terminated
and includes the newline character, if a newline delimiter was found.
If *lineptr is NULL, the getline() routine will allocate a buffer for
containing the line, which must be freed by the user program.
Alternatively, before calling getline(), *lineptr can contain a pointer
to a malloc()-allocated buffer *n bytes in size. If the buffer is not
large enough to hold the line read in, getline() resizes the buffer to
fit with realloc(), updating *lineptr and *n as necessary. In either
case, on a successful call, *lineptr and *n will be updated to reflect
the buffer address and size respectively.
...
On success, getline() ... return
the number of characters
read, including the delimiter character, but not including the termi-
nating null character.
fparseln() is probably not a fair comparison since it's not strictly a
general purpose line buffering interface. From the man page:
The fparseln() function returns a pointer to the next logical line
from the stream referenced by stream. This string is null terminated and
dynamically allocated on each invocation. It is the responsibility of
the caller to free the pointer.
By default, if a character is escaped, both it and the preceding escape
character will be present in the returned string. Various flags alter
this behaviour.