mirror of
https://github.com/github/codeql.git
synced 2026-04-28 02:05:14 +02:00
C++: Add DefinitionByReferenceNode to IR dataflow
This commit is contained in:
@@ -173,11 +173,53 @@ abstract class PostUpdateNode extends Node {
|
||||
abstract Node getPreUpdateNode();
|
||||
}
|
||||
|
||||
/**
|
||||
* A node that represents the value of a variable after a function call that
|
||||
* may have changed the variable because it's passed by reference.
|
||||
*
|
||||
* A typical example would be a call `f(&x)`. Firstly, there will be flow into
|
||||
* `x` from previous definitions of `x`. Secondly, there will be a
|
||||
* `DefinitionByReferenceNode` to represent the value of `x` after the call has
|
||||
* returned. This node will have its `getArgument()` equal to `&x` and its
|
||||
* `getVariableAccess()` equal to `x`.
|
||||
*/
|
||||
class DefinitionByReferenceNode extends Node {
|
||||
override WriteSideEffectInstruction instr;
|
||||
|
||||
/** Gets the argument corresponding to this node. */
|
||||
Expr getArgument() {
|
||||
result = instr
|
||||
.getPrimaryInstruction()
|
||||
.(CallInstruction)
|
||||
.getPositionalArgument(instr.getIndex())
|
||||
.getUnconvertedResultExpression()
|
||||
or
|
||||
result = instr
|
||||
.getPrimaryInstruction()
|
||||
.(CallInstruction)
|
||||
.getThisArgument()
|
||||
.getUnconvertedResultExpression() and
|
||||
instr.getIndex() = -1
|
||||
}
|
||||
|
||||
|
||||
/** Gets the parameter through which this value is assigned. */
|
||||
Parameter getParameter() {
|
||||
exists(CallInstruction ci |
|
||||
result = ci.getStaticCallTarget().getParameter(instr.getIndex())
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the node corresponding to `instr`.
|
||||
*/
|
||||
Node instructionNode(Instruction instr) { result.asInstruction() = instr }
|
||||
|
||||
DefinitionByReferenceNode definitionByReferenceNode(Expr e) {
|
||||
result.getArgument() = e
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets a `Node` corresponding to `e` or any of its conversions. There is no
|
||||
* result if `e` is a `Conversion`.
|
||||
|
||||
@@ -1236,6 +1236,8 @@ class IndirectReadSideEffectInstruction extends SideEffectInstruction {
|
||||
IndirectReadSideEffectInstruction() { getOpcode() instanceof Opcode::IndirectReadSideEffect }
|
||||
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
Instruction getSideEffect() { result = getAnOperand().(SideEffectOperand).getDef() }
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1245,6 +1247,8 @@ class BufferReadSideEffectInstruction extends SideEffectInstruction {
|
||||
BufferReadSideEffectInstruction() { getOpcode() instanceof Opcode::BufferReadSideEffect }
|
||||
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
Instruction getSideEffect() { result = getAnOperand().(SideEffectOperand).getDef() }
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1258,12 +1262,14 @@ class SizedBufferReadSideEffectInstruction extends SideEffectInstruction {
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
Instruction getSizeDef() { result = getAnOperand().(BufferSizeOperand).getDef() }
|
||||
|
||||
Instruction getSideEffect() { result = getAnOperand().(SideEffectOperand).getDef() }
|
||||
}
|
||||
|
||||
/**
|
||||
* An instruction representing a side effect of a function call.
|
||||
*/
|
||||
class WriteSideEffectInstruction extends SideEffectInstruction {
|
||||
class WriteSideEffectInstruction extends SideEffectInstruction, IndexedInstruction {
|
||||
WriteSideEffectInstruction() { getOpcode() instanceof WriteSideEffectOpcode }
|
||||
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
@@ -1236,6 +1236,8 @@ class IndirectReadSideEffectInstruction extends SideEffectInstruction {
|
||||
IndirectReadSideEffectInstruction() { getOpcode() instanceof Opcode::IndirectReadSideEffect }
|
||||
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
Instruction getSideEffect() { result = getAnOperand().(SideEffectOperand).getDef() }
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1245,6 +1247,8 @@ class BufferReadSideEffectInstruction extends SideEffectInstruction {
|
||||
BufferReadSideEffectInstruction() { getOpcode() instanceof Opcode::BufferReadSideEffect }
|
||||
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
Instruction getSideEffect() { result = getAnOperand().(SideEffectOperand).getDef() }
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1258,12 +1262,14 @@ class SizedBufferReadSideEffectInstruction extends SideEffectInstruction {
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
Instruction getSizeDef() { result = getAnOperand().(BufferSizeOperand).getDef() }
|
||||
|
||||
Instruction getSideEffect() { result = getAnOperand().(SideEffectOperand).getDef() }
|
||||
}
|
||||
|
||||
/**
|
||||
* An instruction representing a side effect of a function call.
|
||||
*/
|
||||
class WriteSideEffectInstruction extends SideEffectInstruction {
|
||||
class WriteSideEffectInstruction extends SideEffectInstruction, IndexedInstruction {
|
||||
WriteSideEffectInstruction() { getOpcode() instanceof WriteSideEffectOpcode }
|
||||
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
@@ -1236,6 +1236,8 @@ class IndirectReadSideEffectInstruction extends SideEffectInstruction {
|
||||
IndirectReadSideEffectInstruction() { getOpcode() instanceof Opcode::IndirectReadSideEffect }
|
||||
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
Instruction getSideEffect() { result = getAnOperand().(SideEffectOperand).getDef() }
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1245,6 +1247,8 @@ class BufferReadSideEffectInstruction extends SideEffectInstruction {
|
||||
BufferReadSideEffectInstruction() { getOpcode() instanceof Opcode::BufferReadSideEffect }
|
||||
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
Instruction getSideEffect() { result = getAnOperand().(SideEffectOperand).getDef() }
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1258,12 +1262,14 @@ class SizedBufferReadSideEffectInstruction extends SideEffectInstruction {
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
Instruction getSizeDef() { result = getAnOperand().(BufferSizeOperand).getDef() }
|
||||
|
||||
Instruction getSideEffect() { result = getAnOperand().(SideEffectOperand).getDef() }
|
||||
}
|
||||
|
||||
/**
|
||||
* An instruction representing a side effect of a function call.
|
||||
*/
|
||||
class WriteSideEffectInstruction extends SideEffectInstruction {
|
||||
class WriteSideEffectInstruction extends SideEffectInstruction, IndexedInstruction {
|
||||
WriteSideEffectInstruction() { getOpcode() instanceof WriteSideEffectOpcode }
|
||||
|
||||
Instruction getArgumentDef() { result = getAnOperand().(AddressOperand).getDef() }
|
||||
|
||||
Reference in New Issue
Block a user