On 19.10.2015 11:01, Mark Wielaard wrote:
> On Mon, 2015-10-19 at 03:50 +0300, Alexander Cherepanov wrote:
>> On 2015-06-24 11:14, Mark Wielaard wrote:
>>> But in this case as far as I know these kind of malloc argument checks
>>> are indeed just noise. We do check the results of malloc everywhere
>>> (or should at least). I might be wrong of course, or miss something
>>> subtle. So please do let me know if you think it is something to fix
>>> differently from how we handle it currently.
>>
>> gcc doesn't support objects more than half the address space in size --
>> https://gcc.gnu.org/bugzilla/show_bug.cgi?id=67999 . So if you are
>> malloc'ing >2GB on 32-bit platforms you should be concerned.
>
> Urgh. So malloc might return a memory object larger than PTRDIFF_MAX?

Yup.

> I had indeed assumed something like that couldn't happen. It makes the
> size calculations and/or indexing into such a memory object afterwards a
> little tricky I believe.

True.

> Since pointer + something > PTRDIFF_MAX seems
> not well defined. hmmmm.

pointer + something doesn't have any such limits. It just have to point into the (same) object. That is, according to the C standards. It turned out it's not well-defined in gcc and clang for something > PTRDIFF_MAX (it doesn't matter if pointer + something > PTRDIFF_MAX). And it's not clear what works and what doesn't work. E.g. this:

  for (size_t i = 0; i < len; i++)
    buf[i] = 'A';

seems to work but this:

  char *end = buf + len;
  for (char *p = buf; p < end; p++)
    *p = 'B';

doesn't work. And those things which work now are not guaranteed to work in the future due to changes in optimization etc.

And things like pointer - pointer > PTRDIFF_MAX are not defined at all. They are UB in the C standards.

> I think it makes sense to raise this as a bug against glibc.

You are subscribed to the gcc bug, so you can see the full picture there:-)

> And we probably do have to audit all such suspicious mallocs to make
> sure we aren't actually doing any pointer calculations using the size
> (or just reject any allocation > PTRDIFF_MAX).

If you are not in a position that you _definitely_ need allocations > PTRDIFF_MAX, I guess the easiest solution is to reject them in a wrappers around malloc, mmap, etc. Until the compilers are fixed, for broken versions of compiler, or forever for all compilers. You are saying that you already assumed that it works that way so you are not loosing anything:-)

If you want allocations > PTRDIFF_MAX then you have to fix all cases of pointer - pointer > PTRDIFF_MAX. It affects only arrays of chars, for types with sizeof > 1 it's ok already.

If you want, in addition, to support broken compilers (this includes all(?) existing versions of gcc and clang) you have to check everything touching pointer arithmetic for miscompilations.

--
Alexander Cherepanov

Reply via email to