Adding LoopEntrance as a new CFGElement to the CFG.
This element is added as the last element of the CFGBlock just before the loop condition block.
This can help the Static Analyzer to have a more precise loop modeling.
Details
Diff Detail
Event Timeline
include/clang/Analysis/CFG.h | ||
---|---|---|
199 | This comment refers to the CFGLoopExit class. Please add a separate explaining comment to the CFGLoopEntrance. |
Because it wasn't immediately obvious to me how to apply both this patch and D39398 (there are a couple of minor conflicts between them), i wanted to post a few pictures for the reference, because debug.ViewCFG graphs are much easier to comprehend than text dumps.
For example, here's the new CFG for check_return() in loopexit-cfg-output.cpp:
833 int check_return() { 834 for (int i = 0; i < 10; i++) { 835 int j = 1; 836 while (j < 12) { 837 if (j % 2) 838 return 0; 839 } 840 } 841 return 1; 842 }
I essentially have one question at a glance - for loop counter variables, don't we want LoopEntrance be before the initialization? I.e. on this picture wouldn't it be better to have
[B10] 1: ForStmt (LoopEntrance) 2: 0 3: int i = 0;
?
Because otherwise our future LoopContext wouldn't correspond to any variable's lifetime scope, so it'd be kind of useless as a ScopeContext. Because, as far as i understand, there are two scopes in every loop:
- The scope of the whole loop which includes the counter,
- The scope of every iteration, which goes out of scope after the iteration ends.
And currently LoopContext is none of these. Would loop unrolling still work in a sensible manner if we move LoopEntrance to the beginning of the block?
I essentially have one question at a glance - for loop counter variables, don't we want LoopEntrance be before the initialization?
I guess this would just make too much sense. Done that.
Additionally, handle the cases when we just hop to the body of the loop via goto stmt.
Now the patches can be applied without any conflict (added the loopexit patch as a dependency).
I would prefer a more detailed CFG element with more meta-information about nested loop, but this is a good starting point.
Also loops created with gotos should also be supported (e.g. by finding backedges), but that could be done in a different patch.
This comment refers to the CFGLoopExit class. Please add a separate explaining comment to the CFGLoopEntrance.