This is the mail archive of the gcc@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: locating unsigned type for non-standard precision


Richard Guenther wrote:

>> I've run into another issue supporting a 20-bit integer for which I'd
>> appreciate a hint.  With this code:
>>
>>   typedef long int __attribute__((__a20__)) int20_t;
>>   int20_t xi;
>>   int20_t addit () { xi += 0x54321L; }
>>
>> xi ends up in mode PSImode, which is a MODE_PARTIAL_INT with 20 bits of
>> precision and 32-bit width.
>>
>> convert() notices that, because the constant in the add expression is
>> SImode, there's an SImode add being truncated to a PSImode result, and
>> pushes the truncation down into the operands.
>>
>> The problem is this ends up in convert_to_integer, which detects that the
>> signed operation might overflow so calls unsigned_type_for() to get the
>> unsigned variant.
>>
>> Unfortunately, this ends up in c_common_type_for_size(), which knows nothing
>> about PSImode, and returns an unsigned type with 32 bits of precision when
>> asked for one with 20 bits of precision.
> 
> That's expected - this function returns a type that is suitable for holding all
> values, not a type that has necessarily matching precision.  If the caller
> wants such type it needs to verify what the function returned.  Which seems
> to me to be the correct fix for this (premature) optimization in
> convert_to_integer.
> 
> Richard.
> 
>>   The expression is rewritten with
>> the 32-bit constant integer recast to the 32-bit unsigned type (instead
>> of the 20-bit one it might have used), and infinite recursion results.

This is already filed as

http://gcc.gnu.org/PR51527

It works with 4.8 trunk but crashes with 4.7.
Did not yet track what changes made it work with 4.8, though.
Unfortunately, noone remembers :-(

http://gcc.gnu.org/ml/gcc/2012-03/msg00440.html

Johann

>> Is it proper for c_common_type_for_size() to know about partial int modes
>> and return the best one available?  Is there a hook that would allow me to
>> do this customized in my back-end?  Or is there another way to get
>> unsigned_type_for() to return the "right" type for an unusual integer
>> precision?
>>
>> Thanks.
>>
>> Peter


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]