elee24@castle.ed.ac.uk (H Bruce) (10/04/90)
How should the following code fragment compile ? unsigned char x,y; unsigned short int z; z=x*y; According to the ANSI standard, if the result of x*y exceeds 255, will all 16 bits be copied to z or only the lower 8 ? (i.e if x=2 and y=200 does z=400 or 400%256 ?) I have a C compiler for the 8051 which does not copy the upper byte across even if z=x*y is replaced with z=(unsigned short int)x*y. I want to confirm that this is a bug. Microsoft C does convert the result into 16 bits without a type cast. I can't find reference to this in any "ANSI" C books that we have. Thanks, Henry Bruce.
jh4o+@andrew.cmu.edu (Jeffrey T. Hutzelman) (10/05/90)
The ANSI standard does not guarantee the sizes of unsigned char and
unsigned short int; only that sizeof(char)<=sizeof(short). If you
want to be sure it works, try z=(unsigned short)x * (unsigned short)y
(you may need parens; I'm not familiar with the precedence rules
regarding type casting, but I think it is higher that multiply).
-----------------
Jeffrey Hutzelman
America Online: JeffreyH11
Internet/BITNET:jh4o+@andrew.cmu.edu, jhutz@drycas.club.cc.cmu.edu
>> Apple // Forever!!! <<
henry@zoo.toronto.edu (Henry Spencer) (10/06/90)
In article <6584@castle.ed.ac.uk> elee24@castle.ed.ac.uk (H Bruce) writes: >How should the following code fragment compile ? > >unsigned char x,y; >unsigned short int z; >z=x*y; > >According to the ANSI standard, if the result of x*y exceeds 255, >will all 16 bits be copied to z or only the lower 8 ? >(i.e if x=2 and y=200 does z=400 or 400%256 ?) > >I have a C compiler for the 8051 which does not copy the upper byte across >even if z=x*y is replaced with z=(unsigned short int)x*y. The first question you should ask is "how big is `unsigned short' on the 8051?". If it's 8 bits, then your question is answered. This would not be an ANSI-standard implementation, since ANSI C requires >=16 bits for shorts of all kinds, but there are lots of non-ANSI and semi-ANSI compilers out there, especially for cruddy little 8-bit machines that have trouble supporting 16-bit and 32-bit arithmetic efficiently. Assuming that `unsigned short' is indeed 16 bits, your compiler is exceeding its authority here. `unsigned char' turns into some sort of `int' (details slightly implementation-dependent) immediately on use in an expression, so the value of that multiplication is definitely at least 16 bits, and should be copied as such. A compiler can shorten such operations only if it can guarantee that this will not affect results... not true in this case. -- Imagine life with OS/360 the standard | Henry Spencer at U of Toronto Zoology operating system. Now think about X. | henry@zoo.toronto.edu utzoo!henry