to not be limited to a given size reading a string you can use the modifier 'm' :
char * p;
if (scanf("%ms", &p) == 1) {
...use p;
free(p); /* when stop to be usefull
}
From the man of scanf :
An optional 'm' character. This is used with string conversions (%s, %c, %[), and
relieves the caller of the need to allocate a corresponding buffer to hold the
input: instead, scanf() allocates a buffer of sufficient size, and assigns the
address of this buffer to the corresponding pointer argument, which should be a
pointer to a char * variable (this variable does not need to be initialized before
the call). The caller should subsequently free(3) this buffer when it is no longer
required.
The previous way allows to red a 'word', to read a full line removing spaces (' ', newline, tab ...) at the beginning:
#include <stdio.h>
#include <stdlib.h>
int main()
{
char * p;
if (scanf(" %m[^\n]", &p) == 1) {
printf("'%s'\n", p);
free(p);
}
else
puts("error (EOF...)");
return 0;
}
Compilation and execution:
/tmp % gcc -Wall c.c
/tmp % ./a.out
aze qsd
'aze qsd'
/tmp % ./a.out < /dev/null
error (EOF...)
/tmp %
If you do not have that modifier (not posix ...) to read a full line as it is you can do :
#include <stdio.h>
#include <stdlib.h>
int main()
{
char * p = malloc(1);
size_t len = 0;
int c;
while (((c = getchar()) != '\n') && (c != EOF)) {
p = realloc(p, len+1);
if (p == NULL) {
puts("not enough memory");
return -1;
}
p[len++] = c;
}
p[len] = 0;
printf("'%s'\n", p);
free(p);
return 0;
}
Compilation and execution :
/tmp % gcc -Wall c.c
/tmp % ./a.out
aze qsd
' aze qsd'
/tmp % ./a.out < /dev/null
''
/tmp %