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

--- Comment #7 from Dr. David Alan Gilbert <dgilbert at redhat dot com> ---
(In reply to Martin Sebor from comment #6)
> The reduced test case from comment #4 doesn't trigger a warning because in
> it the value of n is unknown.  The original test case does trigger it
> because in it n's range is known.  This is evident from the VRP dump which
> shows:
> 
> Value ranges after VRP:
> 
> __n_5: ~[1, 18446744071562067967]
> ...
> test_acpi_piix4_tcg ()
> {
>   ...
>   g_assertion_message_cmpnum (0B, "bug2.c", 59, &__func__, "tables_nr > 0",
> _71, ">", 0.0, 105);
>   __n_5 = (gsize) tables_nr_69;
>   __p_58 = g_malloc0_n (__n_5, 4);
> 
> 
> The anti-range implies that the variable's value is either zero or greater
> than 18446744071562067967 (0xffffffff7fffffff) so the allocation request is
> either for zero bytes or some positive multiple of the excessive size. 
> Since zero is not considered a valid size (unless it's constant) and
> 18446744071562067967 is too big the warning triggers.
> 
> The inlining context of the call is shown in the full output of the warning.
> It might help shed light on where the range comes from.
> 
> In function ‘test_acpi_rsdt_table’,
>     inlined from ‘test_acpi_one.constprop’ at pr80346-2.c:19334:5,
>     inlined from ‘test_acpi_piix4_tcg’ at pr80346-2.c:19346:5:
> pr80346-2.c:19319:59: warning: argument 1 range [18446744071562067968,
> 18446744073709551615] exceeds maximum object size 9223372036854775807
> [-Walloc-size-larger-than=]
>              / __s)) __p = g_malloc0 (__n * __s); else __p = g_malloc0_n
> (__n, __s); __p; }));
>                                                       
> ~~~~^~~~~~~~~~~~~~~~~~~~~~~~

The original code is here:
http://git.qemu-project.org/?p=qemu.git;a=blob;f=tests/bios-tables-test.c;h=88dbf9785353d6ac82a7000357d4bd4c658319e7;hb=HEAD#l96

(I had boiled it down a bit for this)
but what confuses me is we start if with 'tables_nr' which is an int
This is x86 - so it's 32bit
we then do an assert to guarantee it's positive
    -> So the possible range is now 0..0x7fffffff
Then I expect it gets multiplied by sizeof(uint32_t)
    -> Range is now 0..0x1ffffffc

the range gcc's warning us about looks like it sign extended a -ve 32bit
integer - but our assert makes sure that can't happen.

Reply via email to