Commit Graph

712 Commits

Author SHA1 Message Date
alexet
d61022ffcc C++: Improve optimiser performance 2018-12-17 16:11:23 +00:00
Jonas Jensen
1a0a8c931f C++: Fix name clash in data flow imports
The AST-based data flow libraries and the IR-based ones both define
modules `DataFlow`, `DataFlow2`, etc. This caused
`ImportAdditionalLibraries.ql` to fail in compilation.
2018-12-13 09:53:20 +00:00
Dave Bartolomeo
be5ac2f2ff Merge pull request #648 from dave-bartolomeo/dave/UnreachableIR
C++: Remove unreachable IR
2018-12-11 20:58:49 -08:00
Dave Bartolomeo
0140cd23d0 C++: Accept correct test output 2018-12-11 17:11:51 -08:00
Dave Bartolomeo
283c1d43c3 C++: Restore previous test expectations 2018-12-11 17:07:25 -08:00
Robert Marsh
59c0e5d39e C++: update test expectations 2018-12-11 15:07:09 -08:00
Aditya Sharad
ce905e7a0a Merge pull request #597 from dave-bartolomeo/dave/IRDataflow
C++: Initial IR-based dataflow implementation
2018-12-11 15:05:58 +00:00
Dave Bartolomeo
8a73bea72f C++: Avoid bad join ordering in getOperandMemoryAccess 2018-12-11 00:47:53 -08:00
Dave Bartolomeo
4170d4fadd C++: Handle relational operators in constant analysis 2018-12-10 23:03:02 -08:00
Dave Bartolomeo
5ba51e32f0 C++: Remove aliased_ssa instantiation of IR reachability
We never actually consumed this iteration, since SSA construction only depends on the reachability instantiation of the previous IR layer.
2018-12-10 21:22:55 -08:00
Dave Bartolomeo
a81ba84c0e C++: Update test expectations after unreachable IR removal 2018-12-10 21:22:55 -08:00
Dave Bartolomeo
b2e596fcc2 C++: Improve join order in IR reachability 2018-12-10 21:22:55 -08:00
Dave Bartolomeo
99d33f9623 C++: Remove unreachable IR
This change removes any IR instructions that can be statically proven unreachable. To detect unreachable IR, we first run a simple constant value analysis on the IR. Then, any `ConditionalBranch` with a constant condition has the appropriate edge marked as "infeasible". We define a class `ReachableBlock` as any `IRBlock` with a path from the entry block of the function. SSA construction has been modified to operate only on `ReachableBlock` and `ReachableInstruction`, which ensures that only reachable IR gets translated into SSA form. For any infeasible edge where its predecessor block is reachable, we replace the original target of the branch with an `Unreached` instruction, which lets us preserve the invariant that all `ConditionalBranch` instructions have both a true and a false edge, and allows guard inference to still work.

The changes to `SSAConstruction.qll` are not as scary as they look. They are almost entirely a mechanical replacement of `OldIR::IRBlock` with `OldBlock`, which is just an alias for `ReachableBlock`.

Note that the `constant_func.ql` test can determine that the two new test functions always return 0.

Removing unreachable code helps get rid of some common FPs in IR-based dataflow analysis, especially for constructs like `while(true)`.
2018-12-10 21:22:55 -08:00
Dave Bartolomeo
59fc77f066 C++: Simple constant analysis
This change moves the simple constant analysis that was used by the const_func test into a pyrameterized module for use on any stage of the IR. This will be used to detect unreachable code.
2018-12-10 21:22:54 -08:00
Dave Bartolomeo
6a11ef5c18 C++: Add a couple test cases for unreachable code in IR 2018-12-10 21:22:54 -08:00
Dave Bartolomeo
78e5b3ad63 C++: Add IR dataflow to ImportAdditionalQueries.ql 2018-12-10 15:09:49 -08:00
Dave Bartolomeo
23993710d1 Revert "C++: Avoid creating ExprNodes for Conversions"
This reverts commit df882a9e72.
2018-12-10 15:06:29 -08:00
Dave Bartolomeo
df882a9e72 C++: Avoid creating ExprNodes for Conversions 2018-12-10 10:09:42 -08:00
Jonas Jensen
00e52df371 C++: Rename "Incorrect 'not' operator usage"
This makes the casing consistent with our other queries.
2018-12-07 09:24:35 +01:00
Dave Bartolomeo
ebbd701188 C++: Fix PR feedback 2018-12-06 12:35:43 -08:00
Dave Bartolomeo
84b39bf999 C++: Simplify models for side effects and alias info. 2018-12-06 12:35:33 -08:00
Dave Bartolomeo
2b80aee557 C++: Use getConvertedResultExpr in IR-based dataflow
This sort of fixes one FP and causes a new FN, but for the wrong reasons. The IR dataflow is tracking the reference itself, rather than the referred-to object. Once we can better model indirections, we can make this work correctly.

