enum function bug?

Chris Torek chris at umcp-cs.UUCP
Wed Oct 1 15:02:20 AEST 1986


>In article <572 at opus.nbires.UUCP> rcd at nbires.UUCP (Dick Dunn) writes:
>>The problem goes a little deeper than this.  Consider that if an enum is
>>defined in a .h file, and that header file is used in two separate .c
>>files, you have (by some annoyingly reasonable argument) two separate
>>types!  [Substitute canonical discussion of name equivalence vs structural

I do not agree, but I have always been a fan of structural equivalence.
Anyway, onward:

In article <226 at BMS-AT.UUCP> stuart at BMS-AT.UUCP (Stuart D. Gathman) replies:
>Did you ever wonder how lint handles _structures_ in .h files?  It's really
>very simple: anything defined in the same file (even included files)
>with the same name is the same.  The same logic works for enum.  

An interesting idea.

>Note that identical structures defined in different files (i.e.
>a function returning a structure that is not defined with a .h file)
>are considered different types by lint.  I like this because it
>encourages defining global structures in only one place (a header file).

Let us try an experiment.  First:

	% more x.c y.c
	::::::::::::::
	x.c
	::::::::::::::
	struct s { int i; };
	proc(p) struct s *p; { p->i = 1; }
	struct s func() { struct s temp; temp.i = 0; return (temp); }
	::::::::::::::
	y.c
	::::::::::::::
	struct s { int i; };
	struct s func();
	main() { struct s temp; temp = func(); proc(&temp); }
	% lint -h x.c y.c
	x.c:
	y.c:
	%

Here the structures are described twice, but are identical in name
and shape.  Lint is happy with this.  Now:

	% more x.c y.c
	::::::::::::::
	x.c
	::::::::::::::
	struct s2 { int i; };
	proc(p) struct s2 *p; { p->i = 1; }
	struct s2 func() { struct s2 temp; temp.i = 0; return (temp); }
	::::::::::::::
	y.c
	::::::::::::::
	struct s { int i; };
	struct s func();
	main() { struct s temp; temp = func(); proc(&temp); }
	% lint -h x.c y.c
	x.c:
	y.c:
	%

Clearly lint does not care about names.  And one last change:

	% more x.c y.c
	% lint -h x.c y.c
	::::::::::::::
	x.c
	::::::::::::::
	struct s2 { int i, j; };
	proc(p) struct s2 *p; { p->i = p->j = 1; }
	struct s2 func() { struct s2 temp; temp.i = temp.j = 0; return (temp); }
	::::::::::::::
	y.c
	::::::::::::::
	struct s { int i; };
	struct s func();
	main() { struct s temp; temp = func(); proc(&temp); }
	x.c:
	y.c:
	func value used inconsistently	x.c(3)  ::  y.c(3)
	proc, arg. 1 used inconsistently	x.c(2)  ::  y.c(3)
	%

My (4.3BSD-beta) lint clearly uses structural conformability, not
names or files.  (As it happens, I prefer this behaviour.)

Ideally, a new strongly-typed language (which would not then be C)
should declare constraints on types, instead of having the compiler
second guessing the programmer.  For example, some enumerations
might be ordered, others not:

	enum color { red ; green ; blue };
		/* pred(green) undefined */
	enum numbers { zero, one, two, many };
		/* succ(two) = many */

If several operations are sensible, make sure all can be implemented
---though not necessarily by embedding them directly in the language.

For now, C enumerated types are rather a mess, and I usually avoid
them entirely.
-- 
In-Real-Life: Chris Torek, Univ of MD Comp Sci Dept (+1 301 454 1516)
UUCP:	seismo!umcp-cs!chris
CSNet:	chris at umcp-cs		ARPA:	chris at mimsy.umd.edu



More information about the Comp.lang.c mailing list