16-bit integer ops on 32-bit processor(PowerPC)

Do you have a question? Post it now! No Registration Necessary

Translate This Thread From English to

Threaded View
I'm wondering about the assembly generated by my compiler for a 32-bit
PowerPC processor. I have some code(in C) that deals with 16 bit
unsigned integer types(unsigned short int on my compiler) and I have
some questions about the assembly that is generated for some of the
code.

If I have a function such as the following:

unsigned short int foo(unsigned short int x, unsigned short int y)
{
  return x >> y;
}

I compile this without optimizations and I get assembly such as the
following(x is passed in r31, y in r30):

rlwinm r12, r31, 0, 16, 31
srw r29, r12, r30

What I want to understand is why 'x' is effectively cast to an unsigned
short int but 'y' is not. Is this because the ANSI C standard states
that shifting a 16-bit value by more than 15 results in undefined
behavior?

I am basically trying to get a grasp of the overhead involved with
dealing with 16-bit integers on a 32-bit machine. BTW, I tried posting
this to comp.compilers but apparently it might take a few days for the
moderator to accept my message so I posted here due to urgency.

Thanks!


Re: 16-bit integer ops on 32-bit processor(PowerPC)

[...]
Quoted text here. Click to load it

It may not be the actual reason (nobody outside your compiler vendor's
shop may actually ever get to know that one), but at the very least,
it's a perfectly valid possible reason.  There's no way any legal
value of y could be large enough to make a cast from 32-bit to 16-bit
integer have any effect.

For the rest, you'll have to consult ABI documentation to learn how
16-bit are supposed to passed to functions, on that platform.  Pay
special attention to the question of whether a 16-bit value passed to
a function in a 32-bit register is supposed to be "masked clean" or
not, and if so, by whom: the caller or the called function.

--
Hans-Bernhard Broeker ( snipped-for-privacy@physik.rwth-aachen.de)
Even if all the snow were burnt, ashes would remain.

Re: 16-bit integer ops on 32-bit processor(PowerPC)
Hans, thanks for the reply. I'll check the documentation for EABI.
Let's suppose that the callee is supposed to do the cleaning of the
most significant 16 bits. This cleaning is happening to achieve typing,
correct? I mean to say it is so if you pass for example a 32-bit
integer in as an argument to a function that takes a 16-bit integer as
a parameter, the 32-bit integer according to the C standard gets cast
to a 16-bit integer and loses its most significant 16 bits.

Thanks.


Re: 16-bit integer ops on 32-bit processor(PowerPC)
Quoted text here. Click to load it

You could put it that way.  The language dictates that the code must
behave *as if* the extra upper 16 bits weren't there at all --- but
only to the extent that a correct C program can ever notice the
difference.  Once the user's source code has trespassed into
"undefined behaviour" country, the implementation can do whatever it
pleases.

It's up to the implementor to decide when and how to achieve the "as
if" result.  The ABI is one of the documents that document or
structure such decisions.

--
Hans-Bernhard Broeker ( snipped-for-privacy@physik.rwth-aachen.de)
Even if all the snow were burnt, ashes would remain.

Re: 16-bit integer ops on 32-bit processor(PowerPC)
Quoted text here. Click to load it

No, if the value doesn't fit you have an undefined behavior
condition.  So you simply document the range of argument the callee
will accept.  Unfortunately, with C lacking sub-ranges and range
checking, you can't enforce this automatically.

--
"If you want to post a followup via groups.google.com, don't use
 the broken "Reply" link at the bottom of the article.  Click on
We've slightly trimmed the long signature. Click to see the full one.
Re: 16-bit integer ops on 32-bit processor(PowerPC)
Quoted text here. Click to load it
unsigned

There are two things about C that are often overlooked in cases like
this. First, according to C standards since K&R, shorts are ordinarily
promoted to ints for arithmetic. This can be optimised into narrower
operations by a compiler but only if the same result can be guaranteed
(as if the operation were evaluated on promoted ints).

Second: unlike other operators, shift amounts (RHS of << >>) are not
really "typed" in the same sense as, for instance, arithmetic operands.
The bit count, shift amount, whatever you call it, is entirely
abstract. For this reason the concept of "promoting" y doesn't have any
real meaning here - despite the blanket implication of the rules.
Semantically the meaning of y is independent of its integral type; so
the specified type of y cannot influence the generated code (unless
there is a compiler bug).

--Toby


Site Timeline