This change is still the right thing to do, because it ensures that the dataflow is looking at actual expression being computed by the instruction.
2018-12-05 12:34:44 -08:00
Dave Bartolomeo
e8efb32156 C++: Remove StoreDestinationAsPostUpdateNode 2018-12-05 11:33:48 -08:00
Dave Bartolomeo
65360b23f9 C++: Change model API based on feedback
I've separated the model interface for memory side effects from the model for escaped addresses. It will be fairly common for a given model to extend both interfaces, but they are used for two different purposes.

I've also put each model interface and the non-member predicates that query it into a named module, which seemed cleaner than having predicates named `functionModelReadsMemory()` and `getFunctionModelParameterAliasBehavior()`.
2018-12-05 10:58:46 -08:00
Dave Bartolomeo
e11b4b6c40 C++: Fix IR Dataflow PR feedback 2018-12-04 07:31:13 -08:00
Geoffrey White
a7f45bb59d Merge pull request #608 from jbj/assignment-this-templates
C++: Fix "Overloaded assignment does not return 'this'" for templates
2018-12-04 14:12:56 +00:00
Jonas Jensen
6239455a91 C++: Remove extra type check in AV Rule 82
These type checks were overlapping with `assignOperatorWithWrongType` is
are no longer needed now that `assignOperatorWithWrongType` is improved.
They were causing FPs and misleading error messages on uninstantiated
templates.
2018-12-04 12:59:21 +01:00
Jonas Jensen
8ac427c387 C++: Add missing getUnspecifiedType in AV Rule 82
Adding this call to `getUnspecifiedType` makes the error message better
in the presence of typedefs and qualifiers on an assignment operator
return type. It's also needed to avoid losing valid results in the
commit that comes after this.
2018-12-04 11:13:11 +01:00
Jonas Jensen
a78ded7551 C++: Demonstrate FP in AV Rule 82
The added test is a reduced version of a FP observed in the wild.
2018-12-04 11:09:35 +01:00
Geoffrey White
436ee553a6 Merge pull request #589 from jbj/1.19-change-notes
C++: add missing 1.19 change notes
2018-12-03 15:56:18 +00:00
Dave Bartolomeo
2822d14588 C++: Add missing changes to test_ir.expected 2018-12-02 22:22:34 -08:00
Jonas Jensen
d14cf34cc6 C++: data flow AlwaysTrueUponEntryLoop perf fix
The predicate `AlwaysTrueUponEntryLoop.getARelevantVariable` was very
sensitive to join ordering, and with the 1.19 QL engine it got an
unfortunate join order that made it explode on certain snapshots. With
this change, it goes from taking minutes to taking less than a second on
a libretro-uae snapshot.
2018-12-01 10:07:08 +01:00
Dave Bartolomeo
7eb47f3f82 C++: A few more IR dataflow tweaks
Made `Node::getType()`, `Node::asParameter()`, and `Node::asUninitialized()` operate directly on the IR. This actually fixed several diffs compared to the AST dataflow, because `getType()` wasn't holding for nodes that weren't `Exprs`.

Made `Uninitialized` a `VariableInstruction`. This makes it consistent with `InitializeParameter`.
2018-11-30 16:53:45 -08:00
Dave Bartolomeo
309b703e47 C++: Models for side-effect-free functions
This commit adds a new model interface that describes the known side effects (or lack thereof) of a library function. Does it read memory, does it write memory, and do any of its parameters escape? Initially, we have models for just two Standard Library functions: `std::move` and `std::forward`, which neither read nor write memory, and do not escape their parameter.

IR construction has been updated to insert the correct side effect instruction (or no side effect instruction) based on the model.
2018-11-30 12:15:23 -08:00
Dave Bartolomeo
af443569d9 C++: Fix handling of accesses to escaped variables in Aliased SSA
This fixes a subtle bug in the construction of aliased SSA. `getResultMemoryAccess` was failing to return a `MemoryAccess` for a store to a variable whose address escaped. This is because no `VirtualIRVariable` was being created for such variables. The code was assuming that any access to such a variable would be via `UnknownMemoryAccess`. The result is that accesses to such variables were not being modeled in SSA at all.

Instead, the way to handle this is to have a `VariableMemoryAccess` even when the variable being accessed has escaped, and to have `VariableMemoryAccess::getVirtualVariable()` return the `UnknownVirtualVariable` for escaped variables. In the future, this will also let us be less conservative about inserting `Chi` nodes, because we'll be able to determine that there's an exact overlap between two accesses to the same escaped variable in some cases.
2018-11-30 12:15:19 -08:00
Dave Bartolomeo
ae8f18c0b5 C++: Treat all Convert instructions as dataflow
The AST dataflow library essentially ignores conversions, which is probably the right behavior. Converting an `int` to a `long` preserves the value, even if the bit pattern might be different. It's arguable whether narrowing conversions should be treated as dataflow, but we'll do so for now. We can revisit that if we see it cause problems.
2018-11-30 12:15:15 -08:00
Dave Bartolomeo
58f7596519 C++: IR-based dataflow 2018-11-30 12:15:11 -08:00
Jonas Jensen
148c79a0e6 C++: Deprecate RecursionPrevention 2018-11-30 15:41:43 +01:00
Geoffrey White
453529e3bf Merge pull request #575 from jbj/UnsafeCreateProcessCall-nullValue
C++: Avoid using nullValue predicate (rc/1.19)
2018-11-30 09:54:17 +00:00
Jonas Jensen
dd3791490a Merge pull request #580 from geoffw0/av-79-perf
CPP: Fix performance issue with AV Rule 79.ql.
2018-11-30 08:39:38 +01:00
Jonas Jensen
b98452ddb1 Merge pull request #474 from rdmarsh2/rdmarsh/cpp/call-side-effect
C++: Initital aliased SSA with Chi nodes and function side effects
2018-11-29 18:31:29 +01:00
Geoffrey White
4744cece7b Merge pull request #576 from jbj/bbEntryReachesLocally-perf
C++: Fix performance of bbEntryReachesLocally (1.19)
2018-11-29 17:12:47 +00:00
Geoffrey White
e09ce77678 CPP: Fix performance issue with AV Rule 79.ql. 2018-11-29 15:16:01 +00:00
Jonas Jensen
62d478eab3 C++: Fix performance of bbEntryReachesLocally
This predicate was fast with the queries and engine from 1.18. With the
queries from `master` it got a bad join order in the
`UninitializedLocal.ql` query, which made it take 2m34s on Wireshark.
This commit decomposes `bbEntryReachesLocally` into two predicates that
together take only 4s.
2018-11-29 15:11:32 +01:00
Jonas Jensen
8654ebcbbd C++: Avoid using nullValue predicate
The `nullValue` predicate performs a slow custom data-flow analysis to
find possible null values. It's so slow that it timed out after 1200s on
Wireshark.

In `UnsafeCreateProcessCall.ql`, the values found with `nullValue` were
used as sources in another data-flow analysis. By using the `NullValue`
class as sink instead of `nullValue`, we avoid the slow-down of doing
data flow twice. The `NullValue` class is essentially the base case of
`nullValue`. Confusing names, yes.
2018-11-29 13:33:45 +01:00
Dave Bartolomeo
40864f9ebb C++: Fix GVN test expectation 2018-11-28 14:07:23 -08:00
Dave Bartolomeo
d7938362dd C++: Rename Chi IPA types to match classes 2018-11-28 10:33:04 -08:00
Dave Bartolomeo
5d997c7135 C++: Big QLDoc comment for ChiInstruction 2018-11-27 17:09:26 -08:00
Dave Bartolomeo
53cd5e9994 C++: Fix bug introduced by earlier commit 2018-11-27 14:57:58 -08:00
Dave Bartolomeo
7e6e6f00c1 C++: Fix IR for designated array initializers 2018-11-27 14:57:23 -08:00