https://gcc.gnu.org/bugzilla/show_bug.cgi?id=125405

--- Comment #5 from Drea Pinski <pinskia at gcc dot gnu.org> ---
(In reply to Drea Pinski from comment #4)
> (In reply to Drea Pinski from comment #3)
> > (In reply to Milan Tripkovic from comment #1)
> > > With the following  patterns:
> > > 
> > > (simplify
> > >  (minus (bit_and @0 INTEGER_CST@1) (bit_and @0 INTEGER_CST@2))
> > >  (if (INTEGRAL_TYPE_P (type)
> > >       && TYPE_PRECISION (type) > 8
> > >       && wi::to_wide (@1) == 127
> > >       && wi::to_wide (@2) == 128)
> > >   (convert (convert:signed_char_type_node @0))))
> > > (simplify
> > >  (minus (bit_and @0 INTEGER_CST@1) (bit_and @0 INTEGER_CST@2))
> > >  (if (INTEGRAL_TYPE_P (type)
> > >       && TYPE_PRECISION (type) > 16
> > >       && wi::to_wide (@1) == 32767
> > >       && wi::to_wide (@2) == 32768)
> > >   (convert (convert:intHI_type_node @0))))
> > 
> > I wonder if we could do this better and more generic.
> > Maybe something like:
> > (simplify
> >  (minus (bit_and @0 INTEGER_CST@1) (bit_and @0 integer_pow2p@2))
> >  (if (wi::to_wide (@1) + 1 == wi::to_wide (@2))
> >   (with { tree ntype = build_nonstandard_integer_type (wi::exact_log2
> > (wi::to_wide (@2)), SIGNED); }
> >    (convert (convert:ntype @0)))
> 
> `wi::exact_log2 (wi::to_wide (@2))` needs to have `+1` added to it; I think.
> That is 32768 is 1<<15 but we want 16 here.
> 
> I had an off by one error :).

With this, you might want to add `TYPE_PRECISION (type) <= MAX_FIXED_MODE_SIZE`
for the bitint case.


>Essentially you can have types that aren't 2^n bits wide.  
I think those would be ok here as long as <= MAX_FIXED_MODE_SIZE. But if not
then you should use `type_has_mode_precision_p (ntype)` to make sure it is only
used with types that have the same precision as the mode (which are power of 2
bits wide; except for PSImode which might show up; e.g. AVR has 24bit PSImode
which can handle the sign extending better than say the subtraction/and trick).

Reply via email to