[comp.unix.wizards] unsigned sizeof

stanonik@nprdc.navy.mil (Ron Stanonik) (02/15/90)

We ran into a "feature" while porting a program to our 3B2/600G
running sysV rel 3.2.2 V3: sizeof() returns unsigned.

The code looked like

	struct arf buf[MAX-1];
	while ((cnt = read(fd, buf, sizeof(buf))) >= sizeof(buf[0])) {
		do stuff with cnt arfs in buf
	}

The intent, apparently, is to reduce the number of reads by reading
several arf structs at once.  The problem occurs when the read returns
-1; since sizeof is unsigned the -1 is coerced into a big positive
number.

Yes, 2nd edition K&R says the result of sizeof is unsigned (though
it also says the type is implementation-defined, p204, which I find
contradictory).  Why though?  Why make sizeof unsigned?

Sorry if this is old news.  It was a surprise to us; ie, sizeof
on our suns and vax (4bsd) returns signed.

Thanks,

Ron Stanonik
stanonik@nprdc.navy.mil
ucsd!nprdc!stanonik

gwyn@smoke.BRL.MIL (Doug Gwyn) (02/15/90)

In article <6042@arctic.nprdc.arpa> stanonik@nprdc.navy.mil (Ron Stanonik) writes:
>Yes, 2nd edition K&R says the result of sizeof is unsigned (though
>it also says the type is implementation-defined, p204, which I find
>contradictory).  Why though?  Why make sizeof unsigned?

sizeof was changed to produce an unsigned int somewhere around 1980.
The main reason was that a signed int was simply unable to express the
size of some C data objects encountered in split-I&D PDP-11 applications.
It is also logically unsigned anyway.

>Sorry if this is old news.  It was a surprise to us; ie, sizeof
>on our suns and vax (4bsd) returns signed.

Well, their C compilers were based on old, decrepit versions of PCC.
And non-portable programs abound, so you really shouldn't be surprised
that you encountered one.

dstewart@fas.ri.cmu.edu (David B Stewart) (02/15/90)

In article <6042@arctic.nprdc.arpa> stanonik@nprdc.navy.mil (Ron Stanonik) writes:
>We ran into a "feature" while porting a program to our 3B2/600G
>running sysV rel 3.2.2 V3: sizeof() returns unsigned.
>
>The code looked like
>
>	struct arf buf[MAX-1];
>	while ((cnt = read(fd, buf, sizeof(buf))) >= sizeof(buf[0])) {
>		do stuff with cnt arfs in buf
>	}
>
>The intent, apparently, is to reduce the number of reads by reading
>several arf structs at once.  The problem occurs when the read returns
>-1; since sizeof is unsigned the -1 is coerced into a big positive
>number.
>
>Yes, 2nd edition K&R says the result of sizeof is unsigned (though
>it also says the type is implementation-defined, p204, which I find
>contradictory).  Why though?  Why make sizeof unsigned?
>
>Sorry if this is old news.  It was a surprise to us; ie, sizeof
>on our suns and vax (4bsd) returns signed.
>
>Thanks,
>
>Ron Stanonik
>stanonik@nprdc.navy.mil
>ucsd!nprdc!stanonik
Newsgroups: comp.unix.wizards
Subject: Virtual Address Caching on Sun 3/260
Keywords: 
Distribution: 
Organization: Carnegie-Mellon University, CS/RI


Newsgroups: comp.unix.wizards
Subject: Re: vmunix: stropen: out of streams in SunOS 4.0 ??
Keywords: 
Distribution: 
References: <21119@adm.BRL.MIL> <2548@auspex.auspex.com>
Organization: Carnegie-Mellon University, CS/RI


Newsgroups: alt.peeves
Subject: Re: Not bad.
Keywords: 
Distribution: alt
References: <13229@boulder.Colorado.EDU>
Organization: Carnegie-Mellon University, CS/RI



In article <626351616.24300@minster.york.ac.uk> alanb@minster.york.ac.uk writes:
>
>There is a new book out called "Real-time Systems and their Programming
>Languages" which people might find interesting.
>Highlights of the book include (according to the back cover anyway!)
>		:
>		:
>  - A detailed comparison and evaluation of the major real-time languages:
>    Ada, Modula-2, and occam 2.
>		:
>		:
>The book is by Alan Burns and Andy Wellings, and it is published by
>Addison Wesley in their International Computer Science Series.
>It is about 600 pages in length and cost 19:95 (UK pounds).


What no C?  I don't care how 'real-time' you think C is, but it is
one of the most common languages for real-time systems ...

