Skip to content

Instantly share code, notes, and snippets.

@btmills
Last active December 13, 2022 01:44
Show Gist options
  • Save btmills/4201660 to your computer and use it in GitHub Desktop.
Save btmills/4201660 to your computer and use it in GitHub Desktop.
Unlimited fgets() - read input from the console with automatic buffer sizing.
#include <stdio.h>
#include <stdlib.h>
/*
* Similar to fgets(), but handles automatic reallocation of the buffer.
* Only parameter is the input stream.
* Return value is a string. Don't forget to free it.
*/
char* ufgets(FILE* stream)
{
unsigned int maxlen = 128, size = 128;
char* buffer = (char*)malloc(maxlen);
if(buffer != NULL) /* NULL if malloc() fails */
{
int ch = EOF;
int pos = 0;
/* Read input one character at a time, resizing the buffer as necessary */
while((ch = fgetc(stream)) != '\n' && ch != EOF && !feof(stream))
{
buffer[pos++] = ch;
if(pos == size) /* Next character to be inserted needs more memory */
{
size = pos + maxlen;
buffer = (char*)realloc(buffer, size);
}
}
buffer[pos] = '\0'; /* Null-terminate the completed string */
}
return buffer;
}
#include <stdio.h>
/*
* Similar to fgets(), but handles automatic reallocation of the buffer.
* Only parameter is the input stream.
* Return value is a string. Don't forget to free it.
*/
char* ufgets(FILE* stream);
@lilyhahn
Copy link

This helped me out a lot with a project I'm working on, thanks!

@migf1
Copy link

migf1 commented May 11, 2013

Alas, realloc() does not guarantee that the returned memory will be an extension of the original one. In that case, your function will leak the original buffer. You should also check & handle the case when realloc() fails.

Here is my go, with a bit more complicated but also a bit more flexible implementation: https://gist.github.com/migf1/5559176

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment