[cfe-dev] [analyzer] Speaking about reaching definitions...

Phil King via cfe-dev cfe-dev at lists.llvm.org
Thu Jun 27 15:13:47 PDT 2019


Would it make sense to allow this sort of behaviour to be configurable?

For example, much of the time I might not want to be nagged with “this may be a problem” and would like a pragmatic approach, but if I’m writing some critical code I would like to know “this cannot be proven to be correct” and would like the check to be pessimistic.

These different use-cases can also be adopted when checking legacy code (pragmatic) or new code (pessimistic).

For the pessimistic case, there is still the chance to use information about bar() to drop the warning if it can be shown never to yield a null pointer.

Sent from my iPhone

> On 27 Jun 2019, at 22:55, Artem Dergachev via cfe-dev <cfe-dev at lists.llvm.org> wrote:
> 
> Yeah, i mean, we cannot be sure, therefore we want to be conservative and not bother the user with a warning. It might be a true positive, but it's very wonky and there's nothing in the code that indicates that bar() may return null; the code makes perfect sense even if bar() doesn't ever return null.
> 
>> On 6/27/19 2:49 PM, Gábor Horváth wrote:
>> I am not sure I follow why do we think that the second example is a false positive. 
>> I think it depends on the user intent. If the user wanted to check if b was reassigned (i.e. checking for the source of the value), and bar never returns a null pointer than it is definitely a false positive. But we cannot be sure what the intent of the check was. What if the user just wanted to check the value regardless of its source. 
>> 
>>> On Thu, 27 Jun 2019 at 13:56, Artem Dergachev <noqnoqneo at gmail.com> wrote:
>>> This is very loosely related to Kristof's GSoC and this is my favorite 
>>> subject: weird assumption chains.
>>> 
>>> Consider:
>>> 
>>>    void foo1() {
>>>      int *a = bar();
>>>      int *b = a;
>>>      if (b) { /* ... */ }
>>>      *a = 1;
>>>    }
>>> 
>>> This is a valid null dereference bug. Like, 'b' is probably null 
>>> (otherwise why check?), therefore 'a', which is equal to 'b', may also 
>>> be null.
>>> 
>>> Now consider:
>>> 
>>>    void foo2() {
>>>      int *a = bar();
>>>      int *b = nullptr;
>>>      if (coin()) {
>>>        b = a;
>>>      }
>>>      if (b) { /* ... */ }
>>>      *a = 1;
>>>    }
>>> 
>>> In foo2 we will report a null dereference as well, however the null 
>>> check for 'b' is well-justified even if bar() never returns null, 
>>> therefore it's a false positive.
>>> 
>>> How 'bout we suppress the null dereference warning when the 
>>> reaching-definition analysis for 'b' that starts at 'if (b)' - i.e. at 
>>> the collapse point - yields multiple definitions and some of them is a 
>>> plain null?
>>> 
>>> Note that the plain-null definition would never be a part of the bug 
>>> path because it would not have a corresponding collapse point (it's 
>>> already a concrete null).
> 
> _______________________________________________
> cfe-dev mailing list
> cfe-dev at lists.llvm.org
> https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-dev
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-dev/attachments/20190627/1aa85b2d/attachment.html>


More information about the cfe-dev mailing list