Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 7c6918d

Browse files
authored
Merge pull request #11543 from MathiasVP/refactor-isdef-isuse
C++: Refactor `isDef` and `isUse` in preparation for iterator flow
2 parents 0a1097d + f814ce7 commit 7c6918d

6 files changed

Lines changed: 190 additions & 175 deletions

File tree

cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/DataFlowPrivate.qll

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -561,7 +561,7 @@ predicate storeStep(Node node1, Content c, PostFieldUpdateNode node2) {
561561
* operations and exactly `n` `LoadInstruction` operations.
562562
*/
563563
private predicate numberOfLoadsFromOperandRec(Operand operandFrom, Operand operandTo, int ind) {
564-
exists(LoadInstruction load | load.getSourceAddressOperand() = operandFrom |
564+
exists(Instruction load | Ssa::isDereference(load, operandFrom) |
565565
operandTo = operandFrom and ind = 0
566566
or
567567
numberOfLoadsFromOperand(load.getAUse(), operandTo, ind - 1)
@@ -581,7 +581,7 @@ private predicate numberOfLoadsFromOperandRec(Operand operandFrom, Operand opera
581581
private predicate numberOfLoadsFromOperand(Operand operandFrom, Operand operandTo, int n) {
582582
numberOfLoadsFromOperandRec(operandFrom, operandTo, n)
583583
or
584-
not any(LoadInstruction load).getSourceAddressOperand() = operandFrom and
584+
not Ssa::isDereference(_, operandFrom) and
585585
not conversionFlow(operandFrom, _, _) and
586586
operandFrom = operandTo and
587587
n = 0

cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/DataFlowUtil.qll

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,8 @@ predicate conversionFlow(Operand opFrom, Instruction instrTo, boolean isPointerA
8686
instrTo.(CheckedConvertOrNullInstruction).getUnaryOperand() = opFrom
8787
or
8888
instrTo.(InheritanceConversionInstruction).getUnaryOperand() = opFrom
89+
or
90+
Ssa::isAdditionalConversionFlow(opFrom, instrTo)
8991
)
9092
or
9193
isPointerArith = true and
@@ -382,12 +384,12 @@ class OperandNode extends Node, Node0 {
382384
* For example, `stripPointers(int*&)` is `int*` and `stripPointers(int*)` is `int`.
383385
*/
384386
private Type stripPointer(Type t) {
385-
result = t.(PointerType).getBaseType()
387+
result = any(Ssa::Indirection ind | ind.getType() = t).getBaseType()
386388
or
389+
// These types have a sensible base type, but don't receive additional
390+
// dataflow nodes representing their indirections. So for now we special case them.
387391
result = t.(ArrayType).getBaseType()
388392
or
389-
result = t.(ReferenceType).getBaseType()
390-
or
391393
result = t.(PointerToMemberType).getBaseType()
392394
or
393395
result = t.(FunctionPointerIshType).getBaseType()
@@ -1140,8 +1142,9 @@ predicate localFlowStep = simpleLocalFlowStep/2;
11401142

11411143
private predicate indirectionOperandFlow(RawIndirectOperand nodeFrom, Node nodeTo) {
11421144
// Reduce the indirection count by 1 if we're passing through a `LoadInstruction`.
1143-
exists(int ind, LoadInstruction load |
1144-
hasOperandAndIndex(nodeFrom, load.getSourceAddressOperand(), ind) and
1145+
exists(int ind, Instruction load, Operand address |
1146+
Ssa::isDereference(load, address) and
1147+
hasOperandAndIndex(nodeFrom, address, ind) and
11451148
nodeHasInstruction(nodeTo, load, ind - 1)
11461149
)
11471150
or

cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/SsaInternals.qll

Lines changed: 7 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -19,12 +19,6 @@ private module SourceVariables {
1919
)
2020
}
2121

22-
class BaseSourceVariable = SsaInternals0::BaseSourceVariable;
23-
24-
class BaseIRVariable = SsaInternals0::BaseIRVariable;
25-
26-
class BaseCallVariable = SsaInternals0::BaseCallVariable;
27-
2822
cached
2923
private newtype TSourceVariable =
3024
TSourceIRVariable(BaseIRVariable baseVar, int ind) {
@@ -159,15 +153,10 @@ abstract private class DefOrUseImpl extends TDefOrUseImpl {
159153
* Gets the instruction that computes the base of this definition or use.
160154
* This is always a `VariableAddressInstruction` or an `AllocationInstruction`.
161155
*/
162-
abstract Instruction getBase();
156+
abstract BaseSourceVariableInstruction getBase();
163157

164158
final BaseSourceVariable getBaseSourceVariable() {
165-
exists(IRVariable var |
166-
result.(BaseIRVariable).getIRVariable() = var and
167-
instructionHasIRVariable(this.getBase(), var)
168-
)
169-
or
170-
result.(BaseCallVariable).getCallInstruction() = this.getBase()
159+
this.getBase().getBaseSourceVariable() = result
171160
}
172161

173162
/** Gets the variable that is defined or used. */
@@ -179,11 +168,6 @@ abstract private class DefOrUseImpl extends TDefOrUseImpl {
179168
}
180169
}
181170

182-
pragma[noinline]
183-
private predicate instructionHasIRVariable(VariableAddressInstruction vai, IRVariable var) {
184-
vai.getIRVariable() = var
185-
}
186-
187171
private predicate defOrUseHasSourceVariable(DefOrUseImpl defOrUse, BaseSourceVariable bv, int ind) {
188172
defHasSourceVariable(defOrUse, bv, ind)
189173
or
@@ -214,7 +198,7 @@ class DefImpl extends DefOrUseImpl, TDefImpl {
214198

215199
DefImpl() { this = TDefImpl(address, ind) }
216200

217-
override Instruction getBase() { isDef(_, _, address, result, _, _) }
201+
override BaseSourceVariableInstruction getBase() { isDef(_, _, address, result, _, _) }
218202

219203
Operand getAddressOperand() { result = address }
220204

@@ -259,7 +243,7 @@ class UseImpl extends DefOrUseImpl, TUseImpl {
259243

260244
override int getIndirectionIndex() { result = ind }
261245

262-
override Instruction getBase() { isUse(_, operand, result, _, ind) }
246+
override BaseSourceVariableInstruction getBase() { isUse(_, operand, result, _, ind) }
263247

264248
predicate isCertain() { isUse(true, operand, _, _, ind) }
265249
}
@@ -308,9 +292,8 @@ predicate outNodeHasAddressAndIndex(
308292
}
309293

310294
private predicate defToNode(Node nodeFrom, Def def) {
311-
// TODO: This is not yet needed (and in fact, the compiler rejects it because `exists(def.getValue().asOperand())` never holds).
312-
// nodeHasOperand(nodeFrom, def.getValue().asOperand(), def.getIndirectionIndex())
313-
// or
295+
nodeHasOperand(nodeFrom, def.getValue().asOperand(), def.getIndirectionIndex())
296+
or
314297
nodeHasInstruction(nodeFrom, def.getValue().asInstruction(), def.getIndirectionIndex())
315298
}
316299

@@ -415,22 +398,14 @@ predicate fromPhiNode(SsaPhiNode nodeFrom, Node nodeTo) {
415398
)
416399
}
417400

418-
private SsaInternals0::SourceVariable getOldSourceVariable(SourceVariable v) {
419-
v.getBaseVariable().(BaseIRVariable).getIRVariable() =
420-
result.getBaseVariable().(SsaInternals0::BaseIRVariable).getIRVariable()
421-
or
422-
v.getBaseVariable().(BaseCallVariable).getCallInstruction() =
423-
result.getBaseVariable().(SsaInternals0::BaseCallVariable).getCallInstruction()
424-
}
425-
426401
/**
427402
* Holds if there is a write at index `i` in basic block `bb` to variable `v` that's
428403
* subsequently read (as determined by the SSA pruning stage).
429404
*/
430405
private predicate variableWriteCand(IRBlock bb, int i, SourceVariable v) {
431406
exists(SsaInternals0::Def def, SsaInternals0::SourceVariable v0 |
432407
def.asDefOrUse().hasIndexInBlock(bb, i, v0) and
433-
v0 = getOldSourceVariable(v)
408+
v0 = v.getBaseVariable()
434409
)
435410
}
436411

0 commit comments

Comments
 (0)