Merge pull request #2805 from jbj/dataflow-sideeffect-join

C++: IR DataFlowUtil::modelFlow join order fix
This commit is contained in:
Dave Bartolomeo
2020-02-10 13:04:51 -07:00
committed by GitHub

View File

@@ -365,10 +365,10 @@ private predicate modelFlow(Instruction iFrom, Instruction iTo) {
modelOut.isReturnValueDeref() and
iTo = call
or
exists(WriteSideEffectInstruction outNode |
modelOut.isParameterDeref(outNode.getIndex()) and
exists(int index, WriteSideEffectInstruction outNode |
modelOut.isParameterDeref(index) and
iTo = outNode and
outNode.getPrimaryInstruction() = call
outNode = getSideEffectFor(call, index)
)
// TODO: add write side effects for qualifiers
) and
@@ -380,8 +380,7 @@ private predicate modelFlow(Instruction iFrom, Instruction iTo) {
or
exists(int index, ReadSideEffectInstruction read |
modelIn.isParameterDeref(index) and
read.getIndex() = index and
read.getPrimaryInstruction() = call and
read = getSideEffectFor(call, index) and
iFrom = read.getSideEffectOperand().getAnyDef()
)
or
@@ -392,6 +391,18 @@ private predicate modelFlow(Instruction iFrom, Instruction iTo) {
)
}
/**
* Holds if the result is a side effect for instruction `call` on argument
* index `argument`. This helper predicate makes it easy to join on both of
* these columns at once, avoiding pathological join orders in case the
* argument index should get joined first.
*/
pragma[noinline]
SideEffectInstruction getSideEffectFor(CallInstruction call, int argument) {
call = result.getPrimaryInstruction() and
argument = result.(IndexedInstruction).getIndex()
}
/**
* Holds if data flows from `source` to `sink` in zero or more local
* (intra-procedural) steps.