Re: Proper way to input a dynamically-allocated string




Eric Sosman wrote:
> Michel Rouzic wrote:
> > Eric Sosman wrote:
> >
> >>Michel Rouzic wrote:
> >>
> >>
> >>>I know it must sound like a newbie question, but I never really had to
> >>>bother with that before, and I didn't even find an answer in the c.l.c
> >>>FAQ
> >>>
> >>>I'd like to know what's the really proper way for input a string in an
> >>>array of char that's dynamically allocated. I mean, I wish not to see
> >>>any such things as char mystring[100]; I don't want to see any number
> >>>(if possible) I just want to declare something like char *mystring; and
> >>>then I don't know how allocate it with just as many chars (with the
> >>>space for the \0 of course) as you get from stdin.
> >>>
> >>>I'd really like to know once for all what's the smartest way of
> >>>inputing strings from stdin and storing them in a way so they take just
> >>>the needed space and I don't want to see any number such as 100 or
> >>>10,000 or even 4,294,967,296 in my code. Any way it can be done?
> >>
> >> Let's suppose you're reading complete '\n'-terminated lines,
> >>the way fgets() does but with no explicit length limit. You
> >>could do something like this (pseudocode, no error checking):
> >>
> >> buffer = <empty>
> >> do {
> >> expand buffer with realloc()
> >> append next input character
> >> } while (character wasn't '\n');
> >> expand buffer with realloc()
> >> append '\0'
> >>
> >> For efficiency's sake you'd probably want to avoid quite
> >>so many trips in and out of the memory allocator, so a refinement
> >>would be to start with a roomier buffer and expand by more than
> >>one character at a time if necessary. (My own function for doing
> >>this -- everybody writes one eventually -- begins with 100 characters
> >>and adds half the buffer's current size each time it needs to expand:
> >>100, 150, 225, ...)
> >>
> >> Once you've read the entire line you can, if you like, realloc()
> >>the buffer one final time to trim it to the exact size. I find
> >>that's seldom worth the bother: your program is probably going to
> >>process the line and free() or re-use the buffer pretty soon.
> >
> >
> > That's the method I like the best. I wouldn't bother with make larger
> > buffers anyways, would make things too complicated, and things don't
> > have to be sooo efficient when it comes to inputting strings, what
> > matters the most is the result. i think I made your idea work pretty
> > good, tell me if you think yous potted anything wrong with it, I GDBed
> > it and the content of the memory looked fine
> >
> > int i;
> > char *mystring;
> >
> > i=0;
> > mystring=NULL;
> > do
> > {
> > mystring=realloc(mystring, i+1);
> > mystring[i]=getchar();
> > i++;
> > }
> > while (mystring[i-1]!='\n');
> > mystring[i-1]='\0';
>
> That's the general idea. As written, though, it's not
> very robust: it's oblivious to realloc() failures and to
> end-of-file or errors on the standard input. Pay attention
> to the Sixth Commandment


"If a function be advertised to return an error code in the event of
difficulties, thou shalt check for that code, yea, even though the
checks triple the size of thy code..."

ok, I guess I should do that but.... well... as it says, it makes the
code much longer and makes it harder to read and, well, I wouldn't know
what to do with an error anyways, I mean, if the return code ain't
right, i might display something like "the return code ain't right\n"
and don't know what I should do.

realloc() failures? never heard of that (maybe cuz im quite new to all
that), what can happen with it? how can you get an EOF or some error
from stdin?

you know, I care to know about why I should check for errors, and about
what can cause them and what I should do about it, but so far (and you
can understand that) I like to keep my code as simple as possible,
mostly that I consider that my program should work only as far as it is
used correctly (like, if a program is supposed to have a .wav file in
input, and the user put a .mp3 or anything else instead, I don't wanna
bother with doing stuff that will tell him "you need to input a .wav
file", i rather let him have a segmentation fault)

.



Relevant Pages

  • Re: Buffer or Realloc?
    ... better to allocate memory and realloc it for the size of the what is ... between deciding to use a fixed size buffer or allocating memory ... Fixed size arrays are good for things that whose contents *CANNOT* ... becomes extremely small when I realloc it. ...
    (comp.lang.c)
  • Re: openssh vulnerability
    ... > second value to realloc). ... call clean-up functions, and apparently one of those clean-up ... functions may call buffer_free() on that same buffer that's in ... talking about writing nulls... ...
    (Vuln-Dev)
  • Re: Crash by allocationg small blocks
    ... "Sebastien LEGUET" wrote: ... >I try to exeute this code and I have a crash during the execution. ... >realloc function return NULL. ... In addition, when the buffer cannot be extended in-place, growing ...
    (microsoft.public.vc.language)
  • Re: Proposed addition of malloc_size_np()
    ... Since malloc_sizeis defined on at least one platform to return the requested size, maybe a name like malloc_allocated_sizewould help avoid that confusion, and make it clear that the consumer is getting back a commitment and not a hint for future realloc(), etc. ... Suppose that we are about to write to a string that we know is malloced, and we want to be sure that we aren't overflowing the allocated buffer. ... We can store that information, or we could just query the size. ... However, unless there is a way of getting the size of each allocation, I don't know how much to subtract from the count for realloc/free calls. ...
    (freebsd-arch)
  • Re: Uses of setvbuf()
    ... Eric Sosman wrote: ... buffer over an automatically allocated one? ... Can we call setvbuf() on ... the implementor often believes he ...
    (comp.lang.c)