~dave
Newsgroups: comp.lang.ada,comp.lang.modula2,comp.sys.transputer,comp.realtime
Subject: Re: New Real-Time Systems Book
Keywords: 
Distribution: 
References: <626351616.24300@minster.york.ac.uk>
Organization: Carnegie-Mellon University, CS/RI

In article <626351616.24300@minster.york.ac.uk> alanb@minster.york.ac.uk writes:
>
>There is a new book out called "Real-time Systems and their Programming
>Languages" which people might find interesting.
>Highlights of the book include (according to the back cover anyway!)
>
>
>  - A detailed comparison and evaluation of the major real-time languages:
>    Ada, Modula-2, and occam 2.
>


What no C?  I don't care how 'real-time' you think C is, but it is
one of the most common languages for real-time systems ...

~dave
Newsgroups: comp.realtime
Subject: Re: Language constructs for interrupt facility
Keywords: 
Distribution: 
References: <29160@shemp.CS.UCLA.EDU> <961@abvax.UUCP> <836@trlluna.trl.oz> <18742@watdragon.waterloo.edu>
Organization: Carnegie-Mellon University, CS/RI

In article <18742@watdragon.waterloo.edu> abrodnik@watdragon.waterloo.edu (Andrej Brodnik (Andy)) writes:
>In article <836@trlluna.trl.oz> aurie@rhea.trl.oz.au.trl.oz (Alistair Urie - Radio and Satellite Networks) writes:
>>>In article <29160@shemp.CS.UCLA.EDU> cshen@maui.cs.ucla.edu
>>>(Chien Chung Shen) writes:
>>>>I am interested in language constructs for interrupt facility.
>>>>Ada has "address clauses" and entry calls. Are there any other
>>>>languages which support interrupt facility and how are they
>>>>implemented? Any direction is appreciated.
>>>>
>>
>>I rather liked the way HP does it in there development systems, a $INTERRUPT
>>pre-complier command in the source sets the following routines as interupts
>>(in effect the routines compile to an RTI rather than RTS return - in 68K )
>
>Modula-2 has IOTRANSFER and the new BSI standard tries to specify it even more
>preceisley. It (Modula-2) assumes that interrupt routine is nothing else but
>another process. So interrupt handling is just a special case of general
>concept of process handling.
>
>Andrej

Newsgroups: comp.unix.wizards
Subject: Re: What new system calls do you want in BSD?
Keywords: 
Distribution: usa
References: <12157@stealth.acf.nyu.edu> <7848@pt.cs.cmu.edu> <2212.21:08:11@stealth.acf.nyu.edu> <131446@sun.Eng.Sun.COM> <MSM1E7xds13@ficc.uu.net>
Organization: Carnegie-Mellon University, CS/RI

