[cfe-dev] [RFC] Introduce overflow builtins
Xi Wang
xi.wang at gmail.com
Sat Mar 31 13:02:09 PDT 2012
On Mar 30, 2012, at 4:32 PM, Dave Zarzycki wrote:
> Have you tried inferring the sign of T* in addition to the size of T* in the API? That would let you simplify this:
>
> __builtin_sadd_with_overflow()
> __builtin_uadd_with_overflow()
> __builtin_ssub_with_overflow()
> __builtin_usub_with_overflow()
> __builtin_smul_with_overflow()
> __builtin_umul_with_overflow()
>
> To this:
>
> __builtin_add_with_overflow()
> __builtin_sub_with_overflow()
> __builtin_mul_with_overflow()
Sounds like a good idea. I am just a little worried that this is more error-prone than explicitly specifying s/u (e.g., if the programmer accidentally mixes signed and unsigned integers). -Wconversion would help (see below), but I guess the option is turned off in general.
> Also, have you verified that -Wconversion does the right thing and warns when the sign of the parameters are inconsistent with each other (or the API if you do not make the above simplification)?
I tried a few examples and -Wconversion seemed to work. Below is an example.
#include <stdlib.h>
void *malloc_array_1(int n, size_t size)
{
size_t bytes;
if (__builtin_umul_with_overflow(&bytes, n, size))
return 0;
return malloc(bytes);
}
void *malloc_array_2(size_t n, size_t size)
{
int bytes;
if (__builtin_umul_with_overflow(&bytes, n, size))
return 0;
return malloc(bytes);
}
$ clang -c -Wconversion m.c
m.c:6:43: warning: implicit conversion changes signedness: 'int' to 'size_t' (aka 'unsigned long') [-Wsign-conversion]
if (__builtin_umul_with_overflow(&bytes, n, size))
~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ^
m.c:16:16: warning: implicit conversion changes signedness: 'int' to 'size_t' (aka 'unsigned long') [-Wsign-conversion]
return malloc(bytes);
~~~~~~ ^~~~~
m.c:14:43: warning: implicit conversion loses integer precision: 'size_t' (aka 'unsigned long') to 'int'
[-Wshorten-64-to-32]
if (__builtin_umul_with_overflow(&bytes, n, size))
~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ^
m.c:14:46: warning: implicit conversion loses integer precision: 'size_t' (aka 'unsigned long') to 'int'
[-Wshorten-64-to-32]
if (__builtin_umul_with_overflow(&bytes, n, size))
~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ^~~~
4 warnings generated.
- xi
More information about the cfe-dev
mailing list