mirror of
https://github.com/github/codeql.git
synced 2026-04-30 19:26:02 +02:00
C++: fix inconsistencies from IR global vars
This commit is contained in:
@@ -100,7 +100,7 @@ class Node extends TIRDataFlowNode {
|
||||
Declaration getEnclosingCallable() { none() } // overridden in subclasses
|
||||
|
||||
/** Gets the function to which this node belongs, if any. */
|
||||
Function getFunction() { none() } // overridden in subclasses
|
||||
Declaration getFunction() { none() } // overridden in subclasses
|
||||
|
||||
/** Gets the type of this node. */
|
||||
IRType getType() { none() } // overridden in subclasses
|
||||
@@ -196,7 +196,7 @@ class InstructionNode extends Node, TInstructionNode {
|
||||
|
||||
override Declaration getEnclosingCallable() { result = this.getFunction() }
|
||||
|
||||
override Function getFunction() { result = instr.getEnclosingFunction() }
|
||||
override Declaration getFunction() { result = instr.getEnclosingFunction() }
|
||||
|
||||
override IRType getType() { result = instr.getResultIRType() }
|
||||
|
||||
@@ -222,7 +222,7 @@ class OperandNode extends Node, TOperandNode {
|
||||
|
||||
override Declaration getEnclosingCallable() { result = this.getFunction() }
|
||||
|
||||
override Function getFunction() { result = op.getUse().getEnclosingFunction() }
|
||||
override Declaration getFunction() { result = op.getUse().getEnclosingFunction() }
|
||||
|
||||
override IRType getType() { result = op.getIRType() }
|
||||
|
||||
@@ -274,7 +274,7 @@ class StoreNodeInstr extends StoreNode, TStoreNodeInstr {
|
||||
/** Gets the underlying instruction. */
|
||||
Instruction getInstruction() { result = instr }
|
||||
|
||||
override Function getFunction() { result = this.getInstruction().getEnclosingFunction() }
|
||||
override Declaration getFunction() { result = this.getInstruction().getEnclosingFunction() }
|
||||
|
||||
override IRType getType() { result = this.getInstruction().getResultIRType() }
|
||||
|
||||
@@ -328,7 +328,7 @@ class StoreNodeOperand extends StoreNode, TStoreNodeOperand {
|
||||
/** Gets the underlying operand. */
|
||||
Operand getOperand() { result = operand }
|
||||
|
||||
override Function getFunction() { result = operand.getDef().getEnclosingFunction() }
|
||||
override Declaration getFunction() { result = operand.getDef().getEnclosingFunction() }
|
||||
|
||||
override IRType getType() { result = operand.getIRType() }
|
||||
|
||||
@@ -384,7 +384,7 @@ class ReadNode extends Node, TReadNode {
|
||||
|
||||
override Declaration getEnclosingCallable() { result = this.getFunction() }
|
||||
|
||||
override Function getFunction() { result = this.getInstruction().getEnclosingFunction() }
|
||||
override Declaration getFunction() { result = this.getInstruction().getEnclosingFunction() }
|
||||
|
||||
override IRType getType() { result = this.getInstruction().getResultIRType() }
|
||||
|
||||
@@ -436,7 +436,7 @@ class SsaPhiNode extends Node, TSsaPhiNode {
|
||||
|
||||
override Declaration getEnclosingCallable() { result = this.getFunction() }
|
||||
|
||||
override Function getFunction() { result = phi.getBasicBlock().getEnclosingFunction() }
|
||||
override Declaration getFunction() { result = phi.getBasicBlock().getEnclosingFunction() }
|
||||
|
||||
override IRType getType() { result instanceof IRVoidType }
|
||||
|
||||
@@ -673,7 +673,7 @@ class VariableNode extends Node, TVariableNode {
|
||||
/** Gets the variable corresponding to this node. */
|
||||
Variable getVariable() { result = v }
|
||||
|
||||
override Function getFunction() { none() }
|
||||
override Declaration getFunction() { none() }
|
||||
|
||||
override Declaration getEnclosingCallable() {
|
||||
// When flow crosses from one _enclosing callable_ to another, the
|
||||
|
||||
@@ -524,4 +524,23 @@ module InstructionConsistency {
|
||||
"' has a `this` argument operand that is not an address, in function '$@'." and
|
||||
irFunc = getInstructionIRFunction(instr, irFuncText)
|
||||
}
|
||||
|
||||
query predicate nonUniqueIRVariable(
|
||||
Instruction instr, string message, OptionalIRFunction irFunc, string irFuncText
|
||||
) {
|
||||
exists(VariableInstruction vi, IRVariable v1, IRVariable v2 |
|
||||
instr = vi and vi.getIRVariable() = v1 and vi.getIRVariable() = v2 and v1 != v2
|
||||
) and
|
||||
message =
|
||||
"Variable instruction '" + instr.toString() +
|
||||
"' has multiple associated variables, in function '$@'." and
|
||||
irFunc = getInstructionIRFunction(instr, irFuncText)
|
||||
or
|
||||
instr.getOpcode() instanceof Opcode::VariableAddress and
|
||||
not instr instanceof VariableInstruction and
|
||||
message =
|
||||
"Variable address instruction '" + instr.toString() +
|
||||
"' has no associated variable, in function '$@'." and
|
||||
irFunc = getInstructionIRFunction(instr, irFuncText)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -13,6 +13,7 @@ private import TranslatedElement
|
||||
private import TranslatedExpr
|
||||
private import TranslatedStmt
|
||||
private import TranslatedFunction
|
||||
private import TranslatedGlobalVar
|
||||
|
||||
TranslatedElement getInstructionTranslatedElement(Instruction instruction) {
|
||||
instruction = TRawInstruction(result, _)
|
||||
@@ -44,8 +45,10 @@ module Raw {
|
||||
}
|
||||
|
||||
cached
|
||||
predicate hasUserVariable(Function func, Variable var, CppType type) {
|
||||
getTranslatedFunction(func).hasUserVariable(var, type)
|
||||
predicate hasUserVariable(Declaration decl, Variable var, CppType type) {
|
||||
getTranslatedFunction(decl).hasUserVariable(var, type)
|
||||
or
|
||||
getTranslatedVarInit(decl).hasUserVariable(var, type)
|
||||
}
|
||||
|
||||
cached
|
||||
|
||||
@@ -6,6 +6,7 @@ private import semmle.code.cpp.ir.implementation.internal.OperandTag
|
||||
private import semmle.code.cpp.ir.internal.CppType
|
||||
private import TranslatedInitialization
|
||||
private import InstructionTag
|
||||
private import semmle.code.cpp.ir.internal.IRUtilities
|
||||
|
||||
class TranslatedGlobalOrNamespaceVarInit extends TranslatedRootElement,
|
||||
TTranslatedGlobalOrNamespaceVarInit, InitializationContext {
|
||||
@@ -98,6 +99,33 @@ class TranslatedGlobalOrNamespaceVarInit extends TranslatedRootElement,
|
||||
}
|
||||
|
||||
override Type getTargetType() { result = var.getUnspecifiedType() }
|
||||
|
||||
/**
|
||||
* Holds if this variable defines or accesses variable `var` with type `type`. This includes all
|
||||
* parameters and local variables, plus any global variables or static data members that are
|
||||
* directly accessed by the function.
|
||||
*/
|
||||
final predicate hasUserVariable(Variable varUsed, CppType type) {
|
||||
(
|
||||
(
|
||||
varUsed instanceof GlobalOrNamespaceVariable
|
||||
or
|
||||
varUsed instanceof MemberVariable and not varUsed instanceof Field
|
||||
) and
|
||||
exists(VariableAccess access |
|
||||
access.getTarget() = varUsed and
|
||||
access.getEnclosingVariable() = var
|
||||
)
|
||||
or
|
||||
var = varUsed
|
||||
or
|
||||
varUsed.(LocalScopeVariable).getEnclosingElement*() = var
|
||||
or
|
||||
varUsed.(Parameter).getCatchBlock().getEnclosingElement*() = var
|
||||
) and
|
||||
type = getTypeForPRValue(getVariableType(varUsed))
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
TranslatedGlobalOrNamespaceVarInit getTranslatedVarInit(GlobalOrNamespaceVariable var) {
|
||||
|
||||
@@ -1,22 +1,4 @@
|
||||
uniqueEnclosingCallable
|
||||
| globals.cpp:9:5:9:19 | Address | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:9:5:9:19 | AliasedDefinition | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:9:5:9:19 | VariableAddress | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:9:5:9:19 | VariableAddress [post update] | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:9:23:9:23 | 0 | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:9:23:9:23 | ChiPartial | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:9:23:9:23 | ChiTotal | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:9:23:9:23 | Store | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:9:23:9:23 | StoreValue | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:16:12:16:26 | Address | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:16:12:16:26 | AliasedDefinition | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:16:12:16:26 | VariableAddress | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:16:12:16:26 | VariableAddress [post update] | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:16:30:16:30 | 0 | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:16:30:16:30 | ChiPartial | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:16:30:16:30 | ChiTotal | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:16:30:16:30 | Store | Node should have one enclosing callable but has 0. |
|
||||
| globals.cpp:16:30:16:30 | StoreValue | Node should have one enclosing callable but has 0. |
|
||||
uniqueType
|
||||
uniqueNodeLocation
|
||||
| BarrierGuard.cpp:2:11:2:13 | (unnamed parameter 0) | Node should have one location but has 6. |
|
||||
@@ -238,10 +220,10 @@ postWithInFlow
|
||||
| lambdas.cpp:20:11:20:11 | FieldAddress [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| lambdas.cpp:20:11:20:11 | FieldAddress [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| lambdas.cpp:20:11:20:11 | FieldAddress [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| lambdas.cpp:23:3:23:3 | (reference dereference) [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| lambdas.cpp:23:3:23:14 | FieldAddress [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| lambdas.cpp:23:3:23:14 | VariableAddress [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| lambdas.cpp:23:3:23:14 | v [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| lambdas.cpp:23:15:23:15 | (reference dereference) [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| lambdas.cpp:28:7:28:7 | VariableAddress [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| lambdas.cpp:28:10:31:2 | FieldAddress [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| lambdas.cpp:28:10:31:2 | FieldAddress [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
|
||||
@@ -27,6 +27,14 @@ invalidOverlap
|
||||
nonUniqueEnclosingIRFunction
|
||||
fieldAddressOnNonPointer
|
||||
thisArgumentIsNonPointer
|
||||
nonUniqueIRVariable
|
||||
| ir.cpp:1038:6:1038:8 | VariableAddress: lam | Variable address instruction 'VariableAddress: lam' has no associated variable, in function '$@'. | ir.cpp:1038:6:1038:8 | (lambda [] type at line 1038, col. 12) lam | (lambda [] type at line 1038, col. 12) lam |
|
||||
| ir.cpp:1759:5:1759:12 | VariableAddress: global_2 | Variable address instruction 'VariableAddress: global_2' has no associated variable, in function '$@'. | ir.cpp:1759:5:1759:12 | int global_2 | int global_2 |
|
||||
| ir.cpp:1761:11:1761:18 | VariableAddress: global_3 | Variable address instruction 'VariableAddress: global_3' has no associated variable, in function '$@'. | ir.cpp:1761:11:1761:18 | int const global_3 | int const global_3 |
|
||||
| ir.cpp:1763:18:1763:25 | VariableAddress: global_4 | Variable address instruction 'VariableAddress: global_4' has no associated variable, in function '$@'. | ir.cpp:1763:18:1763:25 | constructor_only global_4 | constructor_only global_4 |
|
||||
| ir.cpp:1765:18:1765:25 | VariableAddress: global_5 | Variable address instruction 'VariableAddress: global_5' has no associated variable, in function '$@'. | ir.cpp:1765:18:1765:25 | constructor_only global_5 | constructor_only global_5 |
|
||||
| ir.cpp:1767:7:1767:19 | VariableAddress: global_string | Variable address instruction 'VariableAddress: global_string' has no associated variable, in function '$@'. | ir.cpp:1767:7:1767:19 | char* global_string | char* global_string |
|
||||
| struct_init.cpp:9:13:9:25 | VariableAddress: infos_in_file | Variable address instruction 'VariableAddress: infos_in_file' has no associated variable, in function '$@'. | struct_init.cpp:9:13:9:25 | Info infos_in_file[] | Info infos_in_file[] |
|
||||
missingCanonicalLanguageType
|
||||
multipleCanonicalLanguageTypes
|
||||
missingIRType
|
||||
|
||||
Reference in New Issue
Block a user