[net.lang.c] Jumping into blocks is a no-no

stevesu@copper.UUCP (Steve Summit) (04/13/86)

In article <360@hadron.UUCP>, jsdy@hadron.UUCP (Joseph S. D. Yao) writes:
> One major problem is that this code jumps into blocks
> [the effect of case C: and case D: ].  This is something that X3J11
> warns about.  I thought K&R did, too; but I can't find it.  It is
> generally a bad practice, although most compilers seem to allow it
> without too much trouble.

I used to worry about jumps into blocks, too, but I'm afraid
I've really gotten into the habit of using them.  Just how bad
are they?  It's pretty easy arrange that simpleminded, one-pass
code generators generate loops that can be safely jumped into.
I understand that this sort of thing makes an optimizing code
generator's life miserable, but since so much existing code jumps
into blocks, I would guess that optimizing compiler writers have
to worry about it anyway.

Most people agree that goto's are pretty acceptable for handling
error conditions.  For instance:

	if(stbuf.st_uid != getuid())
		{
nope:		printf("I don't think you want to delete this file.\n");
		return;
		}

	if(strcmp(name, "vmunix") == 0)
		goto nope;

	unlink(name);

	return;

(Of course, this usage is not a jump into a loop, which would be
more worrisome.)  Given that the jumped-into block terminates
with a return, it's quite easy to eliminate the jump into a
block, but only at the expense of a _s_e_c_o_n_d goto:

	if(stbuf.st_uid != getuid())
		goto nope;

	if(strcmp(name, "vmunix") == 0)
		goto nope;

	unlink(name);

	return;

nope:	printf("I don't think you want to delete this file.\n");
	return;

What do people think?  It seems to me that if gotos are legal at
all, they might as well be guaranteed to work for jumping into
blocks.  How strong is the "warning" in X3J11 that Joe mentions?

                                         Steve Summit
                                         tektronix!copper!stevesu

jsdy@hadron.UUCP (Joseph S. D. Yao) (04/17/86)

In article <275@copper.UUCP> stevesu@copper.UUCP (Steve Summit) writes:
>	if(stbuf.st_uid != getuid())
>		{
>nope:		printf("I don't think you want to delete this file.\n");
>		return;
>		}
>	if(strcmp(name, "vmunix") == 0)
>		goto nope;
>	unlink(name);
>	return;

	if (stbuf.st_uid != getuid() ||
	    strcmp(name, "vmunix") == 0) {
		printf("I don't think you want to delete this file.\n");
		return;
	}
	unlink(name);
	return;

If the conditions get any more complex, have your function return
a value, and let the calling function perform the error condition
(or not) depending on the value.  It is  n o t  generally agreed
that, just because goto's are used au hazard in UNIX code, that
this is a good thing, even for error returns.  I will defend the
use of goto's in certain cases (and again cite Knuth), but this is
not one of them, nor is any other attempt to jump into blocks.

The pathological case (which occurs quickly) is called "spaghetti
code."  It is the bane of software engineers' lives.

Oh, by the way, there are a lot of people who believe that examining
UNIX source code shows you a lot of good code and a heckuvalotta very
bad code.  Case in point.
-- 

	Joe Yao		hadron!jsdy@seismo.{CSS.GOV,ARPA,UUCP}