In article <MSM1E7xds13@ficc.uu.net> peter@ficc.uu.net (Peter da Silva) writes:
>In article <131446@sun.Eng.Sun.COM> lm@sun.UUCP (Larry McVoy) writes:
>> Bottom line: threads without kernel support are largely useless.
>
>Which is one reason I want *clean* asynchronous I/O, in the form of
>some equivalent of my aread/awrite/await proposal.
>-- 
> _--_|\  Peter da Silva. +1 713 274 5180. <peter@ficc.uu.net>.
>/      \
>\_.--._/ Xenix Support -- it's not just a job, it's an adventure!
>      v  "Have you hugged your wolf today?" `-_-'

----- News saved at 14 Feb 90 18:29:30 GMT
In article <6042@arctic.nprdc.arpa> stanonik@nprdc.navy.mil (Ron Stanonik) writes:
>We ran into a "feature" while porting a program to our 3B2/600G
>running sysV rel 3.2.2 V3: sizeof() returns unsigned.
>
>The code looked like
>
>	struct arf buf[MAX-1];
>	while ((cnt = read(fd, buf, sizeof(buf))) >= sizeof(buf[0])) {
>		do stuff with cnt arfs in buf
>	}
>
>The problem occurs when the read returns -1; 
>since sizeof is unsigned the -1 is coerced into a big positive number.
>

I was not surprosed that sizeof() returned unsigned, but with your post I made
an amazing discovery.  If your code worked previously, I would assume
that 'cnt' was declared as a 'long'.  On the new machine, type "long" is
ignored, and treated as an 'int'.

As an example:

int i;
unsigned u;

	if (i < u) {}

is treated as

	if ((unsigned) i < u) {}

and not

	if (i < (long) u) {}

I would have suspected the last case, where the type long has precedence
over type unsigned.  Back to that
good ol' C reference book and here are the rules, in order:
(According to both K&R and Programming in C, by Stephen G. Kochan),

1. If either operand is of type float, then it is converted to double;
If either operand is of type char or short, it is converted to int;

2. If either operand is double, then all operands converted to double.

3. If either operand is long, then all operands converted to long.

4. If either is unsigned, then all operands converted to unsigned.

5. If none of above conversions performed, then all operands are of type int.


Look closely at number 3.  On all our modern 32-bit systems, long and int
are identical.  Even if you declare something as 'long', it will NOT
have precedence over rule 4.  Thus, throw out rule number 3.  
I have a feeling that for systems where sizeof(unsigned) != sizeof(long)  
rule 3 will still apply.

Followups have been set to comp.lang.c

~dave
-- 
David B. Stewart, Dept. of Elec. & Comp. Engr., and The Robotics Institute, 
	Carnegie Mellon University,  email: stewart@faraday.ece.cmu.edu 
The following software is now available; ask me for details
        CHIMERA II, A Real-time OS for Sensor-Based Control Applications
Newsgroups: u3b.misc,comp.unix.wizards,comp.lang.c
Followup-To: comp.lang.c
Subject: Re: unsigned sizeof()
Keywords: 
Distribution: 
References: <6042@arctic.nprdc.arpa>
Organization: Carnegie-Mellon University, CS/RI

In article <6042@arctic.nprdc.arpa> stanonik@nprdc.navy.mil (Ron Stanonik) writes:
>We ran into a "feature" while porting a program to our 3B2/600G
>running sysV rel 3.2.2 V3: sizeof() returns unsigned.
>
>The code looked like
>
>	struct arf buf[MAX-1];
>	while ((cnt = read(fd, buf, sizeof(buf))) >= sizeof(buf[0])) {
>		do stuff with cnt arfs in buf
>	}
>
>The problem occurs when the read returns -1; 
>since sizeof is unsigned the -1 is coerced into a big positive number.
>

I was not surprosed that sizeof() returned unsigned, but with your post I made
an amazing discovery.  If your code worked previously, I would assume
that 'cnt' was declared as a 'long'.  On the new machine, type "long" is
ignored, and treated as an 'int'.

As an example:

int i;
unsigned u;

	if (i < u) {}

is treated as

	if ((unsigned) i < u) {}

and not

	if (i < (long) u) {}

I would have suspected the last case, where the type long has precedence
over type unsigned.  Back to that
good ol' C reference book and here are the rules, in order:
(According to both K&R and Programming in C, by Stephen G. Kochan),

1. If either operand is of type float, then it is converted to double;
If either operand is of type char or short, it is converted to int;

2. If either operand is double, then all operands converted to double.

3. If either operand is long, then all operands converted to long.

4. If either is unsigned, then all operands converted to unsigned.

5. If none of above conversions performed, then all operands are of type int.


Look closely at number 3.  On all our modern 32-bit systems, long and int
are identical.  Even if you declare something as 'long', it will NOT
have precedence over rule 4.  Thus, throw out rule number 3.  
I have a feeling that for systems where sizeof(unsigned) != sizeof(long)  
rule 3 will still apply.

Followups have been set to comp.lang.c

~dave
-- 
David B. Stewart, Dept. of Elec. & Comp. Engr., and The Robotics Institute, 
	Carnegie Mellon University,  email: stewart@faraday.ece.cmu.edu 
The following software is now available; ask me for details
        CHIMERA II, A Real-time OS for Sensor-Based Control Applications

mdelaney@infmx.UUCP (Mark Delaney) (02/17/90)

In article <12141@smoke.BRL.MIL> gwyn@smoke.BRL.MIL (Doug Gwyn) writes:
>In article <6042@arctic.nprdc.arpa> stanonik@nprdc.navy.mil (Ron Stanonik) writes:
>>Sorry if this is old news.  It was a surprise to us; ie, sizeof
>>on our suns and vax (4bsd) returns signed.
>
>Well, their C compilers were based on old, decrepit versions of PCC.
>And non-portable programs abound, so you really shouldn't be surprised
>that you encountered one.

We too were surprised when this sizeof() caused problems while porting.
Does anyone know of a product (free or purchased) that runs on SunOS that 
could help in finding these little unportable problems?  I checked in the
fall 1989 edition of Catalyst (catalog of third-party products for Suns),
but didn't find anything helpful.  I use lint, but it doesn't catch the 
sizeof() problem.  I would upgrade to ANSI C but we don't have ANSI C 
compilers on all of the machines we port to.  I heard gcc has some good 
warnings build in; has anyone with gcc found that it catches this problem 
when the warning flag is on.

Oh yea, please don't flame me about good programming practices would solve
this problem.  I try to write portable code, but still some bugs get through.

                                              - Mark Delaney