gets() is dead

F

Flash Gordon

Tor Rustad wrote, On 25/04/07 19:35:
Kenny said:
Well, it's not, there is no problem using gets(), when the programmer
control the input.

For example, when writing a quick-and-short-lived test module, which is
needed only during development.

The overhead of using fgets is pretty minimal even in that situation.
 
K

Keith Thompson

CBFalconer said:
Not needed, it can be handled.
[snip]

I don't know what you mean by this. If you mean that eliminating
unmodified %s in scanf is not needed, can you explain? For example:

char s[N];
scanf("%s", s);

reads a (blank-delimited) word from stdin. If the user types, say,
2*N non-blank characters, it will invoke undefined behavior. How can
this be "handled" (other than by avoiding "%s")?
 
C

CBFalconer

Keith said:
CBFalconer said:
Richard Heathfield wrote:
.... snip ...

Not needed, it can be handled.
[snip]

I don't know what you mean by this. If you mean that eliminating
unmodified %s in scanf is not needed, can you explain? For example:

char s[N];
scanf("%s", s);

reads a (blank-delimited) word from stdin. If the user types, say,
2*N non-blank characters, it will invoke undefined behavior. How
can this be "handled" (other than by avoiding "%s")?

By not using unmodified %s. That is a user choice. No such
available for gets.
 
K

Keith Thompson

CBFalconer said:
Keith said:
CBFalconer said:
Richard Heathfield wrote:
... snip ...

Next stop: unmodified %s in scanf.

Not needed, it can be handled.
[snip]

I don't know what you mean by this. If you mean that eliminating
unmodified %s in scanf is not needed, can you explain? For example:

char s[N];
scanf("%s", s);

reads a (blank-delimited) word from stdin. If the user types, say,
2*N non-blank characters, it will invoke undefined behavior. How
can this be "handled" (other than by avoiding "%s")?

By not using unmodified %s. That is a user choice. No such
available for gets.

The suggestion, I think, is to disallow the use of "%s" with scanf.

Disallowing a particular argument value to a function is not as
straightforward as eliminating a function altogether, but the
rationale is the same. gets(..) cannot be used safely;
scanf("%s", ...) cannot be used safely.
 
M

Malcolm McLean

Keith Thompson said:
CBFalconer said:
Keith said:
Richard Heathfield wrote:
... snip ...

Next stop: unmodified %s in scanf.

Not needed, it can be handled.
[snip]

I don't know what you mean by this. If you mean that eliminating
unmodified %s in scanf is not needed, can you explain? For example:

char s[N];
scanf("%s", s);

reads a (blank-delimited) word from stdin. If the user types, say,
2*N non-blank characters, it will invoke undefined behavior. How
can this be "handled" (other than by avoiding "%s")?

By not using unmodified %s. That is a user choice. No such
available for gets.

The suggestion, I think, is to disallow the use of "%s" with scanf.

Disallowing a particular argument value to a function is not as
straightforward as eliminating a function altogether, but the
rationale is the same. gets(..) cannot be used safely;
scanf("%s", ...) cannot be used safely.
And fgets() is in practise too difficult for any but the best programmers to
use safely.
 
K

Keith Thompson

Malcolm McLean said:
And fgets() is in practise too difficult for any but the best
programmers to use safely.

Huh???

fgets() has limitations, but it doesn't pose anything like the danger
of gets() or scanf("%s", ...). It mishandles long lines by leaving
the remainder in the input stream, which is a minor inconvenience
compared to the undefined behavior of gets().
 
R

Richard Heathfield

Keith Thompson said:
"Malcolm McLean" <[email protected]> writes:

Huh???

Quite. It's a ludicrous claim.
fgets() has limitations, but it doesn't pose anything like the danger
of gets() or scanf("%s", ...). It mishandles long lines by leaving
the remainder in the input stream, which is a minor inconvenience
compared to the undefined behavior of gets().

What else could fgets do with long lines, other than leave them in the
input stream, if it isn't allowed to call *alloc()?
 
J

jaysome

In the discussion group comp.std.c Mr Gwyn wrote:

< quote >

... gets has been declared an obsolescent feature and
deprecated, as a direct result of my submitting a DR about it
(which originally suggested a less drastic change). (The official
impact awaits wrapping up the latest batch of TCs into a formal
amending document, and getting it approved and published.)

< end quote >

This is a very positive development. After all those discussions,
reason prevailed and we got rid of that wart.

It *is* possible to influence the comitee as it seems.
This is good news.

jacob

So, I guess the reasoning goes, in C0x or possibly even C1x, we'll all be
relieved of having to deal with gets()?

Will compiler vendors jump on the bandwagon of conforming to the latest
standard and forbid us to use gets(), just like they jumped on the
bandwagon of adopting the now-more-than-8-year-old C99 standard, and
allowed us to use "//" comments and declare variables in-line and use some
great keywords like "restrict"?

And if they do, will we all jump on their bandwagon and switch to their
latest and greatest C0x or C1x compiler--just like we all jumped on the
C99 compiler bandwagon--just so that we can take advantage of the great
feature of deprecating gets()?

I think not.

Although Mr. Gwyn's intentions are laudable, his connection with reality
is arguably questionable, and regrettably about 17 years too late.

Best regards
 
K

Keith Thompson

Richard Heathfield said:
Keith Thompson said: [...]
fgets() has limitations, but it doesn't pose anything like the danger
of gets() or scanf("%s", ...). It mishandles long lines by leaving
the remainder in the input stream, which is a minor inconvenience
compared to the undefined behavior of gets().

What else could fgets do with long lines, other than leave them in the
input stream, if it isn't allowed to call *alloc()?

Well, it could discard them, but that would be dumb.
 
R

Richard Bos

Tor Rustad said:
Well, it's not, there is no problem using gets(), when the programmer
control the input.
s/when/if/.

For example, when writing a quick-and-short-lived test module, which is
needed only during development.

You clearly do not have cats, children, _or_ typo-prone fingers.

Richard
 
W

websnarf

Well, it's not, there is no problem using gets(), when the programmer
control the input.

For example, when writing a quick-and-short-lived test module, which is
needed only during development.

As if we need further proof of just how dangerous gets() is. (James
Dow Allen has posted similar sentiments here in the past.) Even the
face of knowing exactly what's wrong with it, people claim its usable.
 
C

Chris Dollin

Malcolm said:
And fgets() is in practise too difficult for any but the best programmers to
use safely.

I think that's absurd. Do you have a reason for this interesting point of view?

--
"Go not to the Drazi for counsel, Unsaid /Babylon 5/
for they will answer both 'green' and 'purple'."

Hewlett-Packard Limited registered no:
registered office: Cain Road, Bracknell, Berks RG12 1HN 690597 England
 
R

Richard Heathfield

Malcolm McLean said:

And fgets() is in practise too difficult for any but the best
programmers to use safely.

Oh dear. I sure hope I'm a counter-example, because otherwise I've been
using fgets() unsafely for years.
 
F

Francine.Neary

This is a very positive development. After all those discussions,
reason prevailed and we got rid of that wart.

It *is* possible to influence the comitee as it seems.
This is good news.

I wouldn't say it's good news. Firstly, it will break a lot of old
code if it's dropped. Secondly, gets() is completely safe *as long as
_you_ control the data passed to it*. Of course it should never be
used in production code, but for private/development/toy code I find
it extremely useful.
 
E

Eric Sosman

jaysome wrote On 04/26/07 03:13,:
So, I guess the reasoning goes, in C0x or possibly even C1x, we'll all be
relieved of having to deal with gets()?

Will compiler vendors jump on the bandwagon of conforming to the latest
standard and forbid us to use gets(), just like they jumped on the
bandwagon of adopting the now-more-than-8-year-old C99 standard, and
allowed us to use "//" comments and declare variables in-line and use some
great keywords like "restrict"?

And if they do, will we all jump on their bandwagon and switch to their
latest and greatest C0x or C1x compiler--just like we all jumped on the
C99 compiler bandwagon--just so that we can take advantage of the great
feature of deprecating gets()?

I think not.

Although Mr. Gwyn's intentions are laudable, his connection with reality
is arguably questionable, and regrettably about 17 years too late.

What part of the quoted text is connected tenuously to
reality? It says that "gets has been declared an obsolescent
feature and deprecated." Do you have a reason to believe
this is an inaccurate description of the state of affairs?

It was you, not Doug Gwyn, who suggested that the action
of the Committee would "relieve" the world of gets(). It was
you, not Gwyn, who described the miraculous consequences of
gets()' forthcoming status. It is you, not Gwyn, who are
peddling fantasy.
 
G

Gregor H.

I wouldn't say it's good news. Firstly, it will break a lot of old
code if it's dropped.
Which is rather good news, given that the code you are talking about
makes use of "gets()" --- which is an inherently unsafe function.
Secondly, gets() is completely safe *as long as _you_ control the
data passed to it*.
Hear, hear. Well, sure, a gun is also completely safe as long you do
not aim at people with it.
Of course it should never be used in production code, but for
private/development/toy code I find it extremely useful.
It's extremely idiotic to have such a function in the first place,
even if only interested in "private/development/toy code" ...

Why do you think that

fgets(buffer, MAXBUF, stdin);

is less useful than

gets(buffer);

???


And if you have problems with the '\n' read in into the buffer, then
you might just add the code

char *pszTemp;
if ((pszTemp = strchr(buffer, '\n')) != NULL)
*pszTemp = '\0';

Done.


G.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
474,431
Messages
2,571,679
Members
48,796
Latest member
Greg L.

Latest Threads

Top