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: Integer overflow in operator new


On Monday, 9 April 2007 10:23, Florian Weimer wrote:
> * Ross Ridge:
> > Florian Weimer writes:
> >>I don't think this check is correct.  Consider num = 0x33333334 and
> >>size = 6.  It seems that the check is difficult to perform
> >> efficiently unless the architecture provides unsigned
> >> multiplication with overflow detection, or an instruction to
> >> implement __builtin_clz.
> >
> > This should work instead:
> >
> > 	inline size_t __compute_size(size_t num, size_t size) {
> > 		if (num > ~size_t(0) / size)
> > 			return ~size_t(0);
> > 		return num * size;
> > 	}
>
> Yeah, but that division is fairly expensive if it can't be performed
> at compile time.  OTOH, if __compute_size is inlined in all places,
> code size does increase somewhat.

You could avoid the division in nearly all cases by checking for 
reasonably-sized arguments first:

    inline size_t __compute_size(size_t num, size_t size) {
        static const int max_bits = sizeof(size_t) * CHAR_BITS;
        int low_num, low_size;
        low_num = num < ((size_t)1 << (max_bits * 5 / 8));
        low_size = size < ((size_t)1 << (max_bits * 3 / 8));
        if (__builtin_expect(low_num && low_size, 1)
                || num <= ~(size_t)0 / size)
            return num * size;
        else
            return ~size_t(0);
    }


-- 
Ross Smith ........ r-smith@ihug.co.nz ........ Auckland, New Zealand
           "Those who can make you believe absurdities can
           make you commit atrocities."        -- Voltaire


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