https://sourceware.org/bugzilla/show_bug.cgi?id=3298

--- Comment #20 from Joern Rennecke <amylaar at gcc dot gnu.org> ---
(In reply to Quentin Boswank from comment #17)
> Created attachment 16107 [details]
> patch for gas bug zeroing 16 or 32 bit width jumptables when relaxing V2

       max = (1ul << (fixP->fx_size * 8)) - 1;

There are many ways to avoid shifting by a shiftcount as large or larger than
type bing shifted.  This is not one of them.

There are mostly three categories:

1) Make sure the shifted type is wide enough.  This depends on the type
existing,
   which, for 64 bit, might be a problem with older compilers / include file
sets
   (pre-C99 / C++11), and also with a few ports where providing a 64 integer is
not
   feasible; however, this should generally not be a problem for a contemporary
   binutils host.
1a) You could use a (unsigned) long long literal, like 1LL or 1ULL .
1b) You could use the difference of two literals that imply a sufficiently
large type
    due to the size of the literals, e.g. (0xdeadbeef1 - 0xdeadbeef0)
1c) You can cast to long long or unsigned long long by naming the type, e.g.
(long long)1 .
1d) You can make sure the <stdint.h> header is included and use one of the
sufficiently
    wide types defined there.

2) Split the shift into multiple shifts of smaller shift counts so that a more
readily
   available / cheaper type can be used.
2a) Split into rounded down & rounded up halves to make do with half the type
width,
    e.g.  (1UL << (fixP->fx_size * 4)) << (fixP->fx_size * 4) .
2b) Where a shift count value (range) is know, use this to cheaper split.
   (fixP->fx_size * 8) is in the range [8..32] , so you can subtract one to get
   it into the range [7..31].  Then you can do the left shift of the literal by
1 first
   to get a modified literal: (2UL << (fixP->fx_size * 8 - 1)
2c) A combination and/or replication of the above strategies to bridge a wider
    difference between type width and shift count.

3) Avoid the shift altogether by using an alternate computation, e.g. a table
lookup.

There is also the further problem that the 'long' type of max is not known to
be
wide enough to accommodate the value 0xffffffff .  You can use unsigned long
for that, but then you can't do a defined conversion to a signed type without
widening first.  And the comparison to val makes no sense when that is 32 bit,
either.

-- 
You are receiving this mail because:
You are on the CC list for the bug.

Reply via email to