On Fri, Dec 16, 2016 at 07:29:13PM +0100, Markus Trippelsdorf wrote:
> So, to be fair a gave Jakub's patch a try and it has exactly the same
> issues for the Linux kernel: sometimes the warning only triggers with
> -O3, e.g.:
> 
>  % cat sm_ftl.i
> int a;
> void mtd_read_oob(int);
> void sm_read_sector(int *buffer) {
>   __builtin_memset(buffer, 0, 1);
>   mtd_read_oob(a);
> }
> void sm_get_zone() { sm_read_sector(0); }

In this case I think the warning is right, if you ever call sm_get_zone,
it will always invoke UB.

>  % gcc -c -Wnonnull -O2 sm_ftl.i
>  % gcc -c -Wnonnull -O3 sm_ftl.i
> sm_ftl.i: In function ‘sm_get_zone’:
> sm_ftl.i:4:3: warning: argument 1 null where non-null expected [-Wnonnull]
>    __builtin_memset(buffer, 0, 1);
>    ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
> sm_ftl.i:4:3: note: in a call to built-in function ‘__builtin_memset’
> 
> Also, Jakub's patch doesn't catch the following case:
> 
> (tools/perf/util/trace-event-info.c from Linux)
> //...
>         dir = opendir(path);
>         if (!dir) {
>                 err = -errno;
>                 pr_debug("can't read directory '%s'", path);
>                 goto out;
>         }
> //... other stuff
> out:
>         closedir(dir);
> 
> Whereas Martin's does.

This is where you rely on jump threading to duplicate closedir,
otherwise you don't warn.  If you don't jump thread it (say there are
a few more statements after closedir that make it not worth it), then you
don't warn even late.  If the warning in calls.c is guarded with
-Wmaybe-nonnull instead of -Wnonnull, not included in -Wall, I have no
objections.  Then users can select the amount of warnings and false
positives.  Or -Wnonnull can have 3 levels, one warn in the FE only,
then after inlining in the second level and late in the 3rd level.

        Jakub

Reply via email to