mirror of
https://github.com/github/codeql.git
synced 2026-05-30 11:01:24 +02:00
Compare commits
6 Commits
oscarsj-pa
...
rdmarsh2/i
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
06be3aec3e | ||
|
|
cb93684287 | ||
|
|
fd1ade8e50 | ||
|
|
536f9f9cca | ||
|
|
f4d3cdeca9 | ||
|
|
d0c603f2eb |
@@ -1,5 +1,3 @@
|
||||
Please do not merge this PR!
|
||||
|
||||
# CodeQL
|
||||
|
||||
This open source repository contains the standard CodeQL libraries and queries that power [GitHub Advanced Security](https://github.com/features/security/code) and the other application security products that [GitHub](https://github.com/features/security/) makes available to its customers worldwide.
|
||||
|
||||
@@ -40,6 +40,7 @@
|
||||
"csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowImpl3.qll",
|
||||
"csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowImpl4.qll",
|
||||
"csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowImpl5.qll",
|
||||
"csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowImplForContentDataFlow.qll",
|
||||
"go/ql/lib/semmle/go/dataflow/internal/DataFlowImpl1.qll",
|
||||
"go/ql/lib/semmle/go/dataflow/internal/DataFlowImpl2.qll",
|
||||
"go/ql/lib/semmle/go/dataflow/internal/DataFlowImplForStringsNewReplacer.qll",
|
||||
|
||||
@@ -1,7 +1,3 @@
|
||||
## 0.7.1
|
||||
|
||||
No user-facing changes.
|
||||
|
||||
## 0.7.0
|
||||
|
||||
### Breaking Changes
|
||||
|
||||
@@ -1,4 +0,0 @@
|
||||
---
|
||||
category: minorAnalysis
|
||||
---
|
||||
* The new dataflow (`semmle.code.cpp.dataflow.new.DataFlow`) and taint-tracking libraries (`semmle.code.cpp.dataflow.new.TaintTracking`) now support tracking flow through static local variables.
|
||||
@@ -1,3 +0,0 @@
|
||||
## 0.7.1
|
||||
|
||||
No user-facing changes.
|
||||
@@ -1,2 +1,2 @@
|
||||
---
|
||||
lastReleaseVersion: 0.7.1
|
||||
lastReleaseVersion: 0.7.0
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
name: codeql/cpp-all
|
||||
version: 0.7.2-dev
|
||||
version: 0.7.1-dev
|
||||
groups: cpp
|
||||
dbscheme: semmlecode.cpp.dbscheme
|
||||
extractor: cpp
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -815,15 +815,7 @@ private module Cached {
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if data can flow from `node1` to `node2` via a direct assignment to
|
||||
* `c`.
|
||||
*
|
||||
* This includes reverse steps through reads when the result of the read has
|
||||
* been stored into, in order to handle cases like `x.f1.f2 = y`.
|
||||
*/
|
||||
cached
|
||||
predicate store(
|
||||
private predicate store(
|
||||
Node node1, Content c, Node node2, DataFlowType contentType, DataFlowType containerType
|
||||
) {
|
||||
exists(ContentSet cs |
|
||||
@@ -831,6 +823,18 @@ private module Cached {
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if data can flow from `node1` to `node2` via a direct assignment to
|
||||
* `f`.
|
||||
*
|
||||
* This includes reverse steps through reads when the result of the read has
|
||||
* been stored into, in order to handle cases like `x.f1.f2 = y`.
|
||||
*/
|
||||
cached
|
||||
predicate store(Node node1, TypedContent tc, Node node2, DataFlowType contentType) {
|
||||
store(node1, tc.getContent(), node2, contentType, tc.getContainerType())
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if data can flow from `fromNode` to `toNode` because they are the post-update
|
||||
* nodes of some function output and input respectively, where the output and input
|
||||
@@ -928,15 +932,36 @@ private module Cached {
|
||||
TReturnCtxNoFlowThrough() or
|
||||
TReturnCtxMaybeFlowThrough(ReturnPosition pos)
|
||||
|
||||
cached
|
||||
newtype TTypedContentApprox =
|
||||
MkTypedContentApprox(ContentApprox c, DataFlowType t) {
|
||||
exists(Content cont |
|
||||
c = getContentApprox(cont) and
|
||||
store(_, cont, _, _, t)
|
||||
)
|
||||
}
|
||||
|
||||
cached
|
||||
newtype TTypedContent = MkTypedContent(Content c, DataFlowType t) { store(_, c, _, _, t) }
|
||||
|
||||
cached
|
||||
TypedContent getATypedContent(TypedContentApprox c) {
|
||||
exists(ContentApprox cls, DataFlowType t, Content cont |
|
||||
c = MkTypedContentApprox(cls, pragma[only_bind_into](t)) and
|
||||
result = MkTypedContent(cont, pragma[only_bind_into](t)) and
|
||||
cls = getContentApprox(cont)
|
||||
)
|
||||
}
|
||||
|
||||
cached
|
||||
newtype TAccessPathFront =
|
||||
TFrontNil() or
|
||||
TFrontHead(Content c)
|
||||
TFrontNil(DataFlowType t) or
|
||||
TFrontHead(TypedContent tc)
|
||||
|
||||
cached
|
||||
newtype TApproxAccessPathFront =
|
||||
TApproxFrontNil() or
|
||||
TApproxFrontHead(ContentApprox c)
|
||||
TApproxFrontNil(DataFlowType t) or
|
||||
TApproxFrontHead(TypedContentApprox tc)
|
||||
|
||||
cached
|
||||
newtype TAccessPathFrontOption =
|
||||
@@ -961,16 +986,8 @@ predicate recordDataFlowCallSite(DataFlowCall call, DataFlowCallable callable) {
|
||||
/**
|
||||
* A `Node` at which a cast can occur such that the type should be checked.
|
||||
*/
|
||||
class CastingNode instanceof Node {
|
||||
class CastingNode extends Node {
|
||||
CastingNode() { castingNode(this) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
}
|
||||
|
||||
private predicate readStepWithTypes(
|
||||
@@ -1118,17 +1135,9 @@ LocalCallContext getLocalCallContext(CallContext ctx, DataFlowCallable callable)
|
||||
* The value of a parameter at function entry, viewed as a node in a data
|
||||
* flow graph.
|
||||
*/
|
||||
class ParamNode instanceof Node {
|
||||
class ParamNode extends Node {
|
||||
ParamNode() { parameterNode(this, _, _) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if this node is the parameter of callable `c` at the specified
|
||||
* position.
|
||||
@@ -1137,17 +1146,9 @@ class ParamNode instanceof Node {
|
||||
}
|
||||
|
||||
/** A data-flow node that represents a call argument. */
|
||||
class ArgNode instanceof Node {
|
||||
class ArgNode extends Node {
|
||||
ArgNode() { argumentNode(this, _, _) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
|
||||
/** Holds if this argument occurs at the given position in the given call. */
|
||||
final predicate argumentOf(DataFlowCall call, ArgumentPosition pos) {
|
||||
argumentNode(this, call, pos)
|
||||
@@ -1158,17 +1159,9 @@ class ArgNode instanceof Node {
|
||||
* A node from which flow can return to the caller. This is either a regular
|
||||
* `ReturnNode` or a `PostUpdateNode` corresponding to the value of a parameter.
|
||||
*/
|
||||
class ReturnNodeExt instanceof Node {
|
||||
class ReturnNodeExt extends Node {
|
||||
ReturnNodeExt() { returnNodeExt(this, _) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
|
||||
/** Gets the kind of this returned value. */
|
||||
ReturnKindExt getKind() { returnNodeExt(this, result) }
|
||||
}
|
||||
@@ -1177,16 +1170,8 @@ class ReturnNodeExt instanceof Node {
|
||||
* A node to which data can flow from a call. Either an ordinary out node
|
||||
* or a post-update node associated with a call argument.
|
||||
*/
|
||||
class OutNodeExt instanceof Node {
|
||||
class OutNodeExt extends Node {
|
||||
OutNodeExt() { outNodeExt(this) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1402,37 +1387,67 @@ class ReturnCtx extends TReturnCtx {
|
||||
}
|
||||
}
|
||||
|
||||
/** An approximated `Content` tagged with the type of a containing object. */
|
||||
class TypedContentApprox extends MkTypedContentApprox {
|
||||
private ContentApprox c;
|
||||
private DataFlowType t;
|
||||
|
||||
TypedContentApprox() { this = MkTypedContentApprox(c, t) }
|
||||
|
||||
/** Gets a typed content approximated by this value. */
|
||||
TypedContent getATypedContent() { result = getATypedContent(this) }
|
||||
|
||||
/** Gets the content. */
|
||||
ContentApprox getContent() { result = c }
|
||||
|
||||
/** Gets the container type. */
|
||||
DataFlowType getContainerType() { result = t }
|
||||
|
||||
/** Gets a textual representation of this approximated content. */
|
||||
string toString() { result = c.toString() }
|
||||
}
|
||||
|
||||
/**
|
||||
* The front of an approximated access path. This is either a head or a nil.
|
||||
*/
|
||||
abstract class ApproxAccessPathFront extends TApproxAccessPathFront {
|
||||
abstract string toString();
|
||||
|
||||
abstract DataFlowType getType();
|
||||
|
||||
abstract boolean toBoolNonEmpty();
|
||||
|
||||
ContentApprox getHead() { this = TApproxFrontHead(result) }
|
||||
TypedContentApprox getHead() { this = TApproxFrontHead(result) }
|
||||
|
||||
pragma[nomagic]
|
||||
Content getAHead() {
|
||||
exists(ContentApprox cont |
|
||||
TypedContent getAHead() {
|
||||
exists(TypedContentApprox cont |
|
||||
this = TApproxFrontHead(cont) and
|
||||
cont = getContentApprox(result)
|
||||
result = cont.getATypedContent()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
class ApproxAccessPathFrontNil extends ApproxAccessPathFront, TApproxFrontNil {
|
||||
override string toString() { result = "nil" }
|
||||
private DataFlowType t;
|
||||
|
||||
ApproxAccessPathFrontNil() { this = TApproxFrontNil(t) }
|
||||
|
||||
override string toString() { result = ppReprType(t) }
|
||||
|
||||
override DataFlowType getType() { result = t }
|
||||
|
||||
override boolean toBoolNonEmpty() { result = false }
|
||||
}
|
||||
|
||||
class ApproxAccessPathFrontHead extends ApproxAccessPathFront, TApproxFrontHead {
|
||||
private ContentApprox c;
|
||||
private TypedContentApprox tc;
|
||||
|
||||
ApproxAccessPathFrontHead() { this = TApproxFrontHead(c) }
|
||||
ApproxAccessPathFrontHead() { this = TApproxFrontHead(tc) }
|
||||
|
||||
override string toString() { result = c.toString() }
|
||||
override string toString() { result = tc.toString() }
|
||||
|
||||
override DataFlowType getType() { result = tc.getContainerType() }
|
||||
|
||||
override boolean toBoolNonEmpty() { result = true }
|
||||
}
|
||||
@@ -1446,31 +1461,65 @@ class ApproxAccessPathFrontOption extends TApproxAccessPathFrontOption {
|
||||
}
|
||||
}
|
||||
|
||||
/** A `Content` tagged with the type of a containing object. */
|
||||
class TypedContent extends MkTypedContent {
|
||||
private Content c;
|
||||
private DataFlowType t;
|
||||
|
||||
TypedContent() { this = MkTypedContent(c, t) }
|
||||
|
||||
/** Gets the content. */
|
||||
Content getContent() { result = c }
|
||||
|
||||
/** Gets the container type. */
|
||||
DataFlowType getContainerType() { result = t }
|
||||
|
||||
/** Gets a textual representation of this content. */
|
||||
string toString() { result = c.toString() }
|
||||
|
||||
/**
|
||||
* Holds if access paths with this `TypedContent` at their head always should
|
||||
* be tracked at high precision. This disables adaptive access path precision
|
||||
* for such access paths.
|
||||
*/
|
||||
predicate forceHighPrecision() { forceHighPrecision(c) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The front of an access path. This is either a head or a nil.
|
||||
*/
|
||||
abstract class AccessPathFront extends TAccessPathFront {
|
||||
abstract string toString();
|
||||
|
||||
abstract DataFlowType getType();
|
||||
|
||||
abstract ApproxAccessPathFront toApprox();
|
||||
|
||||
Content getHead() { this = TFrontHead(result) }
|
||||
TypedContent getHead() { this = TFrontHead(result) }
|
||||
}
|
||||
|
||||
class AccessPathFrontNil extends AccessPathFront, TFrontNil {
|
||||
override string toString() { result = "nil" }
|
||||
private DataFlowType t;
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result = TApproxFrontNil() }
|
||||
AccessPathFrontNil() { this = TFrontNil(t) }
|
||||
|
||||
override string toString() { result = ppReprType(t) }
|
||||
|
||||
override DataFlowType getType() { result = t }
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result = TApproxFrontNil(t) }
|
||||
}
|
||||
|
||||
class AccessPathFrontHead extends AccessPathFront, TFrontHead {
|
||||
private Content c;
|
||||
private TypedContent tc;
|
||||
|
||||
AccessPathFrontHead() { this = TFrontHead(c) }
|
||||
AccessPathFrontHead() { this = TFrontHead(tc) }
|
||||
|
||||
override string toString() { result = c.toString() }
|
||||
override string toString() { result = tc.toString() }
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result.getAHead() = c }
|
||||
override DataFlowType getType() { result = tc.getContainerType() }
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result.getAHead() = tc }
|
||||
}
|
||||
|
||||
/** An optional access path front. */
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -815,15 +815,7 @@ private module Cached {
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if data can flow from `node1` to `node2` via a direct assignment to
|
||||
* `c`.
|
||||
*
|
||||
* This includes reverse steps through reads when the result of the read has
|
||||
* been stored into, in order to handle cases like `x.f1.f2 = y`.
|
||||
*/
|
||||
cached
|
||||
predicate store(
|
||||
private predicate store(
|
||||
Node node1, Content c, Node node2, DataFlowType contentType, DataFlowType containerType
|
||||
) {
|
||||
exists(ContentSet cs |
|
||||
@@ -831,6 +823,18 @@ private module Cached {
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if data can flow from `node1` to `node2` via a direct assignment to
|
||||
* `f`.
|
||||
*
|
||||
* This includes reverse steps through reads when the result of the read has
|
||||
* been stored into, in order to handle cases like `x.f1.f2 = y`.
|
||||
*/
|
||||
cached
|
||||
predicate store(Node node1, TypedContent tc, Node node2, DataFlowType contentType) {
|
||||
store(node1, tc.getContent(), node2, contentType, tc.getContainerType())
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if data can flow from `fromNode` to `toNode` because they are the post-update
|
||||
* nodes of some function output and input respectively, where the output and input
|
||||
@@ -928,15 +932,36 @@ private module Cached {
|
||||
TReturnCtxNoFlowThrough() or
|
||||
TReturnCtxMaybeFlowThrough(ReturnPosition pos)
|
||||
|
||||
cached
|
||||
newtype TTypedContentApprox =
|
||||
MkTypedContentApprox(ContentApprox c, DataFlowType t) {
|
||||
exists(Content cont |
|
||||
c = getContentApprox(cont) and
|
||||
store(_, cont, _, _, t)
|
||||
)
|
||||
}
|
||||
|
||||
cached
|
||||
newtype TTypedContent = MkTypedContent(Content c, DataFlowType t) { store(_, c, _, _, t) }
|
||||
|
||||
cached
|
||||
TypedContent getATypedContent(TypedContentApprox c) {
|
||||
exists(ContentApprox cls, DataFlowType t, Content cont |
|
||||
c = MkTypedContentApprox(cls, pragma[only_bind_into](t)) and
|
||||
result = MkTypedContent(cont, pragma[only_bind_into](t)) and
|
||||
cls = getContentApprox(cont)
|
||||
)
|
||||
}
|
||||
|
||||
cached
|
||||
newtype TAccessPathFront =
|
||||
TFrontNil() or
|
||||
TFrontHead(Content c)
|
||||
TFrontNil(DataFlowType t) or
|
||||
TFrontHead(TypedContent tc)
|
||||
|
||||
cached
|
||||
newtype TApproxAccessPathFront =
|
||||
TApproxFrontNil() or
|
||||
TApproxFrontHead(ContentApprox c)
|
||||
TApproxFrontNil(DataFlowType t) or
|
||||
TApproxFrontHead(TypedContentApprox tc)
|
||||
|
||||
cached
|
||||
newtype TAccessPathFrontOption =
|
||||
@@ -961,16 +986,8 @@ predicate recordDataFlowCallSite(DataFlowCall call, DataFlowCallable callable) {
|
||||
/**
|
||||
* A `Node` at which a cast can occur such that the type should be checked.
|
||||
*/
|
||||
class CastingNode instanceof Node {
|
||||
class CastingNode extends Node {
|
||||
CastingNode() { castingNode(this) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
}
|
||||
|
||||
private predicate readStepWithTypes(
|
||||
@@ -1118,17 +1135,9 @@ LocalCallContext getLocalCallContext(CallContext ctx, DataFlowCallable callable)
|
||||
* The value of a parameter at function entry, viewed as a node in a data
|
||||
* flow graph.
|
||||
*/
|
||||
class ParamNode instanceof Node {
|
||||
class ParamNode extends Node {
|
||||
ParamNode() { parameterNode(this, _, _) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if this node is the parameter of callable `c` at the specified
|
||||
* position.
|
||||
@@ -1137,17 +1146,9 @@ class ParamNode instanceof Node {
|
||||
}
|
||||
|
||||
/** A data-flow node that represents a call argument. */
|
||||
class ArgNode instanceof Node {
|
||||
class ArgNode extends Node {
|
||||
ArgNode() { argumentNode(this, _, _) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
|
||||
/** Holds if this argument occurs at the given position in the given call. */
|
||||
final predicate argumentOf(DataFlowCall call, ArgumentPosition pos) {
|
||||
argumentNode(this, call, pos)
|
||||
@@ -1158,17 +1159,9 @@ class ArgNode instanceof Node {
|
||||
* A node from which flow can return to the caller. This is either a regular
|
||||
* `ReturnNode` or a `PostUpdateNode` corresponding to the value of a parameter.
|
||||
*/
|
||||
class ReturnNodeExt instanceof Node {
|
||||
class ReturnNodeExt extends Node {
|
||||
ReturnNodeExt() { returnNodeExt(this, _) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
|
||||
/** Gets the kind of this returned value. */
|
||||
ReturnKindExt getKind() { returnNodeExt(this, result) }
|
||||
}
|
||||
@@ -1177,16 +1170,8 @@ class ReturnNodeExt instanceof Node {
|
||||
* A node to which data can flow from a call. Either an ordinary out node
|
||||
* or a post-update node associated with a call argument.
|
||||
*/
|
||||
class OutNodeExt instanceof Node {
|
||||
class OutNodeExt extends Node {
|
||||
OutNodeExt() { outNodeExt(this) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1402,37 +1387,67 @@ class ReturnCtx extends TReturnCtx {
|
||||
}
|
||||
}
|
||||
|
||||
/** An approximated `Content` tagged with the type of a containing object. */
|
||||
class TypedContentApprox extends MkTypedContentApprox {
|
||||
private ContentApprox c;
|
||||
private DataFlowType t;
|
||||
|
||||
TypedContentApprox() { this = MkTypedContentApprox(c, t) }
|
||||
|
||||
/** Gets a typed content approximated by this value. */
|
||||
TypedContent getATypedContent() { result = getATypedContent(this) }
|
||||
|
||||
/** Gets the content. */
|
||||
ContentApprox getContent() { result = c }
|
||||
|
||||
/** Gets the container type. */
|
||||
DataFlowType getContainerType() { result = t }
|
||||
|
||||
/** Gets a textual representation of this approximated content. */
|
||||
string toString() { result = c.toString() }
|
||||
}
|
||||
|
||||
/**
|
||||
* The front of an approximated access path. This is either a head or a nil.
|
||||
*/
|
||||
abstract class ApproxAccessPathFront extends TApproxAccessPathFront {
|
||||
abstract string toString();
|
||||
|
||||
abstract DataFlowType getType();
|
||||
|
||||
abstract boolean toBoolNonEmpty();
|
||||
|
||||
ContentApprox getHead() { this = TApproxFrontHead(result) }
|
||||
TypedContentApprox getHead() { this = TApproxFrontHead(result) }
|
||||
|
||||
pragma[nomagic]
|
||||
Content getAHead() {
|
||||
exists(ContentApprox cont |
|
||||
TypedContent getAHead() {
|
||||
exists(TypedContentApprox cont |
|
||||
this = TApproxFrontHead(cont) and
|
||||
cont = getContentApprox(result)
|
||||
result = cont.getATypedContent()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
class ApproxAccessPathFrontNil extends ApproxAccessPathFront, TApproxFrontNil {
|
||||
override string toString() { result = "nil" }
|
||||
private DataFlowType t;
|
||||
|
||||
ApproxAccessPathFrontNil() { this = TApproxFrontNil(t) }
|
||||
|
||||
override string toString() { result = ppReprType(t) }
|
||||
|
||||
override DataFlowType getType() { result = t }
|
||||
|
||||
override boolean toBoolNonEmpty() { result = false }
|
||||
}
|
||||
|
||||
class ApproxAccessPathFrontHead extends ApproxAccessPathFront, TApproxFrontHead {
|
||||
private ContentApprox c;
|
||||
private TypedContentApprox tc;
|
||||
|
||||
ApproxAccessPathFrontHead() { this = TApproxFrontHead(c) }
|
||||
ApproxAccessPathFrontHead() { this = TApproxFrontHead(tc) }
|
||||
|
||||
override string toString() { result = c.toString() }
|
||||
override string toString() { result = tc.toString() }
|
||||
|
||||
override DataFlowType getType() { result = tc.getContainerType() }
|
||||
|
||||
override boolean toBoolNonEmpty() { result = true }
|
||||
}
|
||||
@@ -1446,31 +1461,65 @@ class ApproxAccessPathFrontOption extends TApproxAccessPathFrontOption {
|
||||
}
|
||||
}
|
||||
|
||||
/** A `Content` tagged with the type of a containing object. */
|
||||
class TypedContent extends MkTypedContent {
|
||||
private Content c;
|
||||
private DataFlowType t;
|
||||
|
||||
TypedContent() { this = MkTypedContent(c, t) }
|
||||
|
||||
/** Gets the content. */
|
||||
Content getContent() { result = c }
|
||||
|
||||
/** Gets the container type. */
|
||||
DataFlowType getContainerType() { result = t }
|
||||
|
||||
/** Gets a textual representation of this content. */
|
||||
string toString() { result = c.toString() }
|
||||
|
||||
/**
|
||||
* Holds if access paths with this `TypedContent` at their head always should
|
||||
* be tracked at high precision. This disables adaptive access path precision
|
||||
* for such access paths.
|
||||
*/
|
||||
predicate forceHighPrecision() { forceHighPrecision(c) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The front of an access path. This is either a head or a nil.
|
||||
*/
|
||||
abstract class AccessPathFront extends TAccessPathFront {
|
||||
abstract string toString();
|
||||
|
||||
abstract DataFlowType getType();
|
||||
|
||||
abstract ApproxAccessPathFront toApprox();
|
||||
|
||||
Content getHead() { this = TFrontHead(result) }
|
||||
TypedContent getHead() { this = TFrontHead(result) }
|
||||
}
|
||||
|
||||
class AccessPathFrontNil extends AccessPathFront, TFrontNil {
|
||||
override string toString() { result = "nil" }
|
||||
private DataFlowType t;
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result = TApproxFrontNil() }
|
||||
AccessPathFrontNil() { this = TFrontNil(t) }
|
||||
|
||||
override string toString() { result = ppReprType(t) }
|
||||
|
||||
override DataFlowType getType() { result = t }
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result = TApproxFrontNil(t) }
|
||||
}
|
||||
|
||||
class AccessPathFrontHead extends AccessPathFront, TFrontHead {
|
||||
private Content c;
|
||||
private TypedContent tc;
|
||||
|
||||
AccessPathFrontHead() { this = TFrontHead(c) }
|
||||
AccessPathFrontHead() { this = TFrontHead(tc) }
|
||||
|
||||
override string toString() { result = c.toString() }
|
||||
override string toString() { result = tc.toString() }
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result.getAHead() = c }
|
||||
override DataFlowType getType() { result = tc.getContainerType() }
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result.getAHead() = tc }
|
||||
}
|
||||
|
||||
/** An optional access path front. */
|
||||
|
||||
@@ -607,21 +607,13 @@ OutNode getAnOutNode(DataFlowCall call, ReturnKind kind) {
|
||||
result.getReturnKind() = kind
|
||||
}
|
||||
|
||||
/** A variable that behaves like a global variable. */
|
||||
class GlobalLikeVariable extends Variable {
|
||||
GlobalLikeVariable() {
|
||||
this instanceof Cpp::GlobalOrNamespaceVariable or
|
||||
this instanceof Cpp::StaticLocalVariable
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if data can flow from `node1` to `node2` in a way that loses the
|
||||
* calling context. For example, this would happen with flow through a
|
||||
* global or static variable.
|
||||
*/
|
||||
predicate jumpStep(Node n1, Node n2) {
|
||||
exists(GlobalLikeVariable v |
|
||||
exists(Cpp::GlobalOrNamespaceVariable v |
|
||||
exists(Ssa::GlobalUse globalUse |
|
||||
v = globalUse.getVariable() and
|
||||
n1.(FinalGlobalValue).getGlobalUse() = globalUse
|
||||
|
||||
@@ -145,14 +145,14 @@ private newtype TDefOrUseImpl =
|
||||
or
|
||||
// Since the pruning stage doesn't know about global variables we can't use the above check to
|
||||
// rule out dead assignments to globals.
|
||||
base.(VariableAddressInstruction).getAstVariable() instanceof GlobalLikeVariable
|
||||
base.(VariableAddressInstruction).getAstVariable() instanceof Cpp::GlobalOrNamespaceVariable
|
||||
)
|
||||
} or
|
||||
TUseImpl(Operand operand, int indirectionIndex) {
|
||||
isUse(_, operand, _, _, indirectionIndex) and
|
||||
not isDef(_, _, operand, _, _, _)
|
||||
} or
|
||||
TGlobalUse(GlobalLikeVariable v, IRFunction f, int indirectionIndex) {
|
||||
TGlobalUse(Cpp::GlobalOrNamespaceVariable v, IRFunction f, int indirectionIndex) {
|
||||
// Represents a final "use" of a global variable to ensure that
|
||||
// the assignment to a global variable isn't ruled out as dead.
|
||||
exists(VariableAddressInstruction vai, int defIndex |
|
||||
@@ -162,7 +162,7 @@ private newtype TDefOrUseImpl =
|
||||
indirectionIndex = [0 .. defIndex] + 1
|
||||
)
|
||||
} or
|
||||
TGlobalDefImpl(GlobalLikeVariable v, IRFunction f, int indirectionIndex) {
|
||||
TGlobalDefImpl(Cpp::GlobalOrNamespaceVariable v, IRFunction f, int indirectionIndex) {
|
||||
// Represents the initial "definition" of a global variable when entering
|
||||
// a function body.
|
||||
exists(VariableAddressInstruction vai |
|
||||
@@ -458,7 +458,7 @@ class FinalParameterUse extends UseImpl, TFinalParameterUse {
|
||||
}
|
||||
|
||||
class GlobalUse extends UseImpl, TGlobalUse {
|
||||
GlobalLikeVariable global;
|
||||
Cpp::GlobalOrNamespaceVariable global;
|
||||
IRFunction f;
|
||||
|
||||
GlobalUse() { this = TGlobalUse(global, f, ind) }
|
||||
@@ -468,7 +468,7 @@ class GlobalUse extends UseImpl, TGlobalUse {
|
||||
override int getIndirection() { result = ind + 1 }
|
||||
|
||||
/** Gets the global variable associated with this use. */
|
||||
GlobalLikeVariable getVariable() { result = global }
|
||||
Cpp::GlobalOrNamespaceVariable getVariable() { result = global }
|
||||
|
||||
/** Gets the `IRFunction` whose body is exited from after this use. */
|
||||
IRFunction getIRFunction() { result = f }
|
||||
@@ -496,14 +496,14 @@ class GlobalUse extends UseImpl, TGlobalUse {
|
||||
}
|
||||
|
||||
class GlobalDefImpl extends DefOrUseImpl, TGlobalDefImpl {
|
||||
GlobalLikeVariable global;
|
||||
Cpp::GlobalOrNamespaceVariable global;
|
||||
IRFunction f;
|
||||
int indirectionIndex;
|
||||
|
||||
GlobalDefImpl() { this = TGlobalDefImpl(global, f, indirectionIndex) }
|
||||
|
||||
/** Gets the global variable associated with this definition. */
|
||||
GlobalLikeVariable getVariable() { result = global }
|
||||
Cpp::GlobalOrNamespaceVariable getVariable() { result = global }
|
||||
|
||||
/** Gets the `IRFunction` whose body is evaluated after this definition. */
|
||||
IRFunction getIRFunction() { result = f }
|
||||
@@ -760,14 +760,13 @@ private predicate variableWriteCand(IRBlock bb, int i, SourceVariable v) {
|
||||
}
|
||||
|
||||
private predicate sourceVariableIsGlobal(
|
||||
SourceVariable sv, GlobalLikeVariable global, IRFunction func, int indirectionIndex
|
||||
SourceVariable sv, Cpp::GlobalOrNamespaceVariable global, IRFunction func, int indirectionIndex
|
||||
) {
|
||||
exists(IRVariable irVar, BaseIRVariable base |
|
||||
sourceVariableHasBaseAndIndex(sv, base, indirectionIndex) and
|
||||
irVar = base.getIRVariable() and
|
||||
irVar.getEnclosingIRFunction() = func and
|
||||
global = irVar.getAst() and
|
||||
not irVar instanceof IRDynamicInitializationFlag
|
||||
global = irVar.getAst()
|
||||
)
|
||||
}
|
||||
|
||||
@@ -920,7 +919,7 @@ class GlobalDef extends TGlobalDef, SsaDefOrUse {
|
||||
IRFunction getIRFunction() { result = global.getIRFunction() }
|
||||
|
||||
/** Gets the global variable associated with this definition. */
|
||||
GlobalLikeVariable getVariable() { result = global.getVariable() }
|
||||
Cpp::GlobalOrNamespaceVariable getVariable() { result = global.getVariable() }
|
||||
}
|
||||
|
||||
class Phi extends TPhi, SsaDefOrUse {
|
||||
|
||||
@@ -34,9 +34,13 @@ private module Cached {
|
||||
|
||||
cached
|
||||
predicate hasUnreachedInstructionCached(IRFunction irFunc) {
|
||||
exists(OldInstruction oldInstruction |
|
||||
exists(OldIR::Instruction oldInstruction |
|
||||
irFunc = oldInstruction.getEnclosingIRFunction() and
|
||||
Reachability::isInfeasibleInstructionSuccessor(oldInstruction, _)
|
||||
(
|
||||
Reachability::isInfeasibleInstructionSuccessor(oldInstruction, _)
|
||||
or
|
||||
oldInstruction.getOpcode() instanceof Opcode::Unreached
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
@@ -366,21 +370,19 @@ private module Cached {
|
||||
then
|
||||
result = getChi(getOldInstruction(instruction)) and
|
||||
kind instanceof GotoEdge
|
||||
else (
|
||||
else
|
||||
exists(OldInstruction oldInstruction |
|
||||
oldInstruction = getOldInstruction(instruction) and
|
||||
(
|
||||
oldInstruction = getOldInstruction(instruction)
|
||||
or
|
||||
instruction = getChi(oldInstruction)
|
||||
) and
|
||||
(
|
||||
if Reachability::isInfeasibleInstructionSuccessor(oldInstruction, kind)
|
||||
then result = unreachedInstruction(instruction.getEnclosingIRFunction())
|
||||
else result = getNewInstruction(oldInstruction.getSuccessor(kind))
|
||||
)
|
||||
)
|
||||
or
|
||||
exists(OldInstruction oldInstruction |
|
||||
instruction = getChi(oldInstruction) and
|
||||
result = getNewInstruction(oldInstruction.getSuccessor(kind))
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
cached
|
||||
|
||||
@@ -6,7 +6,7 @@ private import IRFunctionBaseInternal
|
||||
|
||||
private newtype TIRFunction =
|
||||
TFunctionIRFunction(Language::Function func) { IRConstruction::Raw::functionHasIR(func) } or
|
||||
TVarInitIRFunction(Language::Variable var) { IRConstruction::Raw::varHasIRFunc(var) }
|
||||
TVarInitIRFunction(Language::GlobalVariable var) { IRConstruction::Raw::varHasIRFunc(var) }
|
||||
|
||||
/**
|
||||
* The IR for a function. This base class contains only the predicates that are the same between all
|
||||
|
||||
@@ -19,6 +19,9 @@ newtype TInstruction =
|
||||
) {
|
||||
IRConstruction::Raw::hasInstruction(tag1, tag2)
|
||||
} or
|
||||
TRawUnreachedInstruction(IRFunctionBase irFunc) {
|
||||
IRConstruction::hasUnreachedInstruction(irFunc)
|
||||
} or
|
||||
TUnaliasedSsaPhiInstruction(
|
||||
TRawInstruction blockStartInstr, UnaliasedSsa::Ssa::MemoryLocation memoryLocation
|
||||
) {
|
||||
|
||||
@@ -37,13 +37,7 @@ module Raw {
|
||||
predicate functionHasIR(Function func) { exists(getTranslatedFunction(func)) }
|
||||
|
||||
cached
|
||||
predicate varHasIRFunc(Variable var) {
|
||||
(
|
||||
var instanceof GlobalOrNamespaceVariable
|
||||
or
|
||||
not var.isFromUninstantiatedTemplate(_) and
|
||||
var instanceof StaticInitializedStaticLocalVariable
|
||||
) and
|
||||
predicate varHasIRFunc(GlobalOrNamespaceVariable var) {
|
||||
var.hasInitializer() and
|
||||
(
|
||||
not var.getType().isDeeplyConst()
|
||||
@@ -81,10 +75,9 @@ module Raw {
|
||||
}
|
||||
|
||||
cached
|
||||
predicate hasDynamicInitializationFlag(
|
||||
Function func, RuntimeInitializedStaticLocalVariable var, CppType type
|
||||
) {
|
||||
predicate hasDynamicInitializationFlag(Function func, StaticLocalVariable var, CppType type) {
|
||||
var.getFunction() = func and
|
||||
var.hasDynamicInitialization() and
|
||||
type = getBoolType()
|
||||
}
|
||||
|
||||
@@ -178,9 +171,9 @@ module Raw {
|
||||
}
|
||||
}
|
||||
|
||||
class TStageInstruction = TRawInstruction;
|
||||
class TStageInstruction = TRawInstruction or TRawUnreachedInstruction;
|
||||
|
||||
predicate hasInstruction(TRawInstruction instr) { any() }
|
||||
predicate hasInstruction(TStageInstruction instr) { any() }
|
||||
|
||||
predicate hasModeledMemoryResult(Instruction instruction) { none() }
|
||||
|
||||
@@ -368,6 +361,11 @@ private predicate isStrictlyForwardGoto(GotoStmt goto) {
|
||||
|
||||
Locatable getInstructionAst(TStageInstruction instr) {
|
||||
result = getInstructionTranslatedElement(instr).getAst()
|
||||
or
|
||||
exists(IRFunction irFunc |
|
||||
instr = TRawUnreachedInstruction(irFunc) and
|
||||
result = irFunc.getFunction()
|
||||
)
|
||||
}
|
||||
|
||||
/** DEPRECATED: Alias for getInstructionAst */
|
||||
@@ -377,14 +375,22 @@ deprecated Locatable getInstructionAST(TStageInstruction instr) {
|
||||
|
||||
CppType getInstructionResultType(TStageInstruction instr) {
|
||||
getInstructionTranslatedElement(instr).hasInstruction(_, getInstructionTag(instr), result)
|
||||
or
|
||||
instr instanceof TRawUnreachedInstruction and
|
||||
result = getVoidType()
|
||||
}
|
||||
|
||||
predicate getInstructionOpcode(Opcode opcode, TStageInstruction instr) {
|
||||
getInstructionTranslatedElement(instr).hasInstruction(opcode, getInstructionTag(instr), _)
|
||||
or
|
||||
instr instanceof TRawUnreachedInstruction and
|
||||
opcode instanceof Opcode::Unreached
|
||||
}
|
||||
|
||||
IRFunctionBase getInstructionEnclosingIRFunction(TStageInstruction instr) {
|
||||
result.getFunction() = getInstructionTranslatedElement(instr).getFunction()
|
||||
or
|
||||
instr = TRawUnreachedInstruction(result)
|
||||
}
|
||||
|
||||
Instruction getPrimaryInstructionForSideEffect(SideEffectInstruction instruction) {
|
||||
@@ -393,6 +399,16 @@ Instruction getPrimaryInstructionForSideEffect(SideEffectInstruction instruction
|
||||
.getPrimaryInstructionForSideEffect(getInstructionTag(instruction))
|
||||
}
|
||||
|
||||
predicate hasUnreachedInstruction(IRFunction func) {
|
||||
exists(Call c |
|
||||
c.getEnclosingFunction() = func.getFunction() and
|
||||
any(Options opt).exits(c.getTarget())
|
||||
) and
|
||||
not exists(TranslatedUnreachableReturnStmt return |
|
||||
return.getEnclosingFunction().getFunction() = func.getFunction()
|
||||
)
|
||||
}
|
||||
|
||||
import CachedForDebugging
|
||||
|
||||
cached
|
||||
|
||||
@@ -34,6 +34,7 @@ newtype TInstructionTag =
|
||||
CallTargetTag() or
|
||||
CallTag() or
|
||||
CallSideEffectTag() or
|
||||
CallNoReturnTag() or
|
||||
AllocationSizeTag() or
|
||||
AllocationElementSizeTag() or
|
||||
AllocationExtentConvertTag() or
|
||||
|
||||
@@ -8,6 +8,7 @@ private import SideEffects
|
||||
private import TranslatedElement
|
||||
private import TranslatedExpr
|
||||
private import TranslatedFunction
|
||||
private import DefaultOptions as DefaultOptions
|
||||
|
||||
/**
|
||||
* Gets the `CallInstruction` from the `TranslatedCallExpr` for the specified expression.
|
||||
@@ -66,7 +67,13 @@ abstract class TranslatedCall extends TranslatedExpr {
|
||||
)
|
||||
or
|
||||
child = getSideEffects() and
|
||||
result = getParent().getChildSuccessor(this)
|
||||
if this.isNoReturn()
|
||||
then
|
||||
result =
|
||||
any(UnreachedInstruction instr |
|
||||
this.getEnclosingFunction().getFunction() = instr.getEnclosingFunction()
|
||||
)
|
||||
else result = this.getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
@@ -161,6 +168,8 @@ abstract class TranslatedCall extends TranslatedExpr {
|
||||
*/
|
||||
abstract predicate hasArguments();
|
||||
|
||||
predicate isNoReturn() { none() }
|
||||
|
||||
final TranslatedSideEffects getSideEffects() { result.getExpr() = expr }
|
||||
}
|
||||
|
||||
@@ -180,7 +189,7 @@ abstract class TranslatedSideEffects extends TranslatedElement {
|
||||
/** DEPRECATED: Alias for getAst */
|
||||
deprecated override Locatable getAST() { result = getAst() }
|
||||
|
||||
final override Declaration getFunction() { result = getEnclosingDeclaration(getExpr()) }
|
||||
final override Declaration getFunction() { result = getExpr().getEnclosingDeclaration() }
|
||||
|
||||
final override TranslatedElement getChild(int i) {
|
||||
result =
|
||||
@@ -266,6 +275,8 @@ abstract class TranslatedCallExpr extends TranslatedNonConstantExpr, TranslatedC
|
||||
}
|
||||
|
||||
final override int getNumberOfArguments() { result = expr.getNumberOfArguments() }
|
||||
|
||||
final override predicate isNoReturn() { any(Options opt).exits(expr.getTarget()) }
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -28,11 +28,7 @@ abstract class TranslatedCondition extends TranslatedElement {
|
||||
|
||||
final Expr getExpr() { result = expr }
|
||||
|
||||
final override Declaration getFunction() {
|
||||
result = getEnclosingFunction(expr) or
|
||||
result = getEnclosingVariable(expr).(GlobalOrNamespaceVariable) or
|
||||
result = getEnclosingVariable(expr).(StaticInitializedStaticLocalVariable)
|
||||
}
|
||||
final override Function getFunction() { result = expr.getEnclosingFunction() }
|
||||
|
||||
final Type getResultType() { result = expr.getUnspecifiedType() }
|
||||
}
|
||||
|
||||
@@ -28,14 +28,9 @@ abstract class TranslatedDeclarationEntry extends TranslatedElement, TTranslated
|
||||
|
||||
TranslatedDeclarationEntry() { this = TTranslatedDeclarationEntry(entry) }
|
||||
|
||||
final override Declaration getFunction() {
|
||||
exists(DeclStmt stmt | stmt = entry.getStmt() |
|
||||
result = entry.getDeclaration().(StaticInitializedStaticLocalVariable)
|
||||
or
|
||||
result = entry.getDeclaration().(GlobalOrNamespaceVariable)
|
||||
or
|
||||
not entry.getDeclaration() instanceof StaticInitializedStaticLocalVariable and
|
||||
not entry.getDeclaration() instanceof GlobalOrNamespaceVariable and
|
||||
final override Function getFunction() {
|
||||
exists(DeclStmt stmt |
|
||||
stmt = entry.getStmt() and
|
||||
result = stmt.getEnclosingFunction()
|
||||
)
|
||||
}
|
||||
@@ -242,7 +237,7 @@ class TranslatedStaticLocalVariableInitialization extends TranslatedElement,
|
||||
|
||||
final override LocalVariable getVariable() { result = var }
|
||||
|
||||
final override Declaration getFunction() { result = var.getFunction() }
|
||||
final override Function getFunction() { result = var.getFunction() }
|
||||
}
|
||||
|
||||
TranslatedConditionDecl getTranslatedConditionDecl(ConditionDeclExpr expr) {
|
||||
@@ -269,7 +264,7 @@ class TranslatedConditionDecl extends TranslatedLocalVariableDeclaration, TTrans
|
||||
/** DEPRECATED: Alias for getAst */
|
||||
deprecated override Locatable getAST() { result = getAst() }
|
||||
|
||||
override Declaration getFunction() { result = getEnclosingFunction(conditionDeclExpr) }
|
||||
override Function getFunction() { result = conditionDeclExpr.getEnclosingFunction() }
|
||||
|
||||
override LocalVariable getVariable() { result = conditionDeclExpr.getVariable() }
|
||||
}
|
||||
|
||||
@@ -62,6 +62,15 @@ private predicate ignoreExprAndDescendants(Expr expr) {
|
||||
// constant value.
|
||||
isIRConstant(getRealParent(expr))
|
||||
or
|
||||
// Only translate the initializer of a static local if it uses run-time data.
|
||||
// Otherwise the initializer does not run in function scope.
|
||||
exists(Initializer init, StaticStorageDurationVariable var |
|
||||
init = var.getInitializer() and
|
||||
not var.hasDynamicInitialization() and
|
||||
expr = init.getExpr().getFullyConverted() and
|
||||
not var instanceof GlobalOrNamespaceVariable
|
||||
)
|
||||
or
|
||||
// Ignore descendants of `__assume` expressions, since we translated these to `NoOp`.
|
||||
getRealParent(expr) instanceof AssumeExpr
|
||||
or
|
||||
@@ -109,8 +118,8 @@ private predicate ignoreExprOnly(Expr expr) {
|
||||
// should not be translated.
|
||||
exists(NewOrNewArrayExpr new | expr = new.getAllocatorCall().getArgument(0))
|
||||
or
|
||||
not translateFunction(getEnclosingFunction(expr)) and
|
||||
not Raw::varHasIRFunc(getEnclosingVariable(expr))
|
||||
not translateFunction(expr.getEnclosingFunction()) and
|
||||
not Raw::varHasIRFunc(expr.getEnclosingVariable())
|
||||
or
|
||||
// We do not yet translate destructors properly, so for now we ignore the
|
||||
// destructor call. We do, however, translate the expression being
|
||||
@@ -429,17 +438,6 @@ predicate hasTranslatedSyntheticTemporaryObject(Expr expr) {
|
||||
not expr.hasLValueToRValueConversion()
|
||||
}
|
||||
|
||||
class StaticInitializedStaticLocalVariable extends StaticLocalVariable {
|
||||
StaticInitializedStaticLocalVariable() {
|
||||
this.hasInitializer() and
|
||||
not this.hasDynamicInitialization()
|
||||
}
|
||||
}
|
||||
|
||||
class RuntimeInitializedStaticLocalVariable extends StaticLocalVariable {
|
||||
RuntimeInitializedStaticLocalVariable() { this.hasDynamicInitialization() }
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if the specified `DeclarationEntry` needs an IR translation. An IR translation is only
|
||||
* necessary for automatic local variables, or for static local variables with dynamic
|
||||
@@ -455,7 +453,7 @@ private predicate translateDeclarationEntry(IRDeclarationEntry entry) {
|
||||
not var.isStatic()
|
||||
or
|
||||
// Ignore static variables unless they have a dynamic initializer.
|
||||
var instanceof RuntimeInitializedStaticLocalVariable
|
||||
var.(StaticLocalVariable).hasDynamicInitialization()
|
||||
)
|
||||
)
|
||||
}
|
||||
@@ -757,7 +755,7 @@ newtype TTranslatedElement =
|
||||
} or
|
||||
// The side effect that initializes newly-allocated memory.
|
||||
TTranslatedAllocationSideEffect(AllocationExpr expr) { not ignoreSideEffects(expr) } or
|
||||
TTranslatedStaticStorageDurationVarInit(Variable var) { Raw::varHasIRFunc(var) }
|
||||
TTranslatedGlobalOrNamespaceVarInit(GlobalOrNamespaceVariable var) { Raw::varHasIRFunc(var) }
|
||||
|
||||
/**
|
||||
* Gets the index of the first explicitly initialized element in `initList`
|
||||
@@ -821,7 +819,7 @@ abstract class TranslatedElement extends TTranslatedElement {
|
||||
abstract Locatable getAst();
|
||||
|
||||
/** DEPRECATED: Alias for getAst */
|
||||
deprecated Locatable getAST() { result = this.getAst() }
|
||||
deprecated Locatable getAST() { result = getAst() }
|
||||
|
||||
/**
|
||||
* Get the first instruction to be executed in the evaluation of this element.
|
||||
@@ -831,7 +829,7 @@ abstract class TranslatedElement extends TTranslatedElement {
|
||||
/**
|
||||
* Get the immediate child elements of this element.
|
||||
*/
|
||||
final TranslatedElement getAChild() { result = this.getChild(_) }
|
||||
final TranslatedElement getAChild() { result = getChild(_) }
|
||||
|
||||
/**
|
||||
* Gets the immediate child element of this element. The `id` is unique
|
||||
@@ -844,29 +842,25 @@ abstract class TranslatedElement extends TTranslatedElement {
|
||||
* Gets the an identifier string for the element. This id is unique within
|
||||
* the scope of the element's function.
|
||||
*/
|
||||
final int getId() { result = this.getUniqueId() }
|
||||
final int getId() { result = getUniqueId() }
|
||||
|
||||
private TranslatedElement getChildByRank(int rankIndex) {
|
||||
result =
|
||||
rank[rankIndex + 1](TranslatedElement child, int id |
|
||||
child = this.getChild(id)
|
||||
|
|
||||
child order by id
|
||||
)
|
||||
rank[rankIndex + 1](TranslatedElement child, int id | child = getChild(id) | child order by id)
|
||||
}
|
||||
|
||||
language[monotonicAggregates]
|
||||
private int getDescendantCount() {
|
||||
result =
|
||||
1 + sum(TranslatedElement child | child = this.getChildByRank(_) | child.getDescendantCount())
|
||||
1 + sum(TranslatedElement child | child = getChildByRank(_) | child.getDescendantCount())
|
||||
}
|
||||
|
||||
private int getUniqueId() {
|
||||
if not exists(this.getParent())
|
||||
if not exists(getParent())
|
||||
then result = 0
|
||||
else
|
||||
exists(TranslatedElement parent |
|
||||
parent = this.getParent() and
|
||||
parent = getParent() and
|
||||
if this = parent.getChildByRank(0)
|
||||
then result = 1 + parent.getUniqueId()
|
||||
else
|
||||
@@ -912,7 +906,7 @@ abstract class TranslatedElement extends TTranslatedElement {
|
||||
* there is no enclosing `try`.
|
||||
*/
|
||||
Instruction getExceptionSuccessorInstruction() {
|
||||
result = this.getParent().getExceptionSuccessorInstruction()
|
||||
result = getParent().getExceptionSuccessorInstruction()
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1026,14 +1020,14 @@ abstract class TranslatedElement extends TTranslatedElement {
|
||||
exists(Locatable ast |
|
||||
result.getAst() = ast and
|
||||
result.getTag() = tag and
|
||||
this.hasTempVariableAndAst(tag, ast)
|
||||
hasTempVariableAndAst(tag, ast)
|
||||
)
|
||||
}
|
||||
|
||||
pragma[noinline]
|
||||
private predicate hasTempVariableAndAst(TempVariableTag tag, Locatable ast) {
|
||||
this.hasTempVariable(tag, _) and
|
||||
ast = this.getAst()
|
||||
hasTempVariable(tag, _) and
|
||||
ast = getAst()
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1049,6 +1043,6 @@ abstract class TranslatedRootElement extends TranslatedElement {
|
||||
TranslatedRootElement() {
|
||||
this instanceof TTranslatedFunction
|
||||
or
|
||||
this instanceof TTranslatedStaticStorageDurationVarInit
|
||||
this instanceof TTranslatedGlobalOrNamespaceVarInit
|
||||
}
|
||||
}
|
||||
|
||||
@@ -79,7 +79,7 @@ abstract class TranslatedExpr extends TranslatedElement {
|
||||
/** DEPRECATED: Alias for getAst */
|
||||
deprecated override Locatable getAST() { result = this.getAst() }
|
||||
|
||||
final override Declaration getFunction() { result = getEnclosingDeclaration(expr) }
|
||||
final override Declaration getFunction() { result = expr.getEnclosingDeclaration() }
|
||||
|
||||
/**
|
||||
* Gets the expression from which this `TranslatedExpr` is generated.
|
||||
@@ -90,57 +90,12 @@ abstract class TranslatedExpr extends TranslatedElement {
|
||||
* Gets the `TranslatedFunction` containing this expression.
|
||||
*/
|
||||
final TranslatedRootElement getEnclosingFunction() {
|
||||
result = getTranslatedFunction(getEnclosingFunction(expr))
|
||||
result = getTranslatedFunction(expr.getEnclosingFunction())
|
||||
or
|
||||
result = getTranslatedVarInit(getEnclosingVariable(expr))
|
||||
result = getTranslatedVarInit(expr.getEnclosingVariable())
|
||||
}
|
||||
}
|
||||
|
||||
Function getEnclosingFunction(Expr e) {
|
||||
not exists(getEnclosingVariable(e)) and
|
||||
result = e.getEnclosingFunction()
|
||||
}
|
||||
|
||||
Declaration getEnclosingDeclaration0(Expr e) {
|
||||
result = getEnclosingDeclaration0(e.getParentWithConversions())
|
||||
or
|
||||
exists(Initializer i, Variable v |
|
||||
i.getExpr().getFullyConverted() = e and
|
||||
v = i.getDeclaration()
|
||||
|
|
||||
if v instanceof StaticInitializedStaticLocalVariable or v instanceof GlobalOrNamespaceVariable
|
||||
then result = v
|
||||
else result = e.getEnclosingDeclaration()
|
||||
)
|
||||
}
|
||||
|
||||
Declaration getEnclosingDeclaration(Expr e) {
|
||||
result = getEnclosingDeclaration0(e)
|
||||
or
|
||||
not exists(getEnclosingDeclaration0(e)) and
|
||||
result = e.getEnclosingDeclaration()
|
||||
}
|
||||
|
||||
Variable getEnclosingVariable0(Expr e) {
|
||||
result = getEnclosingVariable0(e.getParentWithConversions())
|
||||
or
|
||||
exists(Initializer i, Variable v |
|
||||
i.getExpr().getFullyConverted() = e and
|
||||
v = i.getDeclaration()
|
||||
|
|
||||
if v instanceof StaticInitializedStaticLocalVariable or v instanceof GlobalOrNamespaceVariable
|
||||
then result = v
|
||||
else result = e.getEnclosingVariable()
|
||||
)
|
||||
}
|
||||
|
||||
Variable getEnclosingVariable(Expr e) {
|
||||
result = getEnclosingVariable0(e)
|
||||
or
|
||||
not exists(getEnclosingVariable0(e)) and
|
||||
result = e.getEnclosingVariable()
|
||||
}
|
||||
|
||||
/**
|
||||
* The IR translation of the "core" part of an expression. This is the part of
|
||||
* the expression that produces the result value of the expression, before any
|
||||
@@ -888,21 +843,10 @@ class TranslatedNonFieldVariableAccess extends TranslatedVariableAccess {
|
||||
|
||||
override IRVariable getInstructionVariable(InstructionTag tag) {
|
||||
tag = OnlyInstructionTag() and
|
||||
exists(Declaration d, Variable v |
|
||||
accessHasEnclosingDeclarationAndVariable(d, v, expr) and
|
||||
result = getIRUserVariable(d, v)
|
||||
)
|
||||
result = getIRUserVariable(expr.getEnclosingDeclaration(), expr.getTarget())
|
||||
}
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate accessHasEnclosingDeclarationAndVariable(
|
||||
Declaration d, Variable v, VariableAccess va
|
||||
) {
|
||||
d = getEnclosingDeclaration(va) and
|
||||
v = va.getTarget()
|
||||
}
|
||||
|
||||
class TranslatedFieldAccess extends TranslatedVariableAccess {
|
||||
override FieldAccess expr;
|
||||
|
||||
@@ -2056,7 +2000,7 @@ class TranslatedDestructorFieldDestruction extends TranslatedNonConstantExpr, St
|
||||
final override Instruction getInstructionRegisterOperand(InstructionTag tag, OperandTag operandTag) {
|
||||
tag = OnlyInstructionTag() and
|
||||
operandTag instanceof UnaryOperandTag and
|
||||
result = getTranslatedFunction(getEnclosingFunction(expr)).getInitializeThisInstruction()
|
||||
result = getTranslatedFunction(expr.getEnclosingFunction()).getInitializeThisInstruction()
|
||||
}
|
||||
|
||||
final override Field getInstructionField(InstructionTag tag) {
|
||||
|
||||
@@ -322,13 +322,11 @@ class TranslatedFunction extends TranslatedRootElement, TTranslatedFunction {
|
||||
(
|
||||
var instanceof GlobalOrNamespaceVariable
|
||||
or
|
||||
var instanceof StaticLocalVariable
|
||||
or
|
||||
var instanceof MemberVariable and not var instanceof Field
|
||||
) and
|
||||
exists(VariableAccess access |
|
||||
access.getTarget() = var and
|
||||
getEnclosingFunction(access) = func
|
||||
access.getEnclosingFunction() = func
|
||||
)
|
||||
or
|
||||
var.(LocalScopeVariable).getFunction() = func
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import semmle.code.cpp.ir.implementation.raw.internal.TranslatedElement
|
||||
private import TranslatedExpr
|
||||
private import cpp
|
||||
private import semmle.code.cpp.ir.implementation.IRType
|
||||
private import semmle.code.cpp.ir.implementation.Opcode
|
||||
@@ -9,16 +8,16 @@ private import TranslatedInitialization
|
||||
private import InstructionTag
|
||||
private import semmle.code.cpp.ir.internal.IRUtilities
|
||||
|
||||
class TranslatedStaticStorageDurationVarInit extends TranslatedRootElement,
|
||||
TTranslatedStaticStorageDurationVarInit, InitializationContext
|
||||
class TranslatedGlobalOrNamespaceVarInit extends TranslatedRootElement,
|
||||
TTranslatedGlobalOrNamespaceVarInit, InitializationContext
|
||||
{
|
||||
Variable var;
|
||||
GlobalOrNamespaceVariable var;
|
||||
|
||||
TranslatedStaticStorageDurationVarInit() { this = TTranslatedStaticStorageDurationVarInit(var) }
|
||||
TranslatedGlobalOrNamespaceVarInit() { this = TTranslatedGlobalOrNamespaceVarInit(var) }
|
||||
|
||||
override string toString() { result = var.toString() }
|
||||
|
||||
final override Variable getAst() { result = var }
|
||||
final override GlobalOrNamespaceVariable getAst() { result = var }
|
||||
|
||||
final override Declaration getFunction() { result = var }
|
||||
|
||||
@@ -112,13 +111,11 @@ class TranslatedStaticStorageDurationVarInit extends TranslatedRootElement,
|
||||
(
|
||||
varUsed instanceof GlobalOrNamespaceVariable
|
||||
or
|
||||
varUsed instanceof StaticLocalVariable
|
||||
or
|
||||
varUsed instanceof MemberVariable and not varUsed instanceof Field
|
||||
) and
|
||||
exists(VariableAccess access |
|
||||
access.getTarget() = varUsed and
|
||||
getEnclosingVariable(access) = var
|
||||
access.getEnclosingVariable() = var
|
||||
)
|
||||
or
|
||||
var = varUsed
|
||||
@@ -131,4 +128,6 @@ class TranslatedStaticStorageDurationVarInit extends TranslatedRootElement,
|
||||
}
|
||||
}
|
||||
|
||||
TranslatedStaticStorageDurationVarInit getTranslatedVarInit(Variable var) { result.getAst() = var }
|
||||
TranslatedGlobalOrNamespaceVarInit getTranslatedVarInit(GlobalOrNamespaceVariable var) {
|
||||
result.getAst() = var
|
||||
}
|
||||
|
||||
@@ -35,64 +35,64 @@ abstract class InitializationContext extends TranslatedElement {
|
||||
* declarations, `return` statements, and `throw` expressions.
|
||||
*/
|
||||
abstract class TranslatedVariableInitialization extends TranslatedElement, InitializationContext {
|
||||
final override TranslatedElement getChild(int id) { id = 0 and result = this.getInitialization() }
|
||||
final override TranslatedElement getChild(int id) { id = 0 and result = getInitialization() }
|
||||
|
||||
final override Instruction getFirstInstruction() {
|
||||
result = this.getInstruction(InitializerVariableAddressTag())
|
||||
result = getInstruction(InitializerVariableAddressTag())
|
||||
}
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
tag = InitializerVariableAddressTag() and
|
||||
opcode instanceof Opcode::VariableAddress and
|
||||
resultType = getTypeForGLValue(this.getTargetType())
|
||||
resultType = getTypeForGLValue(getTargetType())
|
||||
or
|
||||
this.hasUninitializedInstruction() and
|
||||
hasUninitializedInstruction() and
|
||||
tag = InitializerStoreTag() and
|
||||
opcode instanceof Opcode::Uninitialized and
|
||||
resultType = getTypeForPRValue(this.getTargetType())
|
||||
resultType = getTypeForPRValue(getTargetType())
|
||||
}
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
(
|
||||
tag = InitializerVariableAddressTag() and
|
||||
kind instanceof GotoEdge and
|
||||
if this.hasUninitializedInstruction()
|
||||
then result = this.getInstruction(InitializerStoreTag())
|
||||
else result = this.getInitialization().getFirstInstruction()
|
||||
if hasUninitializedInstruction()
|
||||
then result = getInstruction(InitializerStoreTag())
|
||||
else result = getInitialization().getFirstInstruction()
|
||||
)
|
||||
or
|
||||
this.hasUninitializedInstruction() and
|
||||
hasUninitializedInstruction() and
|
||||
kind instanceof GotoEdge and
|
||||
tag = InitializerStoreTag() and
|
||||
(
|
||||
result = this.getInitialization().getFirstInstruction()
|
||||
result = getInitialization().getFirstInstruction()
|
||||
or
|
||||
not exists(this.getInitialization()) and result = this.getInitializationSuccessor()
|
||||
not exists(getInitialization()) and result = getInitializationSuccessor()
|
||||
)
|
||||
}
|
||||
|
||||
final override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getInitialization() and result = this.getInitializationSuccessor()
|
||||
child = getInitialization() and result = getInitializationSuccessor()
|
||||
}
|
||||
|
||||
override Instruction getInstructionRegisterOperand(InstructionTag tag, OperandTag operandTag) {
|
||||
this.hasUninitializedInstruction() and
|
||||
hasUninitializedInstruction() and
|
||||
tag = InitializerStoreTag() and
|
||||
operandTag instanceof AddressOperandTag and
|
||||
result = this.getInstruction(InitializerVariableAddressTag())
|
||||
result = getInstruction(InitializerVariableAddressTag())
|
||||
}
|
||||
|
||||
final override IRVariable getInstructionVariable(InstructionTag tag) {
|
||||
(
|
||||
tag = InitializerVariableAddressTag()
|
||||
or
|
||||
this.hasUninitializedInstruction() and tag = InitializerStoreTag()
|
||||
hasUninitializedInstruction() and tag = InitializerStoreTag()
|
||||
) and
|
||||
result = this.getIRVariable()
|
||||
result = getIRVariable()
|
||||
}
|
||||
|
||||
final override Instruction getTargetAddress() {
|
||||
result = this.getInstruction(InitializerVariableAddressTag())
|
||||
result = getInstruction(InitializerVariableAddressTag())
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -116,13 +116,13 @@ abstract class TranslatedVariableInitialization extends TranslatedElement, Initi
|
||||
*/
|
||||
final predicate hasUninitializedInstruction() {
|
||||
(
|
||||
not exists(this.getInitialization()) or
|
||||
this.getInitialization() instanceof TranslatedListInitialization or
|
||||
this.getInitialization() instanceof TranslatedConstructorInitialization or
|
||||
this.getInitialization().(TranslatedStringLiteralInitialization).zeroInitRange(_, _)
|
||||
not exists(getInitialization()) or
|
||||
getInitialization() instanceof TranslatedListInitialization or
|
||||
getInitialization() instanceof TranslatedConstructorInitialization or
|
||||
getInitialization().(TranslatedStringLiteralInitialization).zeroInitRange(_, _)
|
||||
) and
|
||||
// Variables with static or thread-local storage duration are zero-initialized at program startup.
|
||||
this.getIRVariable() instanceof IRAutomaticVariable
|
||||
getIRVariable() instanceof IRAutomaticVariable
|
||||
}
|
||||
}
|
||||
|
||||
@@ -138,15 +138,14 @@ abstract class TranslatedInitialization extends TranslatedElement, TTranslatedIn
|
||||
final override string toString() { result = "init: " + expr.toString() }
|
||||
|
||||
final override Declaration getFunction() {
|
||||
result = getEnclosingFunction(expr) or
|
||||
result = getEnclosingVariable(expr).(GlobalOrNamespaceVariable) or
|
||||
result = getEnclosingVariable(expr).(StaticInitializedStaticLocalVariable)
|
||||
result = expr.getEnclosingFunction() or
|
||||
result = expr.getEnclosingVariable().(GlobalOrNamespaceVariable)
|
||||
}
|
||||
|
||||
final override Locatable getAst() { result = expr }
|
||||
|
||||
/** DEPRECATED: Alias for getAst */
|
||||
deprecated override Locatable getAST() { result = this.getAst() }
|
||||
deprecated override Locatable getAST() { result = getAst() }
|
||||
|
||||
/**
|
||||
* Gets the expression that is doing the initialization.
|
||||
@@ -157,10 +156,10 @@ abstract class TranslatedInitialization extends TranslatedElement, TTranslatedIn
|
||||
* Gets the initialization context that describes the location being
|
||||
* initialized.
|
||||
*/
|
||||
final InitializationContext getContext() { result = this.getParent() }
|
||||
final InitializationContext getContext() { result = getParent() }
|
||||
|
||||
final TranslatedFunction getEnclosingFunction() {
|
||||
result = getTranslatedFunction(this.getFunction())
|
||||
result = getTranslatedFunction(expr.getEnclosingFunction())
|
||||
}
|
||||
}
|
||||
|
||||
@@ -169,17 +168,17 @@ abstract class TranslatedInitialization extends TranslatedElement, TTranslatedIn
|
||||
*/
|
||||
abstract class TranslatedListInitialization extends TranslatedInitialization, InitializationContext {
|
||||
override Instruction getFirstInstruction() {
|
||||
result = this.getChild(0).getFirstInstruction()
|
||||
result = getChild(0).getFirstInstruction()
|
||||
or
|
||||
not exists(this.getChild(0)) and result = this.getParent().getChildSuccessor(this)
|
||||
not exists(getChild(0)) and result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
exists(int index |
|
||||
child = this.getChild(index) and
|
||||
if exists(this.getChild(index + 1))
|
||||
then result = this.getChild(index + 1).getFirstInstruction()
|
||||
else result = this.getParent().getChildSuccessor(this)
|
||||
child = getChild(index) and
|
||||
if exists(getChild(index + 1))
|
||||
then result = getChild(index + 1).getFirstInstruction()
|
||||
else result = getParent().getChildSuccessor(this)
|
||||
)
|
||||
}
|
||||
|
||||
@@ -189,9 +188,9 @@ abstract class TranslatedListInitialization extends TranslatedInitialization, In
|
||||
|
||||
final override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) { none() }
|
||||
|
||||
override Instruction getTargetAddress() { result = this.getContext().getTargetAddress() }
|
||||
override Instruction getTargetAddress() { result = getContext().getTargetAddress() }
|
||||
|
||||
override Type getTargetType() { result = this.getContext().getTargetType() }
|
||||
override Type getTargetType() { result = getContext().getTargetType() }
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -237,11 +236,9 @@ class TranslatedArrayListInitialization extends TranslatedListInitialization {
|
||||
abstract class TranslatedDirectInitialization extends TranslatedInitialization {
|
||||
TranslatedDirectInitialization() { not expr instanceof AggregateLiteral }
|
||||
|
||||
override TranslatedElement getChild(int id) { id = 0 and result = this.getInitializer() }
|
||||
override TranslatedElement getChild(int id) { id = 0 and result = getInitializer() }
|
||||
|
||||
override Instruction getFirstInstruction() {
|
||||
result = this.getInitializer().getFirstInstruction()
|
||||
}
|
||||
override Instruction getFirstInstruction() { result = getInitializer().getFirstInstruction() }
|
||||
|
||||
final TranslatedExpr getInitializer() { result = getTranslatedExpr(expr) }
|
||||
}
|
||||
@@ -260,27 +257,27 @@ class TranslatedSimpleDirectInitialization extends TranslatedDirectInitializatio
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
tag = InitializerStoreTag() and
|
||||
opcode instanceof Opcode::Store and
|
||||
resultType = getTypeForPRValue(this.getContext().getTargetType())
|
||||
resultType = getTypeForPRValue(getContext().getTargetType())
|
||||
}
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
tag = InitializerStoreTag() and
|
||||
result = this.getParent().getChildSuccessor(this) and
|
||||
result = getParent().getChildSuccessor(this) and
|
||||
kind instanceof GotoEdge
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getInitializer() and result = this.getInstruction(InitializerStoreTag())
|
||||
child = getInitializer() and result = getInstruction(InitializerStoreTag())
|
||||
}
|
||||
|
||||
override Instruction getInstructionRegisterOperand(InstructionTag tag, OperandTag operandTag) {
|
||||
tag = InitializerStoreTag() and
|
||||
(
|
||||
operandTag instanceof AddressOperandTag and
|
||||
result = this.getContext().getTargetAddress()
|
||||
result = getContext().getTargetAddress()
|
||||
or
|
||||
operandTag instanceof StoreValueOperandTag and
|
||||
result = this.getInitializer().getResult()
|
||||
result = getInitializer().getResult()
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -307,13 +304,13 @@ class TranslatedStringLiteralInitialization extends TranslatedDirectInitializati
|
||||
// If the initializer string isn't large enough to fill the target, then
|
||||
// we have to generate another instruction sequence to store a constant
|
||||
// zero into the remainder of the array.
|
||||
this.zeroInitRange(_, elementCount) and
|
||||
zeroInitRange(_, elementCount) and
|
||||
(
|
||||
// Create a constant zero whose size is the size of the remaining
|
||||
// space in the target array.
|
||||
tag = ZeroPadStringConstantTag() and
|
||||
opcode instanceof Opcode::Constant and
|
||||
resultType = getUnknownOpaqueType(elementCount * this.getElementType().getSize())
|
||||
resultType = getUnknownOpaqueType(elementCount * getElementType().getSize())
|
||||
or
|
||||
// The index of the first element to be zero initialized.
|
||||
tag = ZeroPadStringElementIndexTag() and
|
||||
@@ -323,12 +320,12 @@ class TranslatedStringLiteralInitialization extends TranslatedDirectInitializati
|
||||
// Compute the address of the first element to be zero initialized.
|
||||
tag = ZeroPadStringElementAddressTag() and
|
||||
opcode instanceof Opcode::PointerAdd and
|
||||
resultType = getTypeForGLValue(this.getElementType())
|
||||
resultType = getTypeForGLValue(getElementType())
|
||||
or
|
||||
// Store the constant zero into the remainder of the string.
|
||||
tag = ZeroPadStringStoreTag() and
|
||||
opcode instanceof Opcode::Store and
|
||||
resultType = getUnknownOpaqueType(elementCount * this.getElementType().getSize())
|
||||
resultType = getUnknownOpaqueType(elementCount * getElementType().getSize())
|
||||
)
|
||||
)
|
||||
}
|
||||
@@ -337,78 +334,78 @@ class TranslatedStringLiteralInitialization extends TranslatedDirectInitializati
|
||||
kind instanceof GotoEdge and
|
||||
(
|
||||
tag = InitializerLoadStringTag() and
|
||||
result = this.getInstruction(InitializerStoreTag())
|
||||
result = getInstruction(InitializerStoreTag())
|
||||
or
|
||||
if this.zeroInitRange(_, _)
|
||||
if zeroInitRange(_, _)
|
||||
then (
|
||||
tag = InitializerStoreTag() and
|
||||
result = this.getInstruction(ZeroPadStringConstantTag())
|
||||
result = getInstruction(ZeroPadStringConstantTag())
|
||||
or
|
||||
tag = ZeroPadStringConstantTag() and
|
||||
result = this.getInstruction(ZeroPadStringElementIndexTag())
|
||||
result = getInstruction(ZeroPadStringElementIndexTag())
|
||||
or
|
||||
tag = ZeroPadStringElementIndexTag() and
|
||||
result = this.getInstruction(ZeroPadStringElementAddressTag())
|
||||
result = getInstruction(ZeroPadStringElementAddressTag())
|
||||
or
|
||||
tag = ZeroPadStringElementAddressTag() and
|
||||
result = this.getInstruction(ZeroPadStringStoreTag())
|
||||
result = getInstruction(ZeroPadStringStoreTag())
|
||||
or
|
||||
tag = ZeroPadStringStoreTag() and
|
||||
result = this.getParent().getChildSuccessor(this)
|
||||
result = getParent().getChildSuccessor(this)
|
||||
) else (
|
||||
tag = InitializerStoreTag() and
|
||||
result = this.getParent().getChildSuccessor(this)
|
||||
result = getParent().getChildSuccessor(this)
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getInitializer() and result = this.getInstruction(InitializerLoadStringTag())
|
||||
child = getInitializer() and result = getInstruction(InitializerLoadStringTag())
|
||||
}
|
||||
|
||||
override Instruction getInstructionRegisterOperand(InstructionTag tag, OperandTag operandTag) {
|
||||
tag = InitializerLoadStringTag() and
|
||||
(
|
||||
operandTag instanceof AddressOperandTag and
|
||||
result = this.getInitializer().getResult()
|
||||
result = getInitializer().getResult()
|
||||
)
|
||||
or
|
||||
tag = InitializerStoreTag() and
|
||||
(
|
||||
operandTag instanceof AddressOperandTag and
|
||||
result = this.getContext().getTargetAddress()
|
||||
result = getContext().getTargetAddress()
|
||||
or
|
||||
operandTag instanceof StoreValueOperandTag and
|
||||
result = this.getInstruction(InitializerLoadStringTag())
|
||||
result = getInstruction(InitializerLoadStringTag())
|
||||
)
|
||||
or
|
||||
tag = ZeroPadStringElementAddressTag() and
|
||||
(
|
||||
operandTag instanceof LeftOperandTag and
|
||||
result = this.getContext().getTargetAddress()
|
||||
result = getContext().getTargetAddress()
|
||||
or
|
||||
operandTag instanceof RightOperandTag and
|
||||
result = this.getInstruction(ZeroPadStringElementIndexTag())
|
||||
result = getInstruction(ZeroPadStringElementIndexTag())
|
||||
)
|
||||
or
|
||||
tag = ZeroPadStringStoreTag() and
|
||||
(
|
||||
operandTag instanceof AddressOperandTag and
|
||||
result = this.getInstruction(ZeroPadStringElementAddressTag())
|
||||
result = getInstruction(ZeroPadStringElementAddressTag())
|
||||
or
|
||||
operandTag instanceof StoreValueOperandTag and
|
||||
result = this.getInstruction(ZeroPadStringConstantTag())
|
||||
result = getInstruction(ZeroPadStringConstantTag())
|
||||
)
|
||||
}
|
||||
|
||||
override int getInstructionElementSize(InstructionTag tag) {
|
||||
tag = ZeroPadStringElementAddressTag() and
|
||||
result = max(this.getElementType().getSize())
|
||||
result = max(getElementType().getSize())
|
||||
}
|
||||
|
||||
override string getInstructionConstantValue(InstructionTag tag) {
|
||||
exists(int startIndex |
|
||||
this.zeroInitRange(startIndex, _) and
|
||||
zeroInitRange(startIndex, _) and
|
||||
(
|
||||
tag = ZeroPadStringConstantTag() and
|
||||
result = "0"
|
||||
@@ -421,13 +418,13 @@ class TranslatedStringLiteralInitialization extends TranslatedDirectInitializati
|
||||
|
||||
override predicate needsUnknownOpaqueType(int byteSize) {
|
||||
exists(int elementCount |
|
||||
this.zeroInitRange(_, elementCount) and
|
||||
byteSize = elementCount * this.getElementType().getSize()
|
||||
zeroInitRange(_, elementCount) and
|
||||
byteSize = elementCount * getElementType().getSize()
|
||||
)
|
||||
}
|
||||
|
||||
private Type getElementType() {
|
||||
result = this.getContext().getTargetType().getUnspecifiedType().(ArrayType).getBaseType()
|
||||
result = getContext().getTargetType().getUnspecifiedType().(ArrayType).getBaseType()
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -437,8 +434,7 @@ class TranslatedStringLiteralInitialization extends TranslatedDirectInitializati
|
||||
predicate zeroInitRange(int startIndex, int elementCount) {
|
||||
exists(int targetCount |
|
||||
startIndex = expr.getUnspecifiedType().(ArrayType).getArraySize() and
|
||||
targetCount =
|
||||
this.getContext().getTargetType().getUnspecifiedType().(ArrayType).getArraySize() and
|
||||
targetCount = getContext().getTargetType().getUnspecifiedType().(ArrayType).getArraySize() and
|
||||
elementCount = targetCount - startIndex and
|
||||
elementCount > 0
|
||||
)
|
||||
@@ -457,14 +453,14 @@ class TranslatedConstructorInitialization extends TranslatedDirectInitialization
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) { none() }
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getInitializer() and result = this.getParent().getChildSuccessor(this)
|
||||
child = getInitializer() and result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
override Instruction getInstructionRegisterOperand(InstructionTag tag, OperandTag operandTag) {
|
||||
none()
|
||||
}
|
||||
|
||||
override Instruction getReceiver() { result = this.getContext().getTargetAddress() }
|
||||
override Instruction getReceiver() { result = getContext().getTargetAddress() }
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -494,17 +490,14 @@ abstract class TranslatedFieldInitialization extends TranslatedElement {
|
||||
final override Locatable getAst() { result = ast }
|
||||
|
||||
/** DEPRECATED: Alias for getAst */
|
||||
deprecated override Locatable getAST() { result = this.getAst() }
|
||||
deprecated override Locatable getAST() { result = getAst() }
|
||||
|
||||
final override Declaration getFunction() {
|
||||
result = getEnclosingFunction(ast) or
|
||||
result = getEnclosingVariable(ast).(GlobalOrNamespaceVariable) or
|
||||
result = getEnclosingVariable(ast).(StaticInitializedStaticLocalVariable)
|
||||
result = ast.getEnclosingFunction() or
|
||||
result = ast.getEnclosingVariable().(GlobalOrNamespaceVariable)
|
||||
}
|
||||
|
||||
final override Instruction getFirstInstruction() {
|
||||
result = this.getInstruction(this.getFieldAddressTag())
|
||||
}
|
||||
final override Instruction getFirstInstruction() { result = getInstruction(getFieldAddressTag()) }
|
||||
|
||||
/**
|
||||
* Gets the zero-based index describing the order in which this field is to be
|
||||
@@ -513,19 +506,19 @@ abstract class TranslatedFieldInitialization extends TranslatedElement {
|
||||
final int getOrder() { result = field.getInitializationOrder() }
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
tag = this.getFieldAddressTag() and
|
||||
tag = getFieldAddressTag() and
|
||||
opcode instanceof Opcode::FieldAddress and
|
||||
resultType = getTypeForGLValue(field.getType())
|
||||
}
|
||||
|
||||
override Instruction getInstructionRegisterOperand(InstructionTag tag, OperandTag operandTag) {
|
||||
tag = this.getFieldAddressTag() and
|
||||
tag = getFieldAddressTag() and
|
||||
operandTag instanceof UnaryOperandTag and
|
||||
result = this.getParent().(InitializationContext).getTargetAddress()
|
||||
result = getParent().(InitializationContext).getTargetAddress()
|
||||
}
|
||||
|
||||
override Field getInstructionField(InstructionTag tag) {
|
||||
tag = this.getFieldAddressTag() and result = field
|
||||
tag = getFieldAddressTag() and result = field
|
||||
}
|
||||
|
||||
final InstructionTag getFieldAddressTag() { result = InitializerFieldAddressTag() }
|
||||
@@ -550,23 +543,21 @@ class TranslatedExplicitFieldInitialization extends TranslatedFieldInitializatio
|
||||
this = TTranslatedExplicitFieldInitialization(ast, field, expr, position)
|
||||
}
|
||||
|
||||
override Instruction getTargetAddress() {
|
||||
result = this.getInstruction(this.getFieldAddressTag())
|
||||
}
|
||||
override Instruction getTargetAddress() { result = getInstruction(getFieldAddressTag()) }
|
||||
|
||||
override Type getTargetType() { result = field.getUnspecifiedType() }
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
tag = this.getFieldAddressTag() and
|
||||
result = this.getInitialization().getFirstInstruction() and
|
||||
tag = getFieldAddressTag() and
|
||||
result = getInitialization().getFirstInstruction() and
|
||||
kind instanceof GotoEdge
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getInitialization() and result = this.getParent().getChildSuccessor(this)
|
||||
child = getInitialization() and result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
override TranslatedElement getChild(int id) { id = 0 and result = this.getInitialization() }
|
||||
override TranslatedElement getChild(int id) { id = 0 and result = getInitialization() }
|
||||
|
||||
private TranslatedInitialization getInitialization() {
|
||||
result = getTranslatedInitialization(expr)
|
||||
@@ -591,11 +582,11 @@ class TranslatedFieldValueInitialization extends TranslatedFieldInitialization,
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
TranslatedFieldInitialization.super.hasInstruction(opcode, tag, resultType)
|
||||
or
|
||||
tag = this.getFieldDefaultValueTag() and
|
||||
tag = getFieldDefaultValueTag() and
|
||||
opcode instanceof Opcode::Constant and
|
||||
resultType = getTypeForPRValue(field.getType())
|
||||
or
|
||||
tag = this.getFieldDefaultValueStoreTag() and
|
||||
tag = getFieldDefaultValueStoreTag() and
|
||||
opcode instanceof Opcode::Store and
|
||||
resultType = getTypeForPRValue(field.getUnspecifiedType())
|
||||
}
|
||||
@@ -603,32 +594,32 @@ class TranslatedFieldValueInitialization extends TranslatedFieldInitialization,
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
kind instanceof GotoEdge and
|
||||
(
|
||||
tag = this.getFieldAddressTag() and
|
||||
result = this.getInstruction(this.getFieldDefaultValueTag())
|
||||
tag = getFieldAddressTag() and
|
||||
result = getInstruction(getFieldDefaultValueTag())
|
||||
or
|
||||
tag = this.getFieldDefaultValueTag() and
|
||||
result = this.getInstruction(this.getFieldDefaultValueStoreTag())
|
||||
tag = getFieldDefaultValueTag() and
|
||||
result = getInstruction(getFieldDefaultValueStoreTag())
|
||||
or
|
||||
tag = this.getFieldDefaultValueStoreTag() and
|
||||
result = this.getParent().getChildSuccessor(this)
|
||||
tag = getFieldDefaultValueStoreTag() and
|
||||
result = getParent().getChildSuccessor(this)
|
||||
)
|
||||
}
|
||||
|
||||
override string getInstructionConstantValue(InstructionTag tag) {
|
||||
tag = this.getFieldDefaultValueTag() and
|
||||
tag = getFieldDefaultValueTag() and
|
||||
result = getZeroValue(field.getUnspecifiedType())
|
||||
}
|
||||
|
||||
override Instruction getInstructionRegisterOperand(InstructionTag tag, OperandTag operandTag) {
|
||||
result = TranslatedFieldInitialization.super.getInstructionRegisterOperand(tag, operandTag)
|
||||
or
|
||||
tag = this.getFieldDefaultValueStoreTag() and
|
||||
tag = getFieldDefaultValueStoreTag() and
|
||||
(
|
||||
operandTag instanceof AddressOperandTag and
|
||||
result = this.getInstruction(this.getFieldAddressTag())
|
||||
result = getInstruction(getFieldAddressTag())
|
||||
or
|
||||
operandTag instanceof StoreValueOperandTag and
|
||||
result = this.getInstruction(this.getFieldDefaultValueTag())
|
||||
result = getInstruction(getFieldDefaultValueTag())
|
||||
)
|
||||
}
|
||||
|
||||
@@ -651,61 +642,57 @@ abstract class TranslatedElementInitialization extends TranslatedElement {
|
||||
ArrayOrVectorAggregateLiteral initList;
|
||||
|
||||
final override string toString() {
|
||||
result = initList.toString() + "[" + this.getElementIndex().toString() + "]"
|
||||
result = initList.toString() + "[" + getElementIndex().toString() + "]"
|
||||
}
|
||||
|
||||
final override Locatable getAst() { result = initList }
|
||||
|
||||
/** DEPRECATED: Alias for getAst */
|
||||
deprecated override Locatable getAST() { result = this.getAst() }
|
||||
deprecated override Locatable getAST() { result = getAst() }
|
||||
|
||||
final override Declaration getFunction() {
|
||||
result = getEnclosingFunction(initList)
|
||||
result = initList.getEnclosingFunction()
|
||||
or
|
||||
result = getEnclosingVariable(initList).(GlobalOrNamespaceVariable)
|
||||
or
|
||||
result = getEnclosingVariable(initList).(StaticInitializedStaticLocalVariable)
|
||||
result = initList.getEnclosingVariable().(GlobalOrNamespaceVariable)
|
||||
}
|
||||
|
||||
final override Instruction getFirstInstruction() {
|
||||
result = this.getInstruction(this.getElementIndexTag())
|
||||
}
|
||||
final override Instruction getFirstInstruction() { result = getInstruction(getElementIndexTag()) }
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
tag = this.getElementIndexTag() and
|
||||
tag = getElementIndexTag() and
|
||||
opcode instanceof Opcode::Constant and
|
||||
resultType = getIntType()
|
||||
or
|
||||
tag = this.getElementAddressTag() and
|
||||
tag = getElementAddressTag() and
|
||||
opcode instanceof Opcode::PointerAdd and
|
||||
resultType = getTypeForGLValue(this.getElementType())
|
||||
resultType = getTypeForGLValue(getElementType())
|
||||
}
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
tag = this.getElementIndexTag() and
|
||||
result = this.getInstruction(this.getElementAddressTag()) and
|
||||
tag = getElementIndexTag() and
|
||||
result = getInstruction(getElementAddressTag()) and
|
||||
kind instanceof GotoEdge
|
||||
}
|
||||
|
||||
override Instruction getInstructionRegisterOperand(InstructionTag tag, OperandTag operandTag) {
|
||||
tag = this.getElementAddressTag() and
|
||||
tag = getElementAddressTag() and
|
||||
(
|
||||
operandTag instanceof LeftOperandTag and
|
||||
result = this.getParent().(InitializationContext).getTargetAddress()
|
||||
result = getParent().(InitializationContext).getTargetAddress()
|
||||
or
|
||||
operandTag instanceof RightOperandTag and
|
||||
result = this.getInstruction(this.getElementIndexTag())
|
||||
result = getInstruction(getElementIndexTag())
|
||||
)
|
||||
}
|
||||
|
||||
override int getInstructionElementSize(InstructionTag tag) {
|
||||
tag = this.getElementAddressTag() and
|
||||
result = max(this.getElementType().getSize())
|
||||
tag = getElementAddressTag() and
|
||||
result = max(getElementType().getSize())
|
||||
}
|
||||
|
||||
override string getInstructionConstantValue(InstructionTag tag) {
|
||||
tag = this.getElementIndexTag() and
|
||||
result = this.getElementIndex().toString()
|
||||
tag = getElementIndexTag() and
|
||||
result = getElementIndex().toString()
|
||||
}
|
||||
|
||||
abstract int getElementIndex();
|
||||
@@ -735,25 +722,23 @@ class TranslatedExplicitElementInitialization extends TranslatedElementInitializ
|
||||
this = TTranslatedExplicitElementInitialization(initList, elementIndex, position)
|
||||
}
|
||||
|
||||
override Instruction getTargetAddress() {
|
||||
result = this.getInstruction(this.getElementAddressTag())
|
||||
}
|
||||
override Instruction getTargetAddress() { result = getInstruction(getElementAddressTag()) }
|
||||
|
||||
override Type getTargetType() { result = this.getElementType() }
|
||||
override Type getTargetType() { result = getElementType() }
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
result = TranslatedElementInitialization.super.getInstructionSuccessor(tag, kind)
|
||||
or
|
||||
tag = this.getElementAddressTag() and
|
||||
result = this.getInitialization().getFirstInstruction() and
|
||||
tag = getElementAddressTag() and
|
||||
result = getInitialization().getFirstInstruction() and
|
||||
kind instanceof GotoEdge
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getInitialization() and result = this.getParent().getChildSuccessor(this)
|
||||
child = getInitialization() and result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
override TranslatedElement getChild(int id) { id = 0 and result = this.getInitialization() }
|
||||
override TranslatedElement getChild(int id) { id = 0 and result = getInitialization() }
|
||||
|
||||
override int getElementIndex() { result = elementIndex }
|
||||
|
||||
@@ -784,13 +769,13 @@ class TranslatedElementValueInitialization extends TranslatedElementInitializati
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
TranslatedElementInitialization.super.hasInstruction(opcode, tag, resultType)
|
||||
or
|
||||
tag = this.getElementDefaultValueTag() and
|
||||
tag = getElementDefaultValueTag() and
|
||||
opcode instanceof Opcode::Constant and
|
||||
resultType = this.getDefaultValueType()
|
||||
resultType = getDefaultValueType()
|
||||
or
|
||||
tag = this.getElementDefaultValueStoreTag() and
|
||||
tag = getElementDefaultValueStoreTag() and
|
||||
opcode instanceof Opcode::Store and
|
||||
resultType = this.getDefaultValueType()
|
||||
resultType = getDefaultValueType()
|
||||
}
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
@@ -798,34 +783,34 @@ class TranslatedElementValueInitialization extends TranslatedElementInitializati
|
||||
or
|
||||
kind instanceof GotoEdge and
|
||||
(
|
||||
tag = this.getElementAddressTag() and
|
||||
result = this.getInstruction(this.getElementDefaultValueTag())
|
||||
tag = getElementAddressTag() and
|
||||
result = getInstruction(getElementDefaultValueTag())
|
||||
or
|
||||
tag = this.getElementDefaultValueTag() and
|
||||
result = this.getInstruction(this.getElementDefaultValueStoreTag())
|
||||
tag = getElementDefaultValueTag() and
|
||||
result = getInstruction(getElementDefaultValueStoreTag())
|
||||
or
|
||||
tag = this.getElementDefaultValueStoreTag() and
|
||||
result = this.getParent().getChildSuccessor(this)
|
||||
tag = getElementDefaultValueStoreTag() and
|
||||
result = getParent().getChildSuccessor(this)
|
||||
)
|
||||
}
|
||||
|
||||
override string getInstructionConstantValue(InstructionTag tag) {
|
||||
result = TranslatedElementInitialization.super.getInstructionConstantValue(tag)
|
||||
or
|
||||
tag = this.getElementDefaultValueTag() and
|
||||
result = getZeroValue(this.getElementType())
|
||||
tag = getElementDefaultValueTag() and
|
||||
result = getZeroValue(getElementType())
|
||||
}
|
||||
|
||||
override Instruction getInstructionRegisterOperand(InstructionTag tag, OperandTag operandTag) {
|
||||
result = TranslatedElementInitialization.super.getInstructionRegisterOperand(tag, operandTag)
|
||||
or
|
||||
tag = this.getElementDefaultValueStoreTag() and
|
||||
tag = getElementDefaultValueStoreTag() and
|
||||
(
|
||||
operandTag instanceof AddressOperandTag and
|
||||
result = this.getInstruction(this.getElementAddressTag())
|
||||
result = getInstruction(getElementAddressTag())
|
||||
or
|
||||
operandTag instanceof StoreValueOperandTag and
|
||||
result = this.getInstruction(this.getElementDefaultValueTag())
|
||||
result = getInstruction(getElementDefaultValueTag())
|
||||
)
|
||||
}
|
||||
|
||||
@@ -836,7 +821,7 @@ class TranslatedElementValueInitialization extends TranslatedElementInitializati
|
||||
override int getElementIndex() { result = elementIndex }
|
||||
|
||||
override predicate needsUnknownOpaqueType(int byteSize) {
|
||||
elementCount != 0 and byteSize = elementCount * this.getElementType().getSize()
|
||||
elementCount != 0 and byteSize = elementCount * getElementType().getSize()
|
||||
}
|
||||
|
||||
private InstructionTag getElementDefaultValueTag() {
|
||||
@@ -849,8 +834,8 @@ class TranslatedElementValueInitialization extends TranslatedElementInitializati
|
||||
|
||||
private CppType getDefaultValueType() {
|
||||
if elementCount = 1
|
||||
then result = getTypeForPRValue(this.getElementType())
|
||||
else result = getUnknownOpaqueType(elementCount * this.getElementType().getSize())
|
||||
then result = getTypeForPRValue(getElementType())
|
||||
else result = getUnknownOpaqueType(elementCount * getElementType().getSize())
|
||||
}
|
||||
}
|
||||
|
||||
@@ -860,18 +845,18 @@ abstract class TranslatedStructorCallFromStructor extends TranslatedElement, Str
|
||||
final override Locatable getAst() { result = call }
|
||||
|
||||
/** DEPRECATED: Alias for getAst */
|
||||
deprecated override Locatable getAST() { result = this.getAst() }
|
||||
deprecated override Locatable getAST() { result = getAst() }
|
||||
|
||||
final override TranslatedElement getChild(int id) {
|
||||
id = 0 and
|
||||
result = this.getStructorCall()
|
||||
result = getStructorCall()
|
||||
}
|
||||
|
||||
final override Function getFunction() { result = getEnclosingFunction(call) }
|
||||
final override Function getFunction() { result = call.getEnclosingFunction() }
|
||||
|
||||
final override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getStructorCall() and
|
||||
result = this.getParent().getChildSuccessor(this)
|
||||
child = getStructorCall() and
|
||||
result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
final TranslatedExpr getStructorCall() { result = getTranslatedExpr(call) }
|
||||
@@ -882,9 +867,7 @@ abstract class TranslatedStructorCallFromStructor extends TranslatedElement, Str
|
||||
* destructor from within a derived class constructor or destructor.
|
||||
*/
|
||||
abstract class TranslatedBaseStructorCall extends TranslatedStructorCallFromStructor {
|
||||
final override Instruction getFirstInstruction() {
|
||||
result = this.getInstruction(OnlyInstructionTag())
|
||||
}
|
||||
final override Instruction getFirstInstruction() { result = getInstruction(OnlyInstructionTag()) }
|
||||
|
||||
final override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
tag = OnlyInstructionTag() and
|
||||
@@ -895,15 +878,15 @@ abstract class TranslatedBaseStructorCall extends TranslatedStructorCallFromStru
|
||||
final override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
tag = OnlyInstructionTag() and
|
||||
kind instanceof GotoEdge and
|
||||
result = this.getStructorCall().getFirstInstruction()
|
||||
result = getStructorCall().getFirstInstruction()
|
||||
}
|
||||
|
||||
final override Instruction getReceiver() { result = this.getInstruction(OnlyInstructionTag()) }
|
||||
final override Instruction getReceiver() { result = getInstruction(OnlyInstructionTag()) }
|
||||
|
||||
final override Instruction getInstructionRegisterOperand(InstructionTag tag, OperandTag operandTag) {
|
||||
tag = OnlyInstructionTag() and
|
||||
operandTag instanceof UnaryOperandTag and
|
||||
result = getTranslatedFunction(this.getFunction()).getInitializeThisInstruction()
|
||||
result = getTranslatedFunction(getFunction()).getInitializeThisInstruction()
|
||||
}
|
||||
|
||||
final override predicate getInstructionInheritance(
|
||||
@@ -911,7 +894,7 @@ abstract class TranslatedBaseStructorCall extends TranslatedStructorCallFromStru
|
||||
) {
|
||||
tag = OnlyInstructionTag() and
|
||||
baseClass = call.getTarget().getDeclaringType().getUnspecifiedType() and
|
||||
derivedClass = this.getFunction().getDeclaringType().getUnspecifiedType()
|
||||
derivedClass = getFunction().getDeclaringType().getUnspecifiedType()
|
||||
}
|
||||
}
|
||||
|
||||
@@ -937,7 +920,7 @@ class TranslatedConstructorDelegationInit extends TranslatedConstructorCallFromC
|
||||
final override string toString() { result = "delegation construct: " + call.toString() }
|
||||
|
||||
final override Instruction getFirstInstruction() {
|
||||
result = this.getStructorCall().getFirstInstruction()
|
||||
result = getStructorCall().getFirstInstruction()
|
||||
}
|
||||
|
||||
final override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
@@ -947,7 +930,7 @@ class TranslatedConstructorDelegationInit extends TranslatedConstructorCallFromC
|
||||
final override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) { none() }
|
||||
|
||||
final override Instruction getReceiver() {
|
||||
result = getTranslatedFunction(this.getFunction()).getInitializeThisInstruction()
|
||||
result = getTranslatedFunction(getFunction()).getInitializeThisInstruction()
|
||||
}
|
||||
}
|
||||
|
||||
@@ -994,11 +977,11 @@ class TranslatedConstructorBareInit extends TranslatedElement, TTranslatedConstr
|
||||
override Locatable getAst() { result = init }
|
||||
|
||||
/** DEPRECATED: Alias for getAst */
|
||||
deprecated override Locatable getAST() { result = this.getAst() }
|
||||
deprecated override Locatable getAST() { result = getAst() }
|
||||
|
||||
final override string toString() { result = "construct base (no constructor)" }
|
||||
|
||||
override Instruction getFirstInstruction() { result = this.getParent().getChildSuccessor(this) }
|
||||
override Instruction getFirstInstruction() { result = getParent().getChildSuccessor(this) }
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
none()
|
||||
@@ -1006,7 +989,7 @@ class TranslatedConstructorBareInit extends TranslatedElement, TTranslatedConstr
|
||||
|
||||
override TranslatedElement getChild(int id) { none() }
|
||||
|
||||
override Declaration getFunction() { result = this.getParent().getFunction() }
|
||||
override Function getFunction() { result = getParent().getFunction() }
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) { none() }
|
||||
|
||||
|
||||
@@ -240,7 +240,7 @@ abstract class TranslatedStmt extends TranslatedElement, TTranslatedStmt {
|
||||
final override Locatable getAst() { result = stmt }
|
||||
|
||||
/** DEPRECATED: Alias for getAst */
|
||||
deprecated override Locatable getAST() { result = this.getAst() }
|
||||
deprecated override Locatable getAST() { result = getAst() }
|
||||
|
||||
final override Function getFunction() { result = stmt.getEnclosingFunction() }
|
||||
}
|
||||
@@ -254,7 +254,7 @@ class TranslatedEmptyStmt extends TranslatedStmt {
|
||||
|
||||
override TranslatedElement getChild(int id) { none() }
|
||||
|
||||
override Instruction getFirstInstruction() { result = this.getInstruction(OnlyInstructionTag()) }
|
||||
override Instruction getFirstInstruction() { result = getInstruction(OnlyInstructionTag()) }
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
tag = OnlyInstructionTag() and
|
||||
@@ -264,7 +264,7 @@ class TranslatedEmptyStmt extends TranslatedStmt {
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
tag = OnlyInstructionTag() and
|
||||
result = this.getParent().getChildSuccessor(this) and
|
||||
result = getParent().getChildSuccessor(this) and
|
||||
kind instanceof GotoEdge
|
||||
}
|
||||
|
||||
@@ -279,19 +279,19 @@ class TranslatedEmptyStmt extends TranslatedStmt {
|
||||
class TranslatedDeclStmt extends TranslatedStmt {
|
||||
override DeclStmt stmt;
|
||||
|
||||
override TranslatedElement getChild(int id) { result = this.getDeclarationEntry(id) }
|
||||
override TranslatedElement getChild(int id) { result = getDeclarationEntry(id) }
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
none()
|
||||
}
|
||||
|
||||
override Instruction getFirstInstruction() {
|
||||
result = this.getDeclarationEntry(0).getFirstInstruction()
|
||||
result = getDeclarationEntry(0).getFirstInstruction()
|
||||
or
|
||||
not exists(this.getDeclarationEntry(0)) and result = this.getParent().getChildSuccessor(this)
|
||||
not exists(getDeclarationEntry(0)) and result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
private int getChildCount() { result = count(this.getDeclarationEntry(_)) }
|
||||
private int getChildCount() { result = count(getDeclarationEntry(_)) }
|
||||
|
||||
IRDeclarationEntry getIRDeclarationEntry(int index) {
|
||||
result.hasIndex(index) and
|
||||
@@ -319,10 +319,10 @@ class TranslatedDeclStmt extends TranslatedStmt {
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
exists(int index |
|
||||
child = this.getDeclarationEntry(index) and
|
||||
if index = (this.getChildCount() - 1)
|
||||
then result = this.getParent().getChildSuccessor(this)
|
||||
else result = this.getDeclarationEntry(index + 1).getFirstInstruction()
|
||||
child = getDeclarationEntry(index) and
|
||||
if index = (getChildCount() - 1)
|
||||
then result = getParent().getChildSuccessor(this)
|
||||
else result = getDeclarationEntry(index + 1).getFirstInstruction()
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -332,19 +332,19 @@ class TranslatedExprStmt extends TranslatedStmt {
|
||||
|
||||
TranslatedExpr getExpr() { result = getTranslatedExpr(stmt.getExpr().getFullyConverted()) }
|
||||
|
||||
override TranslatedElement getChild(int id) { id = 0 and result = this.getExpr() }
|
||||
override TranslatedElement getChild(int id) { id = 0 and result = getExpr() }
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
none()
|
||||
}
|
||||
|
||||
override Instruction getFirstInstruction() { result = this.getExpr().getFirstInstruction() }
|
||||
override Instruction getFirstInstruction() { result = getExpr().getFirstInstruction() }
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) { none() }
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getExpr() and
|
||||
result = this.getParent().getChildSuccessor(this)
|
||||
child = getExpr() and
|
||||
result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -363,18 +363,16 @@ class TranslatedReturnValueStmt extends TranslatedReturnStmt, TranslatedVariable
|
||||
TranslatedReturnValueStmt() { stmt.hasExpr() and hasReturnValue(stmt.getEnclosingFunction()) }
|
||||
|
||||
final override Instruction getInitializationSuccessor() {
|
||||
result = this.getEnclosingFunction().getReturnSuccessorInstruction()
|
||||
result = getEnclosingFunction().getReturnSuccessorInstruction()
|
||||
}
|
||||
|
||||
final override Type getTargetType() { result = this.getEnclosingFunction().getReturnType() }
|
||||
final override Type getTargetType() { result = getEnclosingFunction().getReturnType() }
|
||||
|
||||
final override TranslatedInitialization getInitialization() {
|
||||
result = getTranslatedInitialization(stmt.getExpr().getFullyConverted())
|
||||
}
|
||||
|
||||
final override IRVariable getIRVariable() {
|
||||
result = this.getEnclosingFunction().getReturnVariable()
|
||||
}
|
||||
final override IRVariable getIRVariable() { result = getEnclosingFunction().getReturnVariable() }
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -387,10 +385,10 @@ class TranslatedReturnVoidExpressionStmt extends TranslatedReturnStmt {
|
||||
|
||||
override TranslatedElement getChild(int id) {
|
||||
id = 0 and
|
||||
result = this.getExpr()
|
||||
result = getExpr()
|
||||
}
|
||||
|
||||
override Instruction getFirstInstruction() { result = this.getExpr().getFirstInstruction() }
|
||||
override Instruction getFirstInstruction() { result = getExpr().getFirstInstruction() }
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
tag = OnlyInstructionTag() and
|
||||
@@ -400,13 +398,13 @@ class TranslatedReturnVoidExpressionStmt extends TranslatedReturnStmt {
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
tag = OnlyInstructionTag() and
|
||||
result = this.getEnclosingFunction().getReturnSuccessorInstruction() and
|
||||
result = getEnclosingFunction().getReturnSuccessorInstruction() and
|
||||
kind instanceof GotoEdge
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getExpr() and
|
||||
result = this.getInstruction(OnlyInstructionTag())
|
||||
child = getExpr() and
|
||||
result = getInstruction(OnlyInstructionTag())
|
||||
}
|
||||
|
||||
private TranslatedExpr getExpr() { result = getTranslatedExpr(stmt.getExpr()) }
|
||||
@@ -423,7 +421,7 @@ class TranslatedReturnVoidStmt extends TranslatedReturnStmt {
|
||||
|
||||
override TranslatedElement getChild(int id) { none() }
|
||||
|
||||
override Instruction getFirstInstruction() { result = this.getInstruction(OnlyInstructionTag()) }
|
||||
override Instruction getFirstInstruction() { result = getInstruction(OnlyInstructionTag()) }
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
tag = OnlyInstructionTag() and
|
||||
@@ -433,7 +431,7 @@ class TranslatedReturnVoidStmt extends TranslatedReturnStmt {
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
tag = OnlyInstructionTag() and
|
||||
result = this.getEnclosingFunction().getReturnSuccessorInstruction() and
|
||||
result = getEnclosingFunction().getReturnSuccessorInstruction() and
|
||||
kind instanceof GotoEdge
|
||||
}
|
||||
|
||||
@@ -454,7 +452,7 @@ class TranslatedUnreachableReturnStmt extends TranslatedReturnStmt {
|
||||
|
||||
override TranslatedElement getChild(int id) { none() }
|
||||
|
||||
override Instruction getFirstInstruction() { result = this.getInstruction(OnlyInstructionTag()) }
|
||||
override Instruction getFirstInstruction() { result = getInstruction(OnlyInstructionTag()) }
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
tag = OnlyInstructionTag() and
|
||||
@@ -513,9 +511,9 @@ class TranslatedTryStmt extends TranslatedStmt {
|
||||
override TryOrMicrosoftTryStmt stmt;
|
||||
|
||||
override TranslatedElement getChild(int id) {
|
||||
id = 0 and result = this.getBody()
|
||||
id = 0 and result = getBody()
|
||||
or
|
||||
result = this.getHandler(id - 1)
|
||||
result = getHandler(id - 1)
|
||||
or
|
||||
id = stmt.getNumberOfCatchClauses() + 1 and
|
||||
result = this.getFinally()
|
||||
@@ -527,7 +525,7 @@ class TranslatedTryStmt extends TranslatedStmt {
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) { none() }
|
||||
|
||||
override Instruction getFirstInstruction() { result = this.getBody().getFirstInstruction() }
|
||||
override Instruction getFirstInstruction() { result = getBody().getFirstInstruction() }
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
// All non-finally children go to the successor of the `try` if
|
||||
@@ -548,19 +546,19 @@ class TranslatedTryStmt extends TranslatedStmt {
|
||||
|
||||
final Instruction getNextHandler(TranslatedHandler handler) {
|
||||
exists(int index |
|
||||
handler = this.getHandler(index) and
|
||||
result = this.getHandler(index + 1).getFirstInstruction()
|
||||
handler = getHandler(index) and
|
||||
result = getHandler(index + 1).getFirstInstruction()
|
||||
)
|
||||
or
|
||||
// The last catch clause flows to the exception successor of the parent
|
||||
// of the `try`, because the exception successor of the `try` itself is
|
||||
// the first catch clause.
|
||||
handler = this.getHandler(stmt.getNumberOfCatchClauses() - 1) and
|
||||
result = this.getParent().getExceptionSuccessorInstruction()
|
||||
handler = getHandler(stmt.getNumberOfCatchClauses() - 1) and
|
||||
result = getParent().getExceptionSuccessorInstruction()
|
||||
}
|
||||
|
||||
final override Instruction getExceptionSuccessorInstruction() {
|
||||
result = this.getHandler(0).getFirstInstruction()
|
||||
result = getHandler(0).getFirstInstruction()
|
||||
}
|
||||
|
||||
private TranslatedElement getHandler(int index) { result = stmt.getTranslatedHandler(index) }
|
||||
@@ -573,19 +571,19 @@ class TranslatedTryStmt extends TranslatedStmt {
|
||||
class TranslatedBlock extends TranslatedStmt {
|
||||
override BlockStmt stmt;
|
||||
|
||||
override TranslatedElement getChild(int id) { result = this.getStmt(id) }
|
||||
override TranslatedElement getChild(int id) { result = getStmt(id) }
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
this.isEmpty() and
|
||||
isEmpty() and
|
||||
opcode instanceof Opcode::NoOp and
|
||||
tag = OnlyInstructionTag() and
|
||||
resultType = getVoidType()
|
||||
}
|
||||
|
||||
override Instruction getFirstInstruction() {
|
||||
if this.isEmpty()
|
||||
then result = this.getInstruction(OnlyInstructionTag())
|
||||
else result = this.getStmt(0).getFirstInstruction()
|
||||
if isEmpty()
|
||||
then result = getInstruction(OnlyInstructionTag())
|
||||
else result = getStmt(0).getFirstInstruction()
|
||||
}
|
||||
|
||||
private predicate isEmpty() { not exists(stmt.getStmt(0)) }
|
||||
@@ -596,16 +594,16 @@ class TranslatedBlock extends TranslatedStmt {
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
tag = OnlyInstructionTag() and
|
||||
result = this.getParent().getChildSuccessor(this) and
|
||||
result = getParent().getChildSuccessor(this) and
|
||||
kind instanceof GotoEdge
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
exists(int index |
|
||||
child = this.getStmt(index) and
|
||||
if index = (this.getStmtCount() - 1)
|
||||
then result = this.getParent().getChildSuccessor(this)
|
||||
else result = this.getStmt(index + 1).getFirstInstruction()
|
||||
child = getStmt(index) and
|
||||
if index = (getStmtCount() - 1)
|
||||
then result = getParent().getChildSuccessor(this)
|
||||
else result = getStmt(index + 1).getFirstInstruction()
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -616,18 +614,18 @@ class TranslatedBlock extends TranslatedStmt {
|
||||
abstract class TranslatedHandler extends TranslatedStmt {
|
||||
override Handler stmt;
|
||||
|
||||
override TranslatedElement getChild(int id) { id = 1 and result = this.getBlock() }
|
||||
override TranslatedElement getChild(int id) { id = 1 and result = getBlock() }
|
||||
|
||||
override Instruction getFirstInstruction() { result = this.getInstruction(CatchTag()) }
|
||||
override Instruction getFirstInstruction() { result = getInstruction(CatchTag()) }
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getBlock() and result = this.getParent().getChildSuccessor(this)
|
||||
child = getBlock() and result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
override Instruction getExceptionSuccessorInstruction() {
|
||||
// A throw from within a `catch` block flows to the handler for the parent of
|
||||
// the `try`.
|
||||
result = this.getParent().getParent().getExceptionSuccessorInstruction()
|
||||
result = getParent().getParent().getExceptionSuccessorInstruction()
|
||||
}
|
||||
|
||||
TranslatedStmt getBlock() { result = getTranslatedStmt(stmt.getBlock()) }
|
||||
@@ -649,23 +647,23 @@ class TranslatedCatchByTypeHandler extends TranslatedHandler {
|
||||
override TranslatedElement getChild(int id) {
|
||||
result = super.getChild(id)
|
||||
or
|
||||
id = 0 and result = this.getParameter()
|
||||
id = 0 and result = getParameter()
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
result = super.getChildSuccessor(child)
|
||||
or
|
||||
child = this.getParameter() and result = this.getBlock().getFirstInstruction()
|
||||
child = getParameter() and result = getBlock().getFirstInstruction()
|
||||
}
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
tag = CatchTag() and
|
||||
(
|
||||
kind instanceof GotoEdge and
|
||||
result = this.getParameter().getFirstInstruction()
|
||||
result = getParameter().getFirstInstruction()
|
||||
or
|
||||
kind instanceof ExceptionEdge and
|
||||
result = this.getParent().(TranslatedTryStmt).getNextHandler(this)
|
||||
result = getParent().(TranslatedTryStmt).getNextHandler(this)
|
||||
)
|
||||
}
|
||||
|
||||
@@ -694,7 +692,7 @@ class TranslatedCatchAnyHandler extends TranslatedHandler {
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
tag = CatchTag() and
|
||||
kind instanceof GotoEdge and
|
||||
result = this.getBlock().getFirstInstruction()
|
||||
result = getBlock().getFirstInstruction()
|
||||
}
|
||||
}
|
||||
|
||||
@@ -702,19 +700,19 @@ class TranslatedIfStmt extends TranslatedStmt, ConditionContext {
|
||||
override IfStmt stmt;
|
||||
|
||||
override Instruction getFirstInstruction() {
|
||||
if this.hasInitialization()
|
||||
then result = this.getInitialization().getFirstInstruction()
|
||||
else result = this.getFirstConditionInstruction()
|
||||
if hasInitialization()
|
||||
then result = getInitialization().getFirstInstruction()
|
||||
else result = getFirstConditionInstruction()
|
||||
}
|
||||
|
||||
override TranslatedElement getChild(int id) {
|
||||
id = 0 and result = this.getInitialization()
|
||||
id = 0 and result = getInitialization()
|
||||
or
|
||||
id = 1 and result = this.getCondition()
|
||||
id = 1 and result = getCondition()
|
||||
or
|
||||
id = 2 and result = this.getThen()
|
||||
id = 2 and result = getThen()
|
||||
or
|
||||
id = 3 and result = this.getElse()
|
||||
id = 3 and result = getElse()
|
||||
}
|
||||
|
||||
private predicate hasInitialization() { exists(stmt.getInitialization()) }
|
||||
@@ -728,7 +726,7 @@ class TranslatedIfStmt extends TranslatedStmt, ConditionContext {
|
||||
}
|
||||
|
||||
private Instruction getFirstConditionInstruction() {
|
||||
result = this.getCondition().getFirstInstruction()
|
||||
result = getCondition().getFirstInstruction()
|
||||
}
|
||||
|
||||
private TranslatedStmt getThen() { result = getTranslatedStmt(stmt.getThen()) }
|
||||
@@ -740,23 +738,23 @@ class TranslatedIfStmt extends TranslatedStmt, ConditionContext {
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) { none() }
|
||||
|
||||
override Instruction getChildTrueSuccessor(TranslatedCondition child) {
|
||||
child = this.getCondition() and
|
||||
result = this.getThen().getFirstInstruction()
|
||||
child = getCondition() and
|
||||
result = getThen().getFirstInstruction()
|
||||
}
|
||||
|
||||
override Instruction getChildFalseSuccessor(TranslatedCondition child) {
|
||||
child = this.getCondition() and
|
||||
if this.hasElse()
|
||||
then result = this.getElse().getFirstInstruction()
|
||||
else result = this.getParent().getChildSuccessor(this)
|
||||
child = getCondition() and
|
||||
if hasElse()
|
||||
then result = getElse().getFirstInstruction()
|
||||
else result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getInitialization() and
|
||||
result = this.getFirstConditionInstruction()
|
||||
child = getInitialization() and
|
||||
result = getFirstConditionInstruction()
|
||||
or
|
||||
(child = this.getThen() or child = this.getElse()) and
|
||||
result = this.getParent().getChildSuccessor(this)
|
||||
(child = getThen() or child = getElse()) and
|
||||
result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
@@ -774,17 +772,17 @@ abstract class TranslatedLoop extends TranslatedStmt, ConditionContext {
|
||||
final TranslatedStmt getBody() { result = getTranslatedStmt(stmt.getStmt()) }
|
||||
|
||||
final Instruction getFirstConditionInstruction() {
|
||||
if this.hasCondition()
|
||||
then result = this.getCondition().getFirstInstruction()
|
||||
else result = this.getBody().getFirstInstruction()
|
||||
if hasCondition()
|
||||
then result = getCondition().getFirstInstruction()
|
||||
else result = getBody().getFirstInstruction()
|
||||
}
|
||||
|
||||
final predicate hasCondition() { exists(stmt.getCondition()) }
|
||||
|
||||
override TranslatedElement getChild(int id) {
|
||||
id = 0 and result = this.getCondition()
|
||||
id = 0 and result = getCondition()
|
||||
or
|
||||
id = 1 and result = this.getBody()
|
||||
id = 1 and result = getBody()
|
||||
}
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
@@ -794,31 +792,31 @@ abstract class TranslatedLoop extends TranslatedStmt, ConditionContext {
|
||||
final override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) { none() }
|
||||
|
||||
final override Instruction getChildTrueSuccessor(TranslatedCondition child) {
|
||||
child = this.getCondition() and result = this.getBody().getFirstInstruction()
|
||||
child = getCondition() and result = getBody().getFirstInstruction()
|
||||
}
|
||||
|
||||
final override Instruction getChildFalseSuccessor(TranslatedCondition child) {
|
||||
child = this.getCondition() and result = this.getParent().getChildSuccessor(this)
|
||||
child = getCondition() and result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
}
|
||||
|
||||
class TranslatedWhileStmt extends TranslatedLoop {
|
||||
TranslatedWhileStmt() { stmt instanceof WhileStmt }
|
||||
|
||||
override Instruction getFirstInstruction() { result = this.getFirstConditionInstruction() }
|
||||
override Instruction getFirstInstruction() { result = getFirstConditionInstruction() }
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getBody() and result = this.getFirstConditionInstruction()
|
||||
child = getBody() and result = getFirstConditionInstruction()
|
||||
}
|
||||
}
|
||||
|
||||
class TranslatedDoStmt extends TranslatedLoop {
|
||||
TranslatedDoStmt() { stmt instanceof DoStmt }
|
||||
|
||||
override Instruction getFirstInstruction() { result = this.getBody().getFirstInstruction() }
|
||||
override Instruction getFirstInstruction() { result = getBody().getFirstInstruction() }
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getBody() and result = this.getFirstConditionInstruction()
|
||||
child = getBody() and result = getFirstConditionInstruction()
|
||||
}
|
||||
}
|
||||
|
||||
@@ -826,13 +824,13 @@ class TranslatedForStmt extends TranslatedLoop {
|
||||
override ForStmt stmt;
|
||||
|
||||
override TranslatedElement getChild(int id) {
|
||||
id = 0 and result = this.getInitialization()
|
||||
id = 0 and result = getInitialization()
|
||||
or
|
||||
id = 1 and result = this.getCondition()
|
||||
id = 1 and result = getCondition()
|
||||
or
|
||||
id = 2 and result = this.getUpdate()
|
||||
id = 2 and result = getUpdate()
|
||||
or
|
||||
id = 3 and result = this.getBody()
|
||||
id = 3 and result = getBody()
|
||||
}
|
||||
|
||||
private TranslatedStmt getInitialization() {
|
||||
@@ -846,23 +844,23 @@ class TranslatedForStmt extends TranslatedLoop {
|
||||
private predicate hasUpdate() { exists(stmt.getUpdate()) }
|
||||
|
||||
override Instruction getFirstInstruction() {
|
||||
if this.hasInitialization()
|
||||
then result = this.getInitialization().getFirstInstruction()
|
||||
else result = this.getFirstConditionInstruction()
|
||||
if hasInitialization()
|
||||
then result = getInitialization().getFirstInstruction()
|
||||
else result = getFirstConditionInstruction()
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getInitialization() and
|
||||
result = this.getFirstConditionInstruction()
|
||||
child = getInitialization() and
|
||||
result = getFirstConditionInstruction()
|
||||
or
|
||||
(
|
||||
child = this.getBody() and
|
||||
if this.hasUpdate()
|
||||
then result = this.getUpdate().getFirstInstruction()
|
||||
else result = this.getFirstConditionInstruction()
|
||||
child = getBody() and
|
||||
if hasUpdate()
|
||||
then result = getUpdate().getFirstInstruction()
|
||||
else result = getFirstConditionInstruction()
|
||||
)
|
||||
or
|
||||
child = this.getUpdate() and result = this.getFirstConditionInstruction()
|
||||
child = getUpdate() and result = getFirstConditionInstruction()
|
||||
}
|
||||
}
|
||||
|
||||
@@ -877,39 +875,39 @@ class TranslatedRangeBasedForStmt extends TranslatedStmt, ConditionContext {
|
||||
override RangeBasedForStmt stmt;
|
||||
|
||||
override TranslatedElement getChild(int id) {
|
||||
id = 0 and result = this.getRangeVariableDeclStmt()
|
||||
id = 0 and result = getRangeVariableDeclStmt()
|
||||
or
|
||||
// Note: `__begin` and `__end` are declared by the same `DeclStmt`
|
||||
id = 1 and result = this.getBeginEndVariableDeclStmt()
|
||||
id = 1 and result = getBeginEndVariableDeclStmt()
|
||||
or
|
||||
id = 2 and result = this.getCondition()
|
||||
id = 2 and result = getCondition()
|
||||
or
|
||||
id = 3 and result = this.getUpdate()
|
||||
id = 3 and result = getUpdate()
|
||||
or
|
||||
id = 4 and result = this.getVariableDeclStmt()
|
||||
id = 4 and result = getVariableDeclStmt()
|
||||
or
|
||||
id = 5 and result = this.getBody()
|
||||
id = 5 and result = getBody()
|
||||
}
|
||||
|
||||
override Instruction getFirstInstruction() {
|
||||
result = this.getRangeVariableDeclStmt().getFirstInstruction()
|
||||
result = getRangeVariableDeclStmt().getFirstInstruction()
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getRangeVariableDeclStmt() and
|
||||
result = this.getBeginEndVariableDeclStmt().getFirstInstruction()
|
||||
child = getRangeVariableDeclStmt() and
|
||||
result = getBeginEndVariableDeclStmt().getFirstInstruction()
|
||||
or
|
||||
child = this.getBeginEndVariableDeclStmt() and
|
||||
result = this.getCondition().getFirstInstruction()
|
||||
child = getBeginEndVariableDeclStmt() and
|
||||
result = getCondition().getFirstInstruction()
|
||||
or
|
||||
child = this.getVariableDeclStmt() and
|
||||
result = this.getBody().getFirstInstruction()
|
||||
child = getVariableDeclStmt() and
|
||||
result = getBody().getFirstInstruction()
|
||||
or
|
||||
child = this.getBody() and
|
||||
result = this.getUpdate().getFirstInstruction()
|
||||
child = getBody() and
|
||||
result = getUpdate().getFirstInstruction()
|
||||
or
|
||||
child = this.getUpdate() and
|
||||
result = this.getCondition().getFirstInstruction()
|
||||
child = getUpdate() and
|
||||
result = getCondition().getFirstInstruction()
|
||||
}
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
@@ -919,11 +917,11 @@ class TranslatedRangeBasedForStmt extends TranslatedStmt, ConditionContext {
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) { none() }
|
||||
|
||||
override Instruction getChildTrueSuccessor(TranslatedCondition child) {
|
||||
child = this.getCondition() and result = this.getVariableDeclStmt().getFirstInstruction()
|
||||
child = getCondition() and result = getVariableDeclStmt().getFirstInstruction()
|
||||
}
|
||||
|
||||
override Instruction getChildFalseSuccessor(TranslatedCondition child) {
|
||||
child = this.getCondition() and result = this.getParent().getChildSuccessor(this)
|
||||
child = getCondition() and result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
private TranslatedDeclStmt getRangeVariableDeclStmt() {
|
||||
@@ -963,7 +961,7 @@ class TranslatedRangeBasedForStmt extends TranslatedStmt, ConditionContext {
|
||||
class TranslatedJumpStmt extends TranslatedStmt {
|
||||
override JumpStmt stmt;
|
||||
|
||||
override Instruction getFirstInstruction() { result = this.getInstruction(OnlyInstructionTag()) }
|
||||
override Instruction getFirstInstruction() { result = getInstruction(OnlyInstructionTag()) }
|
||||
|
||||
override TranslatedElement getChild(int id) { none() }
|
||||
|
||||
@@ -998,22 +996,22 @@ class TranslatedSwitchStmt extends TranslatedStmt {
|
||||
result = getTranslatedExpr(stmt.getExpr().getFullyConverted())
|
||||
}
|
||||
|
||||
private Instruction getFirstExprInstruction() { result = this.getExpr().getFirstInstruction() }
|
||||
private Instruction getFirstExprInstruction() { result = getExpr().getFirstInstruction() }
|
||||
|
||||
private TranslatedStmt getBody() { result = getTranslatedStmt(stmt.getStmt()) }
|
||||
|
||||
override Instruction getFirstInstruction() {
|
||||
if this.hasInitialization()
|
||||
then result = this.getInitialization().getFirstInstruction()
|
||||
else result = this.getFirstExprInstruction()
|
||||
if hasInitialization()
|
||||
then result = getInitialization().getFirstInstruction()
|
||||
else result = getFirstExprInstruction()
|
||||
}
|
||||
|
||||
override TranslatedElement getChild(int id) {
|
||||
id = 0 and result = this.getInitialization()
|
||||
id = 0 and result = getInitialization()
|
||||
or
|
||||
id = 1 and result = this.getExpr()
|
||||
id = 1 and result = getExpr()
|
||||
or
|
||||
id = 2 and result = this.getBody()
|
||||
id = 2 and result = getBody()
|
||||
}
|
||||
|
||||
private predicate hasInitialization() { exists(stmt.getInitialization()) }
|
||||
@@ -1031,7 +1029,7 @@ class TranslatedSwitchStmt extends TranslatedStmt {
|
||||
override Instruction getInstructionRegisterOperand(InstructionTag tag, OperandTag operandTag) {
|
||||
tag = SwitchBranchTag() and
|
||||
operandTag instanceof ConditionOperandTag and
|
||||
result = this.getExpr().getResult()
|
||||
result = getExpr().getResult()
|
||||
}
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
@@ -1045,15 +1043,15 @@ class TranslatedSwitchStmt extends TranslatedStmt {
|
||||
not stmt.hasDefaultCase() and
|
||||
tag = SwitchBranchTag() and
|
||||
kind instanceof DefaultEdge and
|
||||
result = this.getParent().getChildSuccessor(this)
|
||||
result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
child = this.getInitialization() and result = this.getFirstExprInstruction()
|
||||
child = getInitialization() and result = getFirstExprInstruction()
|
||||
or
|
||||
child = this.getExpr() and result = this.getInstruction(SwitchBranchTag())
|
||||
child = getExpr() and result = getInstruction(SwitchBranchTag())
|
||||
or
|
||||
child = this.getBody() and result = this.getParent().getChildSuccessor(this)
|
||||
child = getBody() and result = getParent().getChildSuccessor(this)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1065,9 +1063,9 @@ class TranslatedAsmStmt extends TranslatedStmt {
|
||||
}
|
||||
|
||||
override Instruction getFirstInstruction() {
|
||||
if exists(this.getChild(0))
|
||||
then result = this.getChild(0).getFirstInstruction()
|
||||
else result = this.getInstruction(AsmTag())
|
||||
if exists(getChild(0))
|
||||
then result = getChild(0).getFirstInstruction()
|
||||
else result = getInstruction(AsmTag())
|
||||
}
|
||||
|
||||
override predicate hasInstruction(Opcode opcode, InstructionTag tag, CppType resultType) {
|
||||
@@ -1080,7 +1078,7 @@ class TranslatedAsmStmt extends TranslatedStmt {
|
||||
exists(int index |
|
||||
tag = AsmTag() and
|
||||
operandTag = asmOperand(index) and
|
||||
result = this.getChild(index).getResult()
|
||||
result = getChild(index).getResult()
|
||||
)
|
||||
}
|
||||
|
||||
@@ -1094,16 +1092,16 @@ class TranslatedAsmStmt extends TranslatedStmt {
|
||||
|
||||
override Instruction getInstructionSuccessor(InstructionTag tag, EdgeKind kind) {
|
||||
tag = AsmTag() and
|
||||
result = this.getParent().getChildSuccessor(this) and
|
||||
result = getParent().getChildSuccessor(this) and
|
||||
kind instanceof GotoEdge
|
||||
}
|
||||
|
||||
override Instruction getChildSuccessor(TranslatedElement child) {
|
||||
exists(int index |
|
||||
child = this.getChild(index) and
|
||||
if exists(this.getChild(index + 1))
|
||||
then result = this.getChild(index + 1).getFirstInstruction()
|
||||
else result = this.getInstruction(AsmTag())
|
||||
child = getChild(index) and
|
||||
if exists(getChild(index + 1))
|
||||
then result = getChild(index + 1).getFirstInstruction()
|
||||
else result = getInstruction(AsmTag())
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7,6 +7,9 @@ predicate isInfeasibleInstructionSuccessor(Instruction instr, EdgeKind kind) {
|
||||
conditionValue = getConstantValue(instr.(ConditionalBranchInstruction).getCondition()) and
|
||||
if conditionValue = 0 then kind instanceof TrueEdge else kind instanceof FalseEdge
|
||||
)
|
||||
or
|
||||
instr.getSuccessor(kind) instanceof UnreachedInstruction and
|
||||
kind instanceof GotoEdge
|
||||
}
|
||||
|
||||
pragma[noinline]
|
||||
@@ -41,7 +44,9 @@ class ReachableBlock extends IRBlockBase {
|
||||
* An instruction that is contained in a reachable block.
|
||||
*/
|
||||
class ReachableInstruction extends Instruction {
|
||||
ReachableInstruction() { this.getBlock() instanceof ReachableBlock }
|
||||
ReachableInstruction() {
|
||||
this.getBlock() instanceof ReachableBlock and not this instanceof UnreachedInstruction
|
||||
}
|
||||
}
|
||||
|
||||
module Graph {
|
||||
|
||||
@@ -34,9 +34,13 @@ private module Cached {
|
||||
|
||||
cached
|
||||
predicate hasUnreachedInstructionCached(IRFunction irFunc) {
|
||||
exists(OldInstruction oldInstruction |
|
||||
exists(OldIR::Instruction oldInstruction |
|
||||
irFunc = oldInstruction.getEnclosingIRFunction() and
|
||||
Reachability::isInfeasibleInstructionSuccessor(oldInstruction, _)
|
||||
(
|
||||
Reachability::isInfeasibleInstructionSuccessor(oldInstruction, _)
|
||||
or
|
||||
oldInstruction.getOpcode() instanceof Opcode::Unreached
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
@@ -366,21 +370,19 @@ private module Cached {
|
||||
then
|
||||
result = getChi(getOldInstruction(instruction)) and
|
||||
kind instanceof GotoEdge
|
||||
else (
|
||||
else
|
||||
exists(OldInstruction oldInstruction |
|
||||
oldInstruction = getOldInstruction(instruction) and
|
||||
(
|
||||
oldInstruction = getOldInstruction(instruction)
|
||||
or
|
||||
instruction = getChi(oldInstruction)
|
||||
) and
|
||||
(
|
||||
if Reachability::isInfeasibleInstructionSuccessor(oldInstruction, kind)
|
||||
then result = unreachedInstruction(instruction.getEnclosingIRFunction())
|
||||
else result = getNewInstruction(oldInstruction.getSuccessor(kind))
|
||||
)
|
||||
)
|
||||
or
|
||||
exists(OldInstruction oldInstruction |
|
||||
instruction = getChi(oldInstruction) and
|
||||
result = getNewInstruction(oldInstruction.getSuccessor(kind))
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
cached
|
||||
|
||||
@@ -7,6 +7,9 @@ predicate isInfeasibleInstructionSuccessor(Instruction instr, EdgeKind kind) {
|
||||
conditionValue = getConstantValue(instr.(ConditionalBranchInstruction).getCondition()) and
|
||||
if conditionValue = 0 then kind instanceof TrueEdge else kind instanceof FalseEdge
|
||||
)
|
||||
or
|
||||
instr.getSuccessor(kind) instanceof UnreachedInstruction and
|
||||
kind instanceof GotoEdge
|
||||
}
|
||||
|
||||
pragma[noinline]
|
||||
@@ -41,7 +44,9 @@ class ReachableBlock extends IRBlockBase {
|
||||
* An instruction that is contained in a reachable block.
|
||||
*/
|
||||
class ReachableInstruction extends Instruction {
|
||||
ReachableInstruction() { this.getBlock() instanceof ReachableBlock }
|
||||
ReachableInstruction() {
|
||||
this.getBlock() instanceof ReachableBlock and not this instanceof UnreachedInstruction
|
||||
}
|
||||
}
|
||||
|
||||
module Graph {
|
||||
|
||||
@@ -47,7 +47,7 @@ class Variable = Cpp::Variable;
|
||||
|
||||
class AutomaticVariable = Cpp::StackVariable;
|
||||
|
||||
class StaticVariable = Cpp::StaticStorageDurationVariable;
|
||||
class StaticVariable = Cpp::Variable;
|
||||
|
||||
class GlobalVariable = Cpp::GlobalOrNamespaceVariable;
|
||||
|
||||
|
||||
@@ -1,9 +1,3 @@
|
||||
private import cpp
|
||||
private import semmle.code.cpp.Print as Print
|
||||
|
||||
string getIdentityString(Declaration decl) {
|
||||
if decl instanceof StaticLocalVariable
|
||||
then
|
||||
exists(StaticLocalVariable v | v = decl | result = v.getType().toString() + " " + v.getName())
|
||||
else result = Print::getIdentityString(decl)
|
||||
}
|
||||
predicate getIdentityString = Print::getIdentityString/1;
|
||||
|
||||
@@ -1,10 +1,3 @@
|
||||
## 0.6.1
|
||||
|
||||
### New Queries
|
||||
|
||||
* A new query `cpp/double-free` has been added. The query finds possible cases of deallocating the same pointer twice. The precision of the query has been set to "medium".
|
||||
* The query `cpp/use-after-free` has been modernized and assigned the precision "medium". The query finds cases of where a pointer is dereferenced after its memory has been deallocated.
|
||||
|
||||
## 0.6.0
|
||||
|
||||
### New Queries
|
||||
|
||||
4
cpp/ql/src/change-notes/2023-04-11-double-free.md
Normal file
4
cpp/ql/src/change-notes/2023-04-11-double-free.md
Normal file
@@ -0,0 +1,4 @@
|
||||
---
|
||||
category: newQuery
|
||||
---
|
||||
* A new query `cpp/double-free` has been added. The query finds possible cases of deallocating the same pointer twice. The precision of the query has been set to "medium".
|
||||
4
cpp/ql/src/change-notes/2023-04-11-use-after-free.md
Normal file
4
cpp/ql/src/change-notes/2023-04-11-use-after-free.md
Normal file
@@ -0,0 +1,4 @@
|
||||
---
|
||||
category: newQuery
|
||||
---
|
||||
* The query `cpp/use-after-free` has been modernized and assigned the precision "medium". The query finds cases of where a pointer is dereferenced after its memory has been deallocated.
|
||||
@@ -1,6 +0,0 @@
|
||||
## 0.6.1
|
||||
|
||||
### New Queries
|
||||
|
||||
* A new query `cpp/double-free` has been added. The query finds possible cases of deallocating the same pointer twice. The precision of the query has been set to "medium".
|
||||
* The query `cpp/use-after-free` has been modernized and assigned the precision "medium". The query finds cases of where a pointer is dereferenced after its memory has been deallocated.
|
||||
@@ -1,2 +1,2 @@
|
||||
---
|
||||
lastReleaseVersion: 0.6.1
|
||||
lastReleaseVersion: 0.6.0
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
name: codeql/cpp-queries
|
||||
version: 0.6.2-dev
|
||||
version: 0.6.1-dev
|
||||
groups:
|
||||
- cpp
|
||||
- queries
|
||||
|
||||
@@ -209,9 +209,6 @@ edges
|
||||
| test.cpp:207:17:207:19 | str indirection [string] | test.cpp:207:22:207:27 | string |
|
||||
| test.cpp:207:17:207:19 | str indirection [string] | test.cpp:207:22:207:27 | string indirection |
|
||||
| test.cpp:207:22:207:27 | string indirection | test.cpp:207:22:207:27 | string |
|
||||
| test.cpp:214:24:214:24 | p | test.cpp:216:10:216:10 | p |
|
||||
| test.cpp:220:43:220:48 | call to malloc | test.cpp:222:15:222:20 | buffer |
|
||||
| test.cpp:222:15:222:20 | buffer | test.cpp:214:24:214:24 | p |
|
||||
nodes
|
||||
| test.cpp:16:11:16:21 | mk_string_t indirection [string] | semmle.label | mk_string_t indirection [string] |
|
||||
| test.cpp:18:5:18:30 | ... = ... | semmle.label | ... = ... |
|
||||
@@ -377,10 +374,6 @@ nodes
|
||||
| test.cpp:207:17:207:19 | str indirection [string] | semmle.label | str indirection [string] |
|
||||
| test.cpp:207:22:207:27 | string | semmle.label | string |
|
||||
| test.cpp:207:22:207:27 | string indirection | semmle.label | string indirection |
|
||||
| test.cpp:214:24:214:24 | p | semmle.label | p |
|
||||
| test.cpp:216:10:216:10 | p | semmle.label | p |
|
||||
| test.cpp:220:43:220:48 | call to malloc | semmle.label | call to malloc |
|
||||
| test.cpp:222:15:222:20 | buffer | semmle.label | buffer |
|
||||
subpaths
|
||||
#select
|
||||
| test.cpp:42:5:42:11 | call to strncpy | test.cpp:18:19:18:24 | call to malloc | test.cpp:42:18:42:23 | string | This write may overflow $@ by 1 element. | test.cpp:42:18:42:23 | string | string |
|
||||
@@ -398,4 +391,3 @@ subpaths
|
||||
| test.cpp:199:9:199:15 | call to strncpy | test.cpp:147:19:147:24 | call to malloc | test.cpp:199:22:199:27 | string | This write may overflow $@ by 2 elements. | test.cpp:199:22:199:27 | string | string |
|
||||
| test.cpp:203:9:203:15 | call to strncpy | test.cpp:147:19:147:24 | call to malloc | test.cpp:203:22:203:27 | string | This write may overflow $@ by 2 elements. | test.cpp:203:22:203:27 | string | string |
|
||||
| test.cpp:207:9:207:15 | call to strncpy | test.cpp:147:19:147:24 | call to malloc | test.cpp:207:22:207:27 | string | This write may overflow $@ by 3 elements. | test.cpp:207:22:207:27 | string | string |
|
||||
| test.cpp:216:3:216:8 | call to memset | test.cpp:220:43:220:48 | call to malloc | test.cpp:216:10:216:10 | p | This write may overflow $@ by 5 elements. | test.cpp:216:10:216:10 | p | p |
|
||||
|
||||
@@ -208,16 +208,3 @@ void test5(unsigned size, char *buf, unsigned anotherSize) {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void *memset(void *, int, unsigned);
|
||||
|
||||
void call_memset(void *p, unsigned size)
|
||||
{
|
||||
memset(p, 0, size); // GOOD [FALSE POSITIVE]
|
||||
}
|
||||
|
||||
void test_missing_call_context(unsigned char *unrelated_buffer, unsigned size) {
|
||||
unsigned char* buffer = (unsigned char*)malloc(size);
|
||||
call_memset(unrelated_buffer, size + 5);
|
||||
call_memset(buffer, size);
|
||||
}
|
||||
@@ -575,129 +575,6 @@ edges
|
||||
| test.cpp:213:6:213:6 | q | test.cpp:213:5:213:13 | Store: ... = ... |
|
||||
| test.cpp:213:6:213:6 | q | test.cpp:213:5:213:13 | Store: ... = ... |
|
||||
| test.cpp:221:17:221:22 | call to malloc | test.cpp:222:5:222:5 | p |
|
||||
| test.cpp:231:18:231:30 | new[] | test.cpp:232:3:232:9 | newname |
|
||||
| test.cpp:232:3:232:9 | newname | test.cpp:232:3:232:16 | access to array |
|
||||
| test.cpp:232:3:232:16 | access to array | test.cpp:232:3:232:20 | Store: ... = ... |
|
||||
| test.cpp:238:20:238:32 | new[] | test.cpp:239:5:239:11 | newname |
|
||||
| test.cpp:239:5:239:11 | newname | test.cpp:239:5:239:18 | access to array |
|
||||
| test.cpp:239:5:239:18 | access to array | test.cpp:239:5:239:22 | Store: ... = ... |
|
||||
| test.cpp:248:24:248:30 | call to realloc | test.cpp:249:9:249:9 | p |
|
||||
| test.cpp:248:24:248:30 | call to realloc | test.cpp:250:22:250:22 | p |
|
||||
| test.cpp:248:24:248:30 | call to realloc | test.cpp:254:9:254:9 | p |
|
||||
| test.cpp:254:9:254:9 | p | test.cpp:254:9:254:12 | access to array |
|
||||
| test.cpp:254:9:254:12 | access to array | test.cpp:254:9:254:16 | Store: ... = ... |
|
||||
| test.cpp:260:13:260:24 | new[] | test.cpp:261:14:261:15 | xs |
|
||||
| test.cpp:261:14:261:15 | xs | test.cpp:261:14:261:21 | ... + ... |
|
||||
| test.cpp:261:14:261:15 | xs | test.cpp:261:14:261:21 | ... + ... |
|
||||
| test.cpp:261:14:261:15 | xs | test.cpp:261:14:261:21 | ... + ... |
|
||||
| test.cpp:261:14:261:15 | xs | test.cpp:261:14:261:21 | ... + ... |
|
||||
| test.cpp:261:14:261:15 | xs | test.cpp:262:26:262:28 | end |
|
||||
| test.cpp:261:14:261:15 | xs | test.cpp:262:26:262:28 | end |
|
||||
| test.cpp:261:14:261:15 | xs | test.cpp:262:31:262:31 | x |
|
||||
| test.cpp:261:14:261:15 | xs | test.cpp:262:31:262:33 | ... ++ |
|
||||
| test.cpp:261:14:261:15 | xs | test.cpp:262:31:262:33 | ... ++ |
|
||||
| test.cpp:261:14:261:15 | xs | test.cpp:264:14:264:14 | x |
|
||||
| test.cpp:261:14:261:15 | xs | test.cpp:264:14:264:14 | x |
|
||||
| test.cpp:261:14:261:21 | ... + ... | test.cpp:261:14:261:21 | ... + ... |
|
||||
| test.cpp:261:14:261:21 | ... + ... | test.cpp:261:14:261:21 | ... + ... |
|
||||
| test.cpp:261:14:261:21 | ... + ... | test.cpp:262:26:262:28 | end |
|
||||
| test.cpp:261:14:261:21 | ... + ... | test.cpp:262:26:262:28 | end |
|
||||
| test.cpp:261:14:261:21 | ... + ... | test.cpp:262:26:262:28 | end |
|
||||
| test.cpp:261:14:261:21 | ... + ... | test.cpp:262:26:262:28 | end |
|
||||
| test.cpp:261:14:261:21 | ... + ... | test.cpp:264:13:264:14 | Load: * ... |
|
||||
| test.cpp:261:14:261:21 | ... + ... | test.cpp:264:13:264:14 | Load: * ... |
|
||||
| test.cpp:261:14:261:21 | ... + ... | test.cpp:264:13:264:14 | Load: * ... |
|
||||
| test.cpp:261:14:261:21 | ... + ... | test.cpp:264:13:264:14 | Load: * ... |
|
||||
| test.cpp:262:21:262:21 | x | test.cpp:264:13:264:14 | Load: * ... |
|
||||
| test.cpp:262:26:262:28 | end | test.cpp:262:26:262:28 | end |
|
||||
| test.cpp:262:26:262:28 | end | test.cpp:262:26:262:28 | end |
|
||||
| test.cpp:262:26:262:28 | end | test.cpp:264:13:264:14 | Load: * ... |
|
||||
| test.cpp:262:26:262:28 | end | test.cpp:264:13:264:14 | Load: * ... |
|
||||
| test.cpp:262:31:262:31 | x | test.cpp:264:13:264:14 | Load: * ... |
|
||||
| test.cpp:262:31:262:33 | ... ++ | test.cpp:262:21:262:21 | x |
|
||||
| test.cpp:262:31:262:33 | ... ++ | test.cpp:262:21:262:21 | x |
|
||||
| test.cpp:262:31:262:33 | ... ++ | test.cpp:262:31:262:31 | x |
|
||||
| test.cpp:262:31:262:33 | ... ++ | test.cpp:262:31:262:31 | x |
|
||||
| test.cpp:262:31:262:33 | ... ++ | test.cpp:264:14:264:14 | x |
|
||||
| test.cpp:262:31:262:33 | ... ++ | test.cpp:264:14:264:14 | x |
|
||||
| test.cpp:262:31:262:33 | ... ++ | test.cpp:264:14:264:14 | x |
|
||||
| test.cpp:262:31:262:33 | ... ++ | test.cpp:264:14:264:14 | x |
|
||||
| test.cpp:264:14:264:14 | x | test.cpp:262:31:262:31 | x |
|
||||
| test.cpp:264:14:264:14 | x | test.cpp:264:13:264:14 | Load: * ... |
|
||||
| test.cpp:264:14:264:14 | x | test.cpp:264:13:264:14 | Load: * ... |
|
||||
| test.cpp:270:13:270:24 | new[] | test.cpp:271:14:271:15 | xs |
|
||||
| test.cpp:270:13:270:24 | new[] | test.cpp:272:31:272:31 | x |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:271:14:271:21 | ... + ... |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:271:14:271:21 | ... + ... |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:271:14:271:21 | ... + ... |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:271:14:271:21 | ... + ... |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:272:26:272:28 | end |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:272:26:272:28 | end |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:272:31:272:31 | x |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:272:31:272:33 | ... ++ |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:272:31:272:33 | ... ++ |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:274:5:274:6 | * ... |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:274:6:274:6 | x |
|
||||
| test.cpp:271:14:271:15 | xs | test.cpp:274:6:274:6 | x |
|
||||
| test.cpp:271:14:271:21 | ... + ... | test.cpp:271:14:271:21 | ... + ... |
|
||||
| test.cpp:271:14:271:21 | ... + ... | test.cpp:271:14:271:21 | ... + ... |
|
||||
| test.cpp:271:14:271:21 | ... + ... | test.cpp:272:26:272:28 | end |
|
||||
| test.cpp:271:14:271:21 | ... + ... | test.cpp:272:26:272:28 | end |
|
||||
| test.cpp:271:14:271:21 | ... + ... | test.cpp:272:26:272:28 | end |
|
||||
| test.cpp:271:14:271:21 | ... + ... | test.cpp:272:26:272:28 | end |
|
||||
| test.cpp:271:14:271:21 | ... + ... | test.cpp:274:5:274:10 | Store: ... = ... |
|
||||
| test.cpp:271:14:271:21 | ... + ... | test.cpp:274:5:274:10 | Store: ... = ... |
|
||||
| test.cpp:271:14:271:21 | ... + ... | test.cpp:274:5:274:10 | Store: ... = ... |
|
||||
| test.cpp:271:14:271:21 | ... + ... | test.cpp:274:5:274:10 | Store: ... = ... |
|
||||
| test.cpp:272:21:272:21 | x | test.cpp:274:5:274:10 | Store: ... = ... |
|
||||
| test.cpp:272:26:272:28 | end | test.cpp:272:26:272:28 | end |
|
||||
| test.cpp:272:26:272:28 | end | test.cpp:272:26:272:28 | end |
|
||||
| test.cpp:272:26:272:28 | end | test.cpp:274:5:274:10 | Store: ... = ... |
|
||||
| test.cpp:272:26:272:28 | end | test.cpp:274:5:274:10 | Store: ... = ... |
|
||||
| test.cpp:272:31:272:31 | x | test.cpp:274:5:274:10 | Store: ... = ... |
|
||||
| test.cpp:272:31:272:33 | ... ++ | test.cpp:272:21:272:21 | x |
|
||||
| test.cpp:272:31:272:33 | ... ++ | test.cpp:272:21:272:21 | x |
|
||||
| test.cpp:272:31:272:33 | ... ++ | test.cpp:272:31:272:31 | x |
|
||||
| test.cpp:272:31:272:33 | ... ++ | test.cpp:272:31:272:31 | x |
|
||||
| test.cpp:272:31:272:33 | ... ++ | test.cpp:274:5:274:6 | * ... |
|
||||
| test.cpp:272:31:272:33 | ... ++ | test.cpp:274:5:274:6 | * ... |
|
||||
| test.cpp:272:31:272:33 | ... ++ | test.cpp:274:6:274:6 | x |
|
||||
| test.cpp:272:31:272:33 | ... ++ | test.cpp:274:6:274:6 | x |
|
||||
| test.cpp:272:31:272:33 | ... ++ | test.cpp:274:6:274:6 | x |
|
||||
| test.cpp:272:31:272:33 | ... ++ | test.cpp:274:6:274:6 | x |
|
||||
| test.cpp:274:5:274:6 | * ... | test.cpp:274:5:274:10 | Store: ... = ... |
|
||||
| test.cpp:274:6:274:6 | x | test.cpp:272:31:272:31 | x |
|
||||
| test.cpp:274:6:274:6 | x | test.cpp:274:5:274:6 | * ... |
|
||||
| test.cpp:274:6:274:6 | x | test.cpp:274:5:274:10 | Store: ... = ... |
|
||||
| test.cpp:274:6:274:6 | x | test.cpp:274:5:274:10 | Store: ... = ... |
|
||||
| test.cpp:280:13:280:24 | new[] | test.cpp:281:14:281:15 | xs |
|
||||
| test.cpp:281:14:281:15 | xs | test.cpp:282:30:282:32 | ... ++ |
|
||||
| test.cpp:281:14:281:15 | xs | test.cpp:282:30:282:32 | ... ++ |
|
||||
| test.cpp:282:21:282:21 | x | test.cpp:284:13:284:14 | Load: * ... |
|
||||
| test.cpp:282:30:282:30 | x | test.cpp:284:13:284:14 | Load: * ... |
|
||||
| test.cpp:282:30:282:32 | ... ++ | test.cpp:282:21:282:21 | x |
|
||||
| test.cpp:282:30:282:32 | ... ++ | test.cpp:282:21:282:21 | x |
|
||||
| test.cpp:282:30:282:32 | ... ++ | test.cpp:282:30:282:30 | x |
|
||||
| test.cpp:282:30:282:32 | ... ++ | test.cpp:282:30:282:30 | x |
|
||||
| test.cpp:282:30:282:32 | ... ++ | test.cpp:284:14:284:14 | x |
|
||||
| test.cpp:282:30:282:32 | ... ++ | test.cpp:284:14:284:14 | x |
|
||||
| test.cpp:284:14:284:14 | x | test.cpp:284:13:284:14 | Load: * ... |
|
||||
| test.cpp:290:13:290:24 | new[] | test.cpp:291:14:291:15 | xs |
|
||||
| test.cpp:290:13:290:24 | new[] | test.cpp:292:30:292:30 | x |
|
||||
| test.cpp:291:14:291:15 | xs | test.cpp:292:30:292:32 | ... ++ |
|
||||
| test.cpp:291:14:291:15 | xs | test.cpp:292:30:292:32 | ... ++ |
|
||||
| test.cpp:292:21:292:21 | x | test.cpp:294:5:294:10 | Store: ... = ... |
|
||||
| test.cpp:292:30:292:30 | x | test.cpp:294:5:294:10 | Store: ... = ... |
|
||||
| test.cpp:292:30:292:32 | ... ++ | test.cpp:292:21:292:21 | x |
|
||||
| test.cpp:292:30:292:32 | ... ++ | test.cpp:292:21:292:21 | x |
|
||||
| test.cpp:292:30:292:32 | ... ++ | test.cpp:292:30:292:30 | x |
|
||||
| test.cpp:292:30:292:32 | ... ++ | test.cpp:292:30:292:30 | x |
|
||||
| test.cpp:292:30:292:32 | ... ++ | test.cpp:294:5:294:6 | * ... |
|
||||
| test.cpp:292:30:292:32 | ... ++ | test.cpp:294:5:294:6 | * ... |
|
||||
| test.cpp:292:30:292:32 | ... ++ | test.cpp:294:6:294:6 | x |
|
||||
| test.cpp:292:30:292:32 | ... ++ | test.cpp:294:6:294:6 | x |
|
||||
| test.cpp:294:5:294:6 | * ... | test.cpp:294:5:294:10 | Store: ... = ... |
|
||||
| test.cpp:294:6:294:6 | x | test.cpp:294:5:294:10 | Store: ... = ... |
|
||||
#select
|
||||
| test.cpp:6:14:6:15 | Load: * ... | test.cpp:4:15:4:20 | call to malloc | test.cpp:6:14:6:15 | Load: * ... | This read might be out of bounds, as the pointer might be equal to $@ + $@. | test.cpp:4:15:4:20 | call to malloc | call to malloc | test.cpp:5:19:5:22 | size | size |
|
||||
| test.cpp:8:14:8:21 | Load: * ... | test.cpp:4:15:4:20 | call to malloc | test.cpp:8:14:8:21 | Load: * ... | This read might be out of bounds, as the pointer might be equal to $@ + $@ + 1. | test.cpp:4:15:4:20 | call to malloc | call to malloc | test.cpp:5:19:5:22 | size | size |
|
||||
@@ -716,12 +593,3 @@ edges
|
||||
| test.cpp:171:9:171:14 | Store: ... = ... | test.cpp:143:18:143:23 | call to malloc | test.cpp:171:9:171:14 | Store: ... = ... | This write might be out of bounds, as the pointer might be equal to $@ + $@. | test.cpp:143:18:143:23 | call to malloc | call to malloc | test.cpp:144:29:144:32 | size | size |
|
||||
| test.cpp:201:5:201:19 | Store: ... = ... | test.cpp:194:23:194:28 | call to malloc | test.cpp:201:5:201:19 | Store: ... = ... | This write might be out of bounds, as the pointer might be equal to $@ + $@. | test.cpp:194:23:194:28 | call to malloc | call to malloc | test.cpp:195:21:195:23 | len | len |
|
||||
| test.cpp:213:5:213:13 | Store: ... = ... | test.cpp:205:23:205:28 | call to malloc | test.cpp:213:5:213:13 | Store: ... = ... | This write might be out of bounds, as the pointer might be equal to $@ + $@. | test.cpp:205:23:205:28 | call to malloc | call to malloc | test.cpp:206:21:206:23 | len | len |
|
||||
| test.cpp:232:3:232:20 | Store: ... = ... | test.cpp:231:18:231:30 | new[] | test.cpp:232:3:232:20 | Store: ... = ... | This write might be out of bounds, as the pointer might be equal to $@ + $@. | test.cpp:231:18:231:30 | new[] | new[] | test.cpp:232:11:232:15 | index | index |
|
||||
| test.cpp:239:5:239:22 | Store: ... = ... | test.cpp:238:20:238:32 | new[] | test.cpp:239:5:239:22 | Store: ... = ... | This write might be out of bounds, as the pointer might be equal to $@ + $@. | test.cpp:238:20:238:32 | new[] | new[] | test.cpp:239:13:239:17 | index | index |
|
||||
| test.cpp:254:9:254:16 | Store: ... = ... | test.cpp:248:24:248:30 | call to realloc | test.cpp:254:9:254:16 | Store: ... = ... | This write might be out of bounds, as the pointer might be equal to $@ + $@. | test.cpp:248:24:248:30 | call to realloc | call to realloc | test.cpp:254:11:254:11 | i | i |
|
||||
| test.cpp:264:13:264:14 | Load: * ... | test.cpp:260:13:260:24 | new[] | test.cpp:264:13:264:14 | Load: * ... | This read might be out of bounds, as the pointer might be equal to $@ + $@ + 1. | test.cpp:260:13:260:24 | new[] | new[] | test.cpp:261:19:261:21 | len | len |
|
||||
| test.cpp:264:13:264:14 | Load: * ... | test.cpp:260:13:260:24 | new[] | test.cpp:264:13:264:14 | Load: * ... | This read might be out of bounds, as the pointer might be equal to $@ + $@. | test.cpp:260:13:260:24 | new[] | new[] | test.cpp:261:19:261:21 | len | len |
|
||||
| test.cpp:274:5:274:10 | Store: ... = ... | test.cpp:270:13:270:24 | new[] | test.cpp:274:5:274:10 | Store: ... = ... | This write might be out of bounds, as the pointer might be equal to $@ + $@ + 1. | test.cpp:270:13:270:24 | new[] | new[] | test.cpp:271:19:271:21 | len | len |
|
||||
| test.cpp:274:5:274:10 | Store: ... = ... | test.cpp:270:13:270:24 | new[] | test.cpp:274:5:274:10 | Store: ... = ... | This write might be out of bounds, as the pointer might be equal to $@ + $@. | test.cpp:270:13:270:24 | new[] | new[] | test.cpp:271:19:271:21 | len | len |
|
||||
| test.cpp:284:13:284:14 | Load: * ... | test.cpp:280:13:280:24 | new[] | test.cpp:284:13:284:14 | Load: * ... | This read might be out of bounds, as the pointer might be equal to $@ + $@. | test.cpp:280:13:280:24 | new[] | new[] | test.cpp:281:19:281:21 | len | len |
|
||||
| test.cpp:294:5:294:10 | Store: ... = ... | test.cpp:290:13:290:24 | new[] | test.cpp:294:5:294:10 | Store: ... = ... | This write might be out of bounds, as the pointer might be equal to $@ + $@. | test.cpp:290:13:290:24 | new[] | new[] | test.cpp:291:19:291:21 | len | len |
|
||||
|
||||
@@ -222,75 +222,3 @@ void test14(unsigned long n, char *p) {
|
||||
p[n - 1] = 'a'; // GOOD
|
||||
}
|
||||
}
|
||||
|
||||
void test15(unsigned index) {
|
||||
unsigned size = index + 13;
|
||||
if(size < index) {
|
||||
return;
|
||||
}
|
||||
int* newname = new int[size];
|
||||
newname[index] = 0; // GOOD [FALSE POSITIVE]
|
||||
}
|
||||
|
||||
void test16(unsigned index) {
|
||||
unsigned size = index + 13;
|
||||
if(size >= index) {
|
||||
int* newname = new int[size];
|
||||
newname[index] = 0; // GOOD [FALSE POSITIVE]
|
||||
}
|
||||
}
|
||||
|
||||
void *realloc(void *, unsigned);
|
||||
|
||||
void test17(unsigned *p, unsigned x, unsigned k) {
|
||||
if(k > 0 && p[1] <= p[0]){
|
||||
unsigned n = 3*p[0] + k;
|
||||
p = (unsigned*)realloc(p, n);
|
||||
p[0] = n;
|
||||
unsigned i = p[1];
|
||||
// The following access is okay because:
|
||||
// n = 3*p[0] + k >= p[0] + k >= p[1] + k > p[1] = i
|
||||
// (where p[0] denotes the original value for p[0])
|
||||
p[i] = x; // GOOD [FALSE POSITIVE]
|
||||
}
|
||||
}
|
||||
|
||||
void test17(unsigned len)
|
||||
{
|
||||
int *xs = new int[len];
|
||||
int *end = xs + len;
|
||||
for (int *x = xs; x <= end; x++)
|
||||
{
|
||||
int i = *x; // BAD
|
||||
}
|
||||
}
|
||||
|
||||
void test18(unsigned len)
|
||||
{
|
||||
int *xs = new int[len];
|
||||
int *end = xs + len;
|
||||
for (int *x = xs; x <= end; x++)
|
||||
{
|
||||
*x = 0; // BAD
|
||||
}
|
||||
}
|
||||
|
||||
void test19(unsigned len)
|
||||
{
|
||||
int *xs = new int[len];
|
||||
int *end = xs + len;
|
||||
for (int *x = xs; x < end; x++)
|
||||
{
|
||||
int i = *x; // GOOD [FALSE POSITIVE]
|
||||
}
|
||||
}
|
||||
|
||||
void test20(unsigned len)
|
||||
{
|
||||
int *xs = new int[len];
|
||||
int *end = xs + len;
|
||||
for (int *x = xs; x < end; x++)
|
||||
{
|
||||
*x = 0; // GOOD [FALSE POSITIVE]
|
||||
}
|
||||
}
|
||||
@@ -115,16 +115,6 @@ postWithInFlow
|
||||
| test.cpp:602:3:602:7 | access to array [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:608:3:608:4 | * ... [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:608:4:608:4 | p [inner post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:639:3:639:3 | x [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:646:3:646:3 | x [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:652:3:652:3 | x [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:653:3:653:3 | x [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:659:3:659:3 | x [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:660:3:660:3 | x [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:671:3:671:3 | s [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:681:3:681:3 | s [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:689:3:689:3 | s [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
| test.cpp:690:3:690:3 | s [post update] | PostUpdateNode should not be the target of local flow. |
|
||||
viableImplInCallContextTooLarge
|
||||
uniqueParameterNodeAtPosition
|
||||
uniqueParameterNodePosition
|
||||
|
||||
@@ -627,66 +627,4 @@ void test_def_via_phi_read(bool b)
|
||||
}
|
||||
intPointerSource(buffer);
|
||||
sink(buffer); // $ ast,ir
|
||||
}
|
||||
|
||||
void test_static_local_1() {
|
||||
static int x = source();
|
||||
sink(x); // $ ast,ir
|
||||
}
|
||||
|
||||
void test_static_local_2() {
|
||||
static int x = source();
|
||||
x = 0;
|
||||
sink(x); // clean
|
||||
}
|
||||
|
||||
void test_static_local_3() {
|
||||
static int x = 0;
|
||||
sink(x); // $ ir MISSING: ast
|
||||
x = source();
|
||||
}
|
||||
|
||||
void test_static_local_4() {
|
||||
static int x = 0;
|
||||
sink(x); // clean
|
||||
x = source();
|
||||
x = 0;
|
||||
}
|
||||
|
||||
void test_static_local_5() {
|
||||
static int x = 0;
|
||||
sink(x); // $ ir MISSING: ast
|
||||
x = 0;
|
||||
x = source();
|
||||
}
|
||||
|
||||
void test_static_local_6() {
|
||||
static int s = source();
|
||||
static int* ptr_to_s = &s;
|
||||
sink(*ptr_to_s); // $ ir MISSING: ast
|
||||
}
|
||||
|
||||
void test_static_local_7() {
|
||||
static int s = source();
|
||||
s = 0;
|
||||
static int* ptr_to_s = &s;
|
||||
sink(*ptr_to_s); // clean
|
||||
}
|
||||
|
||||
void test_static_local_8() {
|
||||
static int s;
|
||||
static int* ptr_to_s = &s;
|
||||
sink(*ptr_to_s); // $ ir MISSING: ast
|
||||
|
||||
s = source();
|
||||
}
|
||||
|
||||
void test_static_local_9() {
|
||||
static int s;
|
||||
static int* ptr_to_s = &s;
|
||||
sink(*ptr_to_s); // clean
|
||||
|
||||
s = source();
|
||||
s = 0;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -14377,37 +14377,60 @@ ir.cpp:
|
||||
# 1885| Type = [ClassTemplateInstantiation,Struct] Bar2<int>
|
||||
# 1885| ValueCategory = lvalue
|
||||
# 1886| getStmt(2): [ReturnStmt] return ...
|
||||
# 1891| [TopLevelFunction] int test_global_template_int()
|
||||
# 1889| [TopLevelFunction] void noreturnFunc()
|
||||
# 1889| <params>:
|
||||
# 1891| [TopLevelFunction] int noreturnTest(int)
|
||||
# 1891| <params>:
|
||||
# 1891| getParameter(0): [Parameter] x
|
||||
# 1891| Type = [IntType] int
|
||||
# 1891| getEntryPoint(): [BlockStmt] { ... }
|
||||
# 1892| getStmt(0): [DeclStmt] declaration
|
||||
# 1892| getDeclarationEntry(0): [VariableDeclarationEntry] definition of local_int
|
||||
# 1892| Type = [IntType] int
|
||||
# 1892| getVariable().getInitializer(): [Initializer] initializer for local_int
|
||||
# 1892| getExpr(): [VariableAccess] global_template
|
||||
# 1892| Type = [IntType] int
|
||||
# 1892| ValueCategory = prvalue(load)
|
||||
# 1893| getStmt(1): [DeclStmt] declaration
|
||||
# 1893| getDeclarationEntry(0): [VariableDeclarationEntry] definition of local_char
|
||||
# 1893| Type = [PlainCharType] char
|
||||
# 1893| getVariable().getInitializer(): [Initializer] initializer for local_char
|
||||
# 1893| getExpr(): [VariableAccess] global_template
|
||||
# 1893| Type = [PlainCharType] char
|
||||
# 1892| getStmt(0): [IfStmt] if (...) ...
|
||||
# 1892| getCondition(): [LTExpr] ... < ...
|
||||
# 1892| Type = [BoolType] bool
|
||||
# 1892| ValueCategory = prvalue
|
||||
# 1892| getLesserOperand(): [VariableAccess] x
|
||||
# 1892| Type = [IntType] int
|
||||
# 1892| ValueCategory = prvalue(load)
|
||||
# 1892| getGreaterOperand(): [Literal] 10
|
||||
# 1892| Type = [IntType] int
|
||||
# 1892| Value = [Literal] 10
|
||||
# 1892| ValueCategory = prvalue
|
||||
# 1892| getThen(): [BlockStmt] { ... }
|
||||
# 1893| getStmt(0): [ReturnStmt] return ...
|
||||
# 1893| getExpr(): [VariableAccess] x
|
||||
# 1893| Type = [IntType] int
|
||||
# 1893| ValueCategory = prvalue(load)
|
||||
# 1894| getStmt(2): [ReturnStmt] return ...
|
||||
# 1894| getExpr(): [AddExpr] ... + ...
|
||||
# 1894| Type = [IntType] int
|
||||
# 1894| ValueCategory = prvalue
|
||||
# 1894| getLeftOperand(): [VariableAccess] local_int
|
||||
# 1894| Type = [IntType] int
|
||||
# 1894| ValueCategory = prvalue(load)
|
||||
# 1894| getRightOperand(): [VariableAccess] local_char
|
||||
# 1894| Type = [PlainCharType] char
|
||||
# 1894| ValueCategory = prvalue(load)
|
||||
# 1894| getRightOperand().getFullyConverted(): [CStyleCast] (int)...
|
||||
# 1894| Conversion = [IntegralConversion] integral conversion
|
||||
# 1894| Type = [IntType] int
|
||||
# 1894| ValueCategory = prvalue
|
||||
# 1894| getElse(): [BlockStmt] { ... }
|
||||
# 1895| getStmt(0): [ExprStmt] ExprStmt
|
||||
# 1895| getExpr(): [FunctionCall] call to noreturnFunc
|
||||
# 1895| Type = [VoidType] void
|
||||
# 1895| ValueCategory = prvalue
|
||||
# 1897| getStmt(1): [ReturnStmt] return ...
|
||||
# 1899| [TopLevelFunction] int noreturnTest2(int)
|
||||
# 1899| <params>:
|
||||
# 1899| getParameter(0): [Parameter] x
|
||||
# 1899| Type = [IntType] int
|
||||
# 1899| getEntryPoint(): [BlockStmt] { ... }
|
||||
# 1900| getStmt(0): [IfStmt] if (...) ...
|
||||
# 1900| getCondition(): [LTExpr] ... < ...
|
||||
# 1900| Type = [BoolType] bool
|
||||
# 1900| ValueCategory = prvalue
|
||||
# 1900| getLesserOperand(): [VariableAccess] x
|
||||
# 1900| Type = [IntType] int
|
||||
# 1900| ValueCategory = prvalue(load)
|
||||
# 1900| getGreaterOperand(): [Literal] 10
|
||||
# 1900| Type = [IntType] int
|
||||
# 1900| Value = [Literal] 10
|
||||
# 1900| ValueCategory = prvalue
|
||||
# 1900| getThen(): [BlockStmt] { ... }
|
||||
# 1901| getStmt(0): [ExprStmt] ExprStmt
|
||||
# 1901| getExpr(): [FunctionCall] call to noreturnFunc
|
||||
# 1901| Type = [VoidType] void
|
||||
# 1901| ValueCategory = prvalue
|
||||
# 1903| getStmt(1): [ReturnStmt] return ...
|
||||
# 1903| getExpr(): [VariableAccess] x
|
||||
# 1903| Type = [IntType] int
|
||||
# 1903| ValueCategory = prvalue(load)
|
||||
perf-regression.cpp:
|
||||
# 4| [CopyAssignmentOperator] Big& Big::operator=(Big const&)
|
||||
# 4| <params>:
|
||||
|
||||
@@ -18,7 +18,5 @@ predicate shouldDumpFunction(Declaration decl) {
|
||||
decl instanceof Function
|
||||
or
|
||||
decl.(GlobalOrNamespaceVariable).hasInitializer()
|
||||
or
|
||||
decl.(StaticLocalVariable).hasInitializer()
|
||||
)
|
||||
}
|
||||
|
||||
@@ -1886,12 +1886,21 @@ namespace missing_declaration_entries {
|
||||
}
|
||||
}
|
||||
|
||||
template<typename T> T global_template = 42;
|
||||
[[noreturn]] void noreturnFunc();
|
||||
|
||||
int test_global_template_int() {
|
||||
int local_int = global_template<int>;
|
||||
char local_char = global_template<char>;
|
||||
return local_int + (int)local_char;
|
||||
int noreturnTest(int x) {
|
||||
if (x < 10) {
|
||||
return x;
|
||||
} else {
|
||||
noreturnFunc();
|
||||
}
|
||||
}
|
||||
|
||||
int noreturnTest2(int x) {
|
||||
if (x < 10) {
|
||||
noreturnFunc();
|
||||
}
|
||||
return x;
|
||||
}
|
||||
|
||||
// semmle-extractor-options: -std=c++17 --clang
|
||||
|
||||
@@ -5754,16 +5754,6 @@
|
||||
| ir.cpp:1231:5:1231:19 | Load | m1237_15 |
|
||||
| ir.cpp:1231:5:1231:19 | SideEffect | ~m1237_2 |
|
||||
| ir.cpp:1231:25:1231:25 | Address | &:r1231_5 |
|
||||
| ir.cpp:1232:16:1232:16 | Address | &:r1232_3 |
|
||||
| ir.cpp:1232:16:1232:16 | SideEffect | ~m1232_6 |
|
||||
| ir.cpp:1232:20:1232:20 | ChiPartial | partial:m1232_5 |
|
||||
| ir.cpp:1232:20:1232:20 | ChiTotal | total:m1232_2 |
|
||||
| ir.cpp:1232:20:1232:20 | StoreValue | r1232_4 |
|
||||
| ir.cpp:1233:16:1233:16 | Address | &:r1233_3 |
|
||||
| ir.cpp:1233:16:1233:16 | SideEffect | ~m1233_6 |
|
||||
| ir.cpp:1233:20:1233:28 | ChiPartial | partial:m1233_5 |
|
||||
| ir.cpp:1233:20:1233:28 | ChiTotal | total:m1233_2 |
|
||||
| ir.cpp:1233:20:1233:28 | StoreValue | r1233_4 |
|
||||
| ir.cpp:1234:16:1234:16 | Address | &:r1234_1 |
|
||||
| ir.cpp:1234:16:1234:16 | Address | &:r1234_1 |
|
||||
| ir.cpp:1234:16:1234:16 | Address | &:r1234_4 |
|
||||
@@ -8751,38 +8741,44 @@
|
||||
| ir.cpp:1885:11:1885:50 | ChiPartial | partial:m1885_4 |
|
||||
| ir.cpp:1885:11:1885:50 | ChiTotal | total:m1883_4 |
|
||||
| ir.cpp:1885:11:1885:50 | SideEffect | ~m1883_4 |
|
||||
| ir.cpp:1889:24:1889:24 | Address | &:r1889_3 |
|
||||
| ir.cpp:1889:24:1889:24 | Address | &:r1889_3 |
|
||||
| ir.cpp:1889:24:1889:24 | SideEffect | ~m1889_6 |
|
||||
| ir.cpp:1889:24:1889:24 | SideEffect | ~m1889_6 |
|
||||
| ir.cpp:1889:42:1889:43 | ChiPartial | partial:m1889_5 |
|
||||
| ir.cpp:1889:42:1889:43 | ChiPartial | partial:m1889_5 |
|
||||
| ir.cpp:1889:42:1889:43 | ChiTotal | total:m1889_2 |
|
||||
| ir.cpp:1889:42:1889:43 | ChiTotal | total:m1889_2 |
|
||||
| ir.cpp:1889:42:1889:43 | StoreValue | r1889_4 |
|
||||
| ir.cpp:1889:42:1889:43 | StoreValue | r1889_4 |
|
||||
| ir.cpp:1891:5:1891:28 | Address | &:r1891_5 |
|
||||
| ir.cpp:1891:5:1891:28 | ChiPartial | partial:m1891_3 |
|
||||
| ir.cpp:1891:5:1891:28 | ChiTotal | total:m1891_2 |
|
||||
| ir.cpp:1891:5:1891:28 | Load | m1894_8 |
|
||||
| ir.cpp:1891:5:1891:28 | SideEffect | m1891_3 |
|
||||
| ir.cpp:1892:9:1892:17 | Address | &:r1892_1 |
|
||||
| ir.cpp:1892:21:1892:40 | Address | &:r1892_2 |
|
||||
| ir.cpp:1892:21:1892:40 | Load | ~m1891_3 |
|
||||
| ir.cpp:1892:21:1892:40 | StoreValue | r1892_3 |
|
||||
| ir.cpp:1893:10:1893:19 | Address | &:r1893_1 |
|
||||
| ir.cpp:1893:23:1893:43 | Address | &:r1893_2 |
|
||||
| ir.cpp:1893:23:1893:43 | Load | ~m1891_3 |
|
||||
| ir.cpp:1893:23:1893:43 | StoreValue | r1893_3 |
|
||||
| ir.cpp:1894:5:1894:39 | Address | &:r1894_1 |
|
||||
| ir.cpp:1894:12:1894:20 | Address | &:r1894_2 |
|
||||
| ir.cpp:1894:12:1894:20 | Left | r1894_3 |
|
||||
| ir.cpp:1894:12:1894:20 | Load | m1892_4 |
|
||||
| ir.cpp:1894:12:1894:38 | StoreValue | r1894_7 |
|
||||
| ir.cpp:1894:24:1894:38 | Right | r1894_6 |
|
||||
| ir.cpp:1894:29:1894:38 | Address | &:r1894_4 |
|
||||
| ir.cpp:1894:29:1894:38 | Load | m1893_4 |
|
||||
| ir.cpp:1894:29:1894:38 | Unary | r1894_5 |
|
||||
| ir.cpp:1891:5:1891:16 | Address | &:r1891_7 |
|
||||
| ir.cpp:1891:5:1891:16 | ChiPartial | partial:m1891_3 |
|
||||
| ir.cpp:1891:5:1891:16 | ChiTotal | total:m1891_2 |
|
||||
| ir.cpp:1891:5:1891:16 | Load | m1893_4 |
|
||||
| ir.cpp:1891:5:1891:16 | SideEffect | m1891_3 |
|
||||
| ir.cpp:1891:22:1891:22 | Address | &:r1891_5 |
|
||||
| ir.cpp:1892:9:1892:9 | Address | &:r1892_1 |
|
||||
| ir.cpp:1892:9:1892:9 | Left | r1892_2 |
|
||||
| ir.cpp:1892:9:1892:9 | Load | m1891_6 |
|
||||
| ir.cpp:1892:9:1892:14 | Condition | r1892_4 |
|
||||
| ir.cpp:1892:13:1892:14 | Right | r1892_3 |
|
||||
| ir.cpp:1893:9:1893:17 | Address | &:r1893_1 |
|
||||
| ir.cpp:1893:16:1893:16 | Address | &:r1893_2 |
|
||||
| ir.cpp:1893:16:1893:16 | Load | m1891_6 |
|
||||
| ir.cpp:1893:16:1893:16 | StoreValue | r1893_3 |
|
||||
| ir.cpp:1895:9:1895:20 | CallTarget | func:r1895_1 |
|
||||
| ir.cpp:1895:9:1895:20 | ChiPartial | partial:m1895_3 |
|
||||
| ir.cpp:1895:9:1895:20 | ChiTotal | total:m1891_4 |
|
||||
| ir.cpp:1895:9:1895:20 | SideEffect | ~m1891_4 |
|
||||
| ir.cpp:1899:5:1899:17 | Address | &:r1899_8 |
|
||||
| ir.cpp:1899:5:1899:17 | ChiPartial | partial:m1899_3 |
|
||||
| ir.cpp:1899:5:1899:17 | ChiTotal | total:m1899_2 |
|
||||
| ir.cpp:1899:5:1899:17 | Load | m1903_4 |
|
||||
| ir.cpp:1899:5:1899:17 | SideEffect | m1899_3 |
|
||||
| ir.cpp:1899:23:1899:23 | Address | &:r1899_5 |
|
||||
| ir.cpp:1900:9:1900:9 | Address | &:r1900_1 |
|
||||
| ir.cpp:1900:9:1900:9 | Left | r1900_2 |
|
||||
| ir.cpp:1900:9:1900:9 | Load | m1899_6 |
|
||||
| ir.cpp:1900:9:1900:14 | Condition | r1900_4 |
|
||||
| ir.cpp:1900:13:1900:14 | Right | r1900_3 |
|
||||
| ir.cpp:1901:9:1901:20 | CallTarget | func:r1901_1 |
|
||||
| ir.cpp:1901:9:1901:20 | ChiPartial | partial:m1901_3 |
|
||||
| ir.cpp:1901:9:1901:20 | ChiTotal | total:m1899_4 |
|
||||
| ir.cpp:1901:9:1901:20 | SideEffect | ~m1899_4 |
|
||||
| ir.cpp:1903:5:1903:13 | Address | &:r1903_1 |
|
||||
| ir.cpp:1903:12:1903:12 | Address | &:r1903_2 |
|
||||
| ir.cpp:1903:12:1903:12 | Load | m1899_6 |
|
||||
| ir.cpp:1903:12:1903:12 | StoreValue | r1903_3 |
|
||||
| perf-regression.cpp:6:3:6:5 | Address | &:r6_5 |
|
||||
| perf-regression.cpp:6:3:6:5 | Address | &:r6_5 |
|
||||
| perf-regression.cpp:6:3:6:5 | Address | &:r6_7 |
|
||||
@@ -9072,34 +9068,6 @@
|
||||
| struct_init.cpp:20:6:20:25 | ChiPartial | partial:m20_3 |
|
||||
| struct_init.cpp:20:6:20:25 | ChiTotal | total:m20_2 |
|
||||
| struct_init.cpp:20:6:20:25 | SideEffect | ~m25_9 |
|
||||
| struct_init.cpp:21:17:21:28 | Left | r21_3 |
|
||||
| struct_init.cpp:21:17:21:28 | Left | r21_3 |
|
||||
| struct_init.cpp:21:17:21:28 | SideEffect | ~m23_10 |
|
||||
| struct_init.cpp:21:34:24:5 | Right | r21_4 |
|
||||
| struct_init.cpp:21:34:24:5 | Right | r21_6 |
|
||||
| struct_init.cpp:21:34:24:5 | Unary | r21_5 |
|
||||
| struct_init.cpp:21:34:24:5 | Unary | r21_5 |
|
||||
| struct_init.cpp:21:34:24:5 | Unary | r21_7 |
|
||||
| struct_init.cpp:21:34:24:5 | Unary | r21_7 |
|
||||
| struct_init.cpp:22:9:22:25 | Address | &:r22_1 |
|
||||
| struct_init.cpp:22:9:22:25 | Address | &:r22_6 |
|
||||
| struct_init.cpp:22:11:22:13 | ChiPartial | partial:m22_4 |
|
||||
| struct_init.cpp:22:11:22:13 | ChiTotal | total:m21_2 |
|
||||
| struct_init.cpp:22:11:22:13 | StoreValue | r22_3 |
|
||||
| struct_init.cpp:22:11:22:13 | Unary | r22_2 |
|
||||
| struct_init.cpp:22:16:22:23 | ChiPartial | partial:m22_8 |
|
||||
| struct_init.cpp:22:16:22:23 | ChiTotal | total:m22_5 |
|
||||
| struct_init.cpp:22:16:22:23 | StoreValue | r22_7 |
|
||||
| struct_init.cpp:23:9:23:26 | Address | &:r23_1 |
|
||||
| struct_init.cpp:23:9:23:26 | Address | &:r23_6 |
|
||||
| struct_init.cpp:23:11:23:13 | ChiPartial | partial:m23_4 |
|
||||
| struct_init.cpp:23:11:23:13 | ChiTotal | total:m22_9 |
|
||||
| struct_init.cpp:23:11:23:13 | StoreValue | r23_3 |
|
||||
| struct_init.cpp:23:11:23:13 | Unary | r23_2 |
|
||||
| struct_init.cpp:23:16:23:24 | ChiPartial | partial:m23_9 |
|
||||
| struct_init.cpp:23:16:23:24 | ChiTotal | total:m23_5 |
|
||||
| struct_init.cpp:23:16:23:24 | StoreValue | r23_8 |
|
||||
| struct_init.cpp:23:17:23:24 | Unary | r23_7 |
|
||||
| struct_init.cpp:25:5:25:19 | CallTarget | func:r25_1 |
|
||||
| struct_init.cpp:25:5:25:19 | ChiPartial | partial:m25_5 |
|
||||
| struct_init.cpp:25:5:25:19 | ChiTotal | total:m20_4 |
|
||||
|
||||
@@ -6841,28 +6841,6 @@ ir.cpp:
|
||||
# 1231| v1231_8(void) = AliasedUse : ~m?
|
||||
# 1231| v1231_9(void) = ExitFunction :
|
||||
|
||||
# 1232| int a
|
||||
# 1232| Block 0
|
||||
# 1232| v1232_1(void) = EnterFunction :
|
||||
# 1232| mu1232_2(unknown) = AliasedDefinition :
|
||||
# 1232| r1232_3(glval<int>) = VariableAddress[a] :
|
||||
# 1232| r1232_4(int) = Constant[0] :
|
||||
# 1232| mu1232_5(int) = Store[a] : &:r1232_3, r1232_4
|
||||
# 1232| v1232_6(void) = ReturnVoid :
|
||||
# 1232| v1232_7(void) = AliasedUse : ~m?
|
||||
# 1232| v1232_8(void) = ExitFunction :
|
||||
|
||||
# 1233| int b
|
||||
# 1233| Block 0
|
||||
# 1233| v1233_1(void) = EnterFunction :
|
||||
# 1233| mu1233_2(unknown) = AliasedDefinition :
|
||||
# 1233| r1233_3(glval<int>) = VariableAddress[b] :
|
||||
# 1233| r1233_4(int) = Constant[4] :
|
||||
# 1233| mu1233_5(int) = Store[b] : &:r1233_3, r1233_4
|
||||
# 1233| v1233_6(void) = ReturnVoid :
|
||||
# 1233| v1233_7(void) = AliasedUse : ~m?
|
||||
# 1233| v1233_8(void) = ExitFunction :
|
||||
|
||||
# 1240| void staticLocalWithConstructor(char const*)
|
||||
# 1240| Block 0
|
||||
# 1240| v1240_1(void) = EnterFunction :
|
||||
@@ -10057,53 +10035,67 @@ ir.cpp:
|
||||
# 1883| v1883_5(void) = AliasedUse : ~m?
|
||||
# 1883| v1883_6(void) = ExitFunction :
|
||||
|
||||
# 1889| char global_template<char>
|
||||
# 1889| Block 0
|
||||
# 1889| v1889_1(void) = EnterFunction :
|
||||
# 1889| mu1889_2(unknown) = AliasedDefinition :
|
||||
# 1889| r1889_3(glval<char>) = VariableAddress[global_template] :
|
||||
# 1889| r1889_4(char) = Constant[42] :
|
||||
# 1889| mu1889_5(char) = Store[global_template] : &:r1889_3, r1889_4
|
||||
# 1889| v1889_6(void) = ReturnVoid :
|
||||
# 1889| v1889_7(void) = AliasedUse : ~m?
|
||||
# 1889| v1889_8(void) = ExitFunction :
|
||||
|
||||
# 1889| int global_template<int>
|
||||
# 1889| Block 0
|
||||
# 1889| v1889_1(void) = EnterFunction :
|
||||
# 1889| mu1889_2(unknown) = AliasedDefinition :
|
||||
# 1889| r1889_3(glval<int>) = VariableAddress[global_template] :
|
||||
# 1889| r1889_4(int) = Constant[42] :
|
||||
# 1889| mu1889_5(int) = Store[global_template] : &:r1889_3, r1889_4
|
||||
# 1889| v1889_6(void) = ReturnVoid :
|
||||
# 1889| v1889_7(void) = AliasedUse : ~m?
|
||||
# 1889| v1889_8(void) = ExitFunction :
|
||||
|
||||
# 1891| int test_global_template_int()
|
||||
# 1891| int noreturnTest(int)
|
||||
# 1891| Block 0
|
||||
# 1891| v1891_1(void) = EnterFunction :
|
||||
# 1891| mu1891_2(unknown) = AliasedDefinition :
|
||||
# 1891| mu1891_3(unknown) = InitializeNonLocal :
|
||||
# 1892| r1892_1(glval<int>) = VariableAddress[local_int] :
|
||||
# 1892| r1892_2(glval<int>) = VariableAddress[global_template] :
|
||||
# 1892| r1892_3(int) = Load[global_template] : &:r1892_2, ~m?
|
||||
# 1892| mu1892_4(int) = Store[local_int] : &:r1892_1, r1892_3
|
||||
# 1893| r1893_1(glval<char>) = VariableAddress[local_char] :
|
||||
# 1893| r1893_2(glval<char>) = VariableAddress[global_template] :
|
||||
# 1893| r1893_3(char) = Load[global_template] : &:r1893_2, ~m?
|
||||
# 1893| mu1893_4(char) = Store[local_char] : &:r1893_1, r1893_3
|
||||
# 1894| r1894_1(glval<int>) = VariableAddress[#return] :
|
||||
# 1894| r1894_2(glval<int>) = VariableAddress[local_int] :
|
||||
# 1894| r1894_3(int) = Load[local_int] : &:r1894_2, ~m?
|
||||
# 1894| r1894_4(glval<char>) = VariableAddress[local_char] :
|
||||
# 1894| r1894_5(char) = Load[local_char] : &:r1894_4, ~m?
|
||||
# 1894| r1894_6(int) = Convert : r1894_5
|
||||
# 1894| r1894_7(int) = Add : r1894_3, r1894_6
|
||||
# 1894| mu1894_8(int) = Store[#return] : &:r1894_1, r1894_7
|
||||
# 1891| r1891_4(glval<int>) = VariableAddress[#return] :
|
||||
# 1891| v1891_5(void) = ReturnValue : &:r1891_4, ~m?
|
||||
# 1891| v1891_6(void) = AliasedUse : ~m?
|
||||
# 1891| v1891_7(void) = ExitFunction :
|
||||
# 1891| v1891_1(void) = EnterFunction :
|
||||
# 1891| mu1891_2(unknown) = AliasedDefinition :
|
||||
# 1891| mu1891_3(unknown) = InitializeNonLocal :
|
||||
# 1891| r1891_4(glval<int>) = VariableAddress[x] :
|
||||
# 1891| mu1891_5(int) = InitializeParameter[x] : &:r1891_4
|
||||
# 1892| r1892_1(glval<int>) = VariableAddress[x] :
|
||||
# 1892| r1892_2(int) = Load[x] : &:r1892_1, ~m?
|
||||
# 1892| r1892_3(int) = Constant[10] :
|
||||
# 1892| r1892_4(bool) = CompareLT : r1892_2, r1892_3
|
||||
# 1892| v1892_5(void) = ConditionalBranch : r1892_4
|
||||
#-----| False -> Block 2
|
||||
#-----| True -> Block 1
|
||||
|
||||
# 1893| Block 1
|
||||
# 1893| r1893_1(glval<int>) = VariableAddress[#return] :
|
||||
# 1893| r1893_2(glval<int>) = VariableAddress[x] :
|
||||
# 1893| r1893_3(int) = Load[x] : &:r1893_2, ~m?
|
||||
# 1893| mu1893_4(int) = Store[#return] : &:r1893_1, r1893_3
|
||||
# 1891| r1891_6(glval<int>) = VariableAddress[#return] :
|
||||
# 1891| v1891_7(void) = ReturnValue : &:r1891_6, ~m?
|
||||
# 1891| v1891_8(void) = AliasedUse : ~m?
|
||||
# 1891| v1891_9(void) = ExitFunction :
|
||||
|
||||
# 1895| Block 2
|
||||
# 1895| r1895_1(glval<unknown>) = FunctionAddress[noreturnFunc] :
|
||||
# 1895| v1895_2(void) = Call[noreturnFunc] : func:r1895_1
|
||||
# 1895| mu1895_3(unknown) = ^CallSideEffect : ~m?
|
||||
# 1897| v1897_1(void) = Unreached :
|
||||
|
||||
# 1899| int noreturnTest2(int)
|
||||
# 1899| Block 0
|
||||
# 1899| v1899_1(void) = EnterFunction :
|
||||
# 1899| mu1899_2(unknown) = AliasedDefinition :
|
||||
# 1899| mu1899_3(unknown) = InitializeNonLocal :
|
||||
# 1899| r1899_4(glval<int>) = VariableAddress[x] :
|
||||
# 1899| mu1899_5(int) = InitializeParameter[x] : &:r1899_4
|
||||
# 1900| r1900_1(glval<int>) = VariableAddress[x] :
|
||||
# 1900| r1900_2(int) = Load[x] : &:r1900_1, ~m?
|
||||
# 1900| r1900_3(int) = Constant[10] :
|
||||
# 1900| r1900_4(bool) = CompareLT : r1900_2, r1900_3
|
||||
# 1900| v1900_5(void) = ConditionalBranch : r1900_4
|
||||
#-----| False -> Block 2
|
||||
#-----| True -> Block 1
|
||||
|
||||
# 1901| Block 1
|
||||
# 1901| r1901_1(glval<unknown>) = FunctionAddress[noreturnFunc] :
|
||||
# 1901| v1901_2(void) = Call[noreturnFunc] : func:r1901_1
|
||||
# 1901| mu1901_3(unknown) = ^CallSideEffect : ~m?
|
||||
# 1899| v1899_6(void) = Unreached :
|
||||
|
||||
# 1903| Block 2
|
||||
# 1903| r1903_1(glval<int>) = VariableAddress[#return] :
|
||||
# 1903| r1903_2(glval<int>) = VariableAddress[x] :
|
||||
# 1903| r1903_3(int) = Load[x] : &:r1903_2, ~m?
|
||||
# 1903| mu1903_4(int) = Store[#return] : &:r1903_1, r1903_3
|
||||
# 1899| r1899_7(glval<int>) = VariableAddress[#return] :
|
||||
# 1899| v1899_8(void) = ReturnValue : &:r1899_7, ~m?
|
||||
# 1899| v1899_9(void) = AliasedUse : ~m?
|
||||
# 1899| v1899_10(void) = ExitFunction :
|
||||
|
||||
perf-regression.cpp:
|
||||
# 6| void Big::Big()
|
||||
@@ -10390,34 +10382,6 @@ struct_init.cpp:
|
||||
# 20| v20_5(void) = AliasedUse : ~m?
|
||||
# 20| v20_6(void) = ExitFunction :
|
||||
|
||||
# 21| Info[] static_infos
|
||||
# 21| Block 0
|
||||
# 21| v21_1(void) = EnterFunction :
|
||||
# 21| mu21_2(unknown) = AliasedDefinition :
|
||||
# 21| r21_3(glval<Info[]>) = VariableAddress[static_infos] :
|
||||
# 21| r21_4(int) = Constant[0] :
|
||||
# 21| r21_5(glval<Info>) = PointerAdd[16] : r21_3, r21_4
|
||||
# 22| r22_1(glval<char *>) = FieldAddress[name] : r21_5
|
||||
# 22| r22_2(glval<char[2]>) = StringConstant["1"] :
|
||||
# 22| r22_3(char *) = Convert : r22_2
|
||||
# 22| mu22_4(char *) = Store[?] : &:r22_1, r22_3
|
||||
# 22| r22_5(glval<..(*)(..)>) = FieldAddress[handler] : r21_5
|
||||
# 22| r22_6(..(*)(..)) = FunctionAddress[handler1] :
|
||||
# 22| mu22_7(..(*)(..)) = Store[?] : &:r22_5, r22_6
|
||||
# 21| r21_6(int) = Constant[1] :
|
||||
# 21| r21_7(glval<Info>) = PointerAdd[16] : r21_3, r21_6
|
||||
# 23| r23_1(glval<char *>) = FieldAddress[name] : r21_7
|
||||
# 23| r23_2(glval<char[2]>) = StringConstant["2"] :
|
||||
# 23| r23_3(char *) = Convert : r23_2
|
||||
# 23| mu23_4(char *) = Store[?] : &:r23_1, r23_3
|
||||
# 23| r23_5(glval<..(*)(..)>) = FieldAddress[handler] : r21_7
|
||||
# 23| r23_6(glval<..()(..)>) = FunctionAddress[handler2] :
|
||||
# 23| r23_7(..(*)(..)) = CopyValue : r23_6
|
||||
# 23| mu23_8(..(*)(..)) = Store[?] : &:r23_5, r23_7
|
||||
# 21| v21_8(void) = ReturnVoid :
|
||||
# 21| v21_9(void) = AliasedUse : ~m?
|
||||
# 21| v21_10(void) = ExitFunction :
|
||||
|
||||
# 28| void declare_local_infos()
|
||||
# 28| Block 0
|
||||
# 28| v28_1(void) = EnterFunction :
|
||||
|
||||
@@ -2091,3 +2091,69 @@ ssa.cpp:
|
||||
# 417| v417_5(void) = ReturnVoid :
|
||||
# 417| v417_6(void) = AliasedUse : m417_3
|
||||
# 417| v417_7(void) = ExitFunction :
|
||||
|
||||
# 423| int noreturnTest(int)
|
||||
# 423| Block 0
|
||||
# 423| v423_1(void) = EnterFunction :
|
||||
# 423| m423_2(unknown) = AliasedDefinition :
|
||||
# 423| m423_3(unknown) = InitializeNonLocal :
|
||||
# 423| m423_4(unknown) = Chi : total:m423_2, partial:m423_3
|
||||
# 423| r423_5(glval<int>) = VariableAddress[x] :
|
||||
# 423| m423_6(int) = InitializeParameter[x] : &:r423_5
|
||||
# 424| r424_1(glval<int>) = VariableAddress[x] :
|
||||
# 424| r424_2(int) = Load[x] : &:r424_1, m423_6
|
||||
# 424| r424_3(int) = Constant[10] :
|
||||
# 424| r424_4(bool) = CompareLT : r424_2, r424_3
|
||||
# 424| v424_5(void) = ConditionalBranch : r424_4
|
||||
#-----| False -> Block 2
|
||||
#-----| True -> Block 1
|
||||
|
||||
# 425| Block 1
|
||||
# 425| r425_1(glval<int>) = VariableAddress[#return] :
|
||||
# 425| r425_2(glval<int>) = VariableAddress[x] :
|
||||
# 425| r425_3(int) = Load[x] : &:r425_2, m423_6
|
||||
# 425| m425_4(int) = Store[#return] : &:r425_1, r425_3
|
||||
# 423| r423_7(glval<int>) = VariableAddress[#return] :
|
||||
# 423| v423_8(void) = ReturnValue : &:r423_7, m425_4
|
||||
# 423| v423_9(void) = AliasedUse : m423_3
|
||||
# 423| v423_10(void) = ExitFunction :
|
||||
|
||||
# 427| Block 2
|
||||
# 427| r427_1(glval<unknown>) = FunctionAddress[noreturnFunc] :
|
||||
# 427| v427_2(void) = Call[noreturnFunc] : func:r427_1
|
||||
# 427| m427_3(unknown) = ^CallSideEffect : ~m423_4
|
||||
# 427| m427_4(unknown) = Chi : total:m423_4, partial:m427_3
|
||||
# 423| v423_11(void) = Unreached :
|
||||
|
||||
# 431| int noreturnTest2(int)
|
||||
# 431| Block 0
|
||||
# 431| v431_1(void) = EnterFunction :
|
||||
# 431| m431_2(unknown) = AliasedDefinition :
|
||||
# 431| m431_3(unknown) = InitializeNonLocal :
|
||||
# 431| m431_4(unknown) = Chi : total:m431_2, partial:m431_3
|
||||
# 431| r431_5(glval<int>) = VariableAddress[x] :
|
||||
# 431| m431_6(int) = InitializeParameter[x] : &:r431_5
|
||||
# 432| r432_1(glval<int>) = VariableAddress[x] :
|
||||
# 432| r432_2(int) = Load[x] : &:r432_1, m431_6
|
||||
# 432| r432_3(int) = Constant[10] :
|
||||
# 432| r432_4(bool) = CompareLT : r432_2, r432_3
|
||||
# 432| v432_5(void) = ConditionalBranch : r432_4
|
||||
#-----| False -> Block 2
|
||||
#-----| True -> Block 1
|
||||
|
||||
# 433| Block 1
|
||||
# 433| r433_1(glval<unknown>) = FunctionAddress[noreturnFunc] :
|
||||
# 433| v433_2(void) = Call[noreturnFunc] : func:r433_1
|
||||
# 433| m433_3(unknown) = ^CallSideEffect : ~m431_4
|
||||
# 433| m433_4(unknown) = Chi : total:m431_4, partial:m433_3
|
||||
# 431| v431_7(void) = Unreached :
|
||||
|
||||
# 435| Block 2
|
||||
# 435| r435_1(glval<int>) = VariableAddress[#return] :
|
||||
# 435| r435_2(glval<int>) = VariableAddress[x] :
|
||||
# 435| r435_3(int) = Load[x] : &:r435_2, m431_6
|
||||
# 435| m435_4(int) = Store[#return] : &:r435_1, r435_3
|
||||
# 431| r431_8(glval<int>) = VariableAddress[#return] :
|
||||
# 431| v431_9(void) = ReturnValue : &:r431_8, m435_4
|
||||
# 431| v431_10(void) = AliasedUse : m431_3
|
||||
# 431| v431_11(void) = ExitFunction :
|
||||
|
||||
@@ -2080,3 +2080,69 @@ ssa.cpp:
|
||||
# 417| v417_5(void) = ReturnVoid :
|
||||
# 417| v417_6(void) = AliasedUse : m417_3
|
||||
# 417| v417_7(void) = ExitFunction :
|
||||
|
||||
# 423| int noreturnTest(int)
|
||||
# 423| Block 0
|
||||
# 423| v423_1(void) = EnterFunction :
|
||||
# 423| m423_2(unknown) = AliasedDefinition :
|
||||
# 423| m423_3(unknown) = InitializeNonLocal :
|
||||
# 423| m423_4(unknown) = Chi : total:m423_2, partial:m423_3
|
||||
# 423| r423_5(glval<int>) = VariableAddress[x] :
|
||||
# 423| m423_6(int) = InitializeParameter[x] : &:r423_5
|
||||
# 424| r424_1(glval<int>) = VariableAddress[x] :
|
||||
# 424| r424_2(int) = Load[x] : &:r424_1, m423_6
|
||||
# 424| r424_3(int) = Constant[10] :
|
||||
# 424| r424_4(bool) = CompareLT : r424_2, r424_3
|
||||
# 424| v424_5(void) = ConditionalBranch : r424_4
|
||||
#-----| False -> Block 2
|
||||
#-----| True -> Block 1
|
||||
|
||||
# 425| Block 1
|
||||
# 425| r425_1(glval<int>) = VariableAddress[#return] :
|
||||
# 425| r425_2(glval<int>) = VariableAddress[x] :
|
||||
# 425| r425_3(int) = Load[x] : &:r425_2, m423_6
|
||||
# 425| m425_4(int) = Store[#return] : &:r425_1, r425_3
|
||||
# 423| r423_7(glval<int>) = VariableAddress[#return] :
|
||||
# 423| v423_8(void) = ReturnValue : &:r423_7, m425_4
|
||||
# 423| v423_9(void) = AliasedUse : m423_3
|
||||
# 423| v423_10(void) = ExitFunction :
|
||||
|
||||
# 427| Block 2
|
||||
# 427| r427_1(glval<unknown>) = FunctionAddress[noreturnFunc] :
|
||||
# 427| v427_2(void) = Call[noreturnFunc] : func:r427_1
|
||||
# 427| m427_3(unknown) = ^CallSideEffect : ~m423_4
|
||||
# 427| m427_4(unknown) = Chi : total:m423_4, partial:m427_3
|
||||
# 423| v423_11(void) = Unreached :
|
||||
|
||||
# 431| int noreturnTest2(int)
|
||||
# 431| Block 0
|
||||
# 431| v431_1(void) = EnterFunction :
|
||||
# 431| m431_2(unknown) = AliasedDefinition :
|
||||
# 431| m431_3(unknown) = InitializeNonLocal :
|
||||
# 431| m431_4(unknown) = Chi : total:m431_2, partial:m431_3
|
||||
# 431| r431_5(glval<int>) = VariableAddress[x] :
|
||||
# 431| m431_6(int) = InitializeParameter[x] : &:r431_5
|
||||
# 432| r432_1(glval<int>) = VariableAddress[x] :
|
||||
# 432| r432_2(int) = Load[x] : &:r432_1, m431_6
|
||||
# 432| r432_3(int) = Constant[10] :
|
||||
# 432| r432_4(bool) = CompareLT : r432_2, r432_3
|
||||
# 432| v432_5(void) = ConditionalBranch : r432_4
|
||||
#-----| False -> Block 2
|
||||
#-----| True -> Block 1
|
||||
|
||||
# 433| Block 1
|
||||
# 433| r433_1(glval<unknown>) = FunctionAddress[noreturnFunc] :
|
||||
# 433| v433_2(void) = Call[noreturnFunc] : func:r433_1
|
||||
# 433| m433_3(unknown) = ^CallSideEffect : ~m431_4
|
||||
# 433| m433_4(unknown) = Chi : total:m431_4, partial:m433_3
|
||||
# 431| v431_7(void) = Unreached :
|
||||
|
||||
# 435| Block 2
|
||||
# 435| r435_1(glval<int>) = VariableAddress[#return] :
|
||||
# 435| r435_2(glval<int>) = VariableAddress[x] :
|
||||
# 435| r435_3(int) = Load[x] : &:r435_2, m431_6
|
||||
# 435| m435_4(int) = Store[#return] : &:r435_1, r435_3
|
||||
# 431| r431_8(glval<int>) = VariableAddress[#return] :
|
||||
# 431| v431_9(void) = ReturnValue : &:r431_8, m435_4
|
||||
# 431| v431_10(void) = AliasedUse : m431_3
|
||||
# 431| v431_11(void) = ExitFunction :
|
||||
|
||||
@@ -417,3 +417,20 @@ void vla(int n1, int n2, int n3, bool b1) {
|
||||
void nested_array_designators() {
|
||||
int x[1][2] = {[0][0] = 1234, [0][1] = 5678};
|
||||
}
|
||||
|
||||
[[noreturn]] void noreturnFunc();
|
||||
|
||||
int noreturnTest(int x) {
|
||||
if (x < 10) {
|
||||
return x;
|
||||
} else {
|
||||
noreturnFunc();
|
||||
}
|
||||
}
|
||||
|
||||
int noreturnTest2(int x) {
|
||||
if (x < 10) {
|
||||
noreturnFunc();
|
||||
}
|
||||
return x;
|
||||
}
|
||||
|
||||
@@ -1940,3 +1940,65 @@ ssa.cpp:
|
||||
# 417| v417_4(void) = ReturnVoid :
|
||||
# 417| v417_5(void) = AliasedUse : ~m?
|
||||
# 417| v417_6(void) = ExitFunction :
|
||||
|
||||
# 423| int noreturnTest(int)
|
||||
# 423| Block 0
|
||||
# 423| v423_1(void) = EnterFunction :
|
||||
# 423| mu423_2(unknown) = AliasedDefinition :
|
||||
# 423| mu423_3(unknown) = InitializeNonLocal :
|
||||
# 423| r423_4(glval<int>) = VariableAddress[x] :
|
||||
# 423| m423_5(int) = InitializeParameter[x] : &:r423_4
|
||||
# 424| r424_1(glval<int>) = VariableAddress[x] :
|
||||
# 424| r424_2(int) = Load[x] : &:r424_1, m423_5
|
||||
# 424| r424_3(int) = Constant[10] :
|
||||
# 424| r424_4(bool) = CompareLT : r424_2, r424_3
|
||||
# 424| v424_5(void) = ConditionalBranch : r424_4
|
||||
#-----| False -> Block 2
|
||||
#-----| True -> Block 1
|
||||
|
||||
# 425| Block 1
|
||||
# 425| r425_1(glval<int>) = VariableAddress[#return] :
|
||||
# 425| r425_2(glval<int>) = VariableAddress[x] :
|
||||
# 425| r425_3(int) = Load[x] : &:r425_2, m423_5
|
||||
# 425| m425_4(int) = Store[#return] : &:r425_1, r425_3
|
||||
# 423| r423_6(glval<int>) = VariableAddress[#return] :
|
||||
# 423| v423_7(void) = ReturnValue : &:r423_6, m425_4
|
||||
# 423| v423_8(void) = AliasedUse : ~m?
|
||||
# 423| v423_9(void) = ExitFunction :
|
||||
|
||||
# 427| Block 2
|
||||
# 427| r427_1(glval<unknown>) = FunctionAddress[noreturnFunc] :
|
||||
# 427| v427_2(void) = Call[noreturnFunc] : func:r427_1
|
||||
# 427| mu427_3(unknown) = ^CallSideEffect : ~m?
|
||||
# 423| v423_10(void) = Unreached :
|
||||
|
||||
# 431| int noreturnTest2(int)
|
||||
# 431| Block 0
|
||||
# 431| v431_1(void) = EnterFunction :
|
||||
# 431| mu431_2(unknown) = AliasedDefinition :
|
||||
# 431| mu431_3(unknown) = InitializeNonLocal :
|
||||
# 431| r431_4(glval<int>) = VariableAddress[x] :
|
||||
# 431| m431_5(int) = InitializeParameter[x] : &:r431_4
|
||||
# 432| r432_1(glval<int>) = VariableAddress[x] :
|
||||
# 432| r432_2(int) = Load[x] : &:r432_1, m431_5
|
||||
# 432| r432_3(int) = Constant[10] :
|
||||
# 432| r432_4(bool) = CompareLT : r432_2, r432_3
|
||||
# 432| v432_5(void) = ConditionalBranch : r432_4
|
||||
#-----| False -> Block 2
|
||||
#-----| True -> Block 1
|
||||
|
||||
# 433| Block 1
|
||||
# 433| r433_1(glval<unknown>) = FunctionAddress[noreturnFunc] :
|
||||
# 433| v433_2(void) = Call[noreturnFunc] : func:r433_1
|
||||
# 433| mu433_3(unknown) = ^CallSideEffect : ~m?
|
||||
# 431| v431_6(void) = Unreached :
|
||||
|
||||
# 435| Block 2
|
||||
# 435| r435_1(glval<int>) = VariableAddress[#return] :
|
||||
# 435| r435_2(glval<int>) = VariableAddress[x] :
|
||||
# 435| r435_3(int) = Load[x] : &:r435_2, m431_5
|
||||
# 435| m435_4(int) = Store[#return] : &:r435_1, r435_3
|
||||
# 431| r431_7(glval<int>) = VariableAddress[#return] :
|
||||
# 431| v431_8(void) = ReturnValue : &:r431_7, m435_4
|
||||
# 431| v431_9(void) = AliasedUse : ~m?
|
||||
# 431| v431_10(void) = ExitFunction :
|
||||
|
||||
@@ -1940,3 +1940,65 @@ ssa.cpp:
|
||||
# 417| v417_4(void) = ReturnVoid :
|
||||
# 417| v417_5(void) = AliasedUse : ~m?
|
||||
# 417| v417_6(void) = ExitFunction :
|
||||
|
||||
# 423| int noreturnTest(int)
|
||||
# 423| Block 0
|
||||
# 423| v423_1(void) = EnterFunction :
|
||||
# 423| mu423_2(unknown) = AliasedDefinition :
|
||||
# 423| mu423_3(unknown) = InitializeNonLocal :
|
||||
# 423| r423_4(glval<int>) = VariableAddress[x] :
|
||||
# 423| m423_5(int) = InitializeParameter[x] : &:r423_4
|
||||
# 424| r424_1(glval<int>) = VariableAddress[x] :
|
||||
# 424| r424_2(int) = Load[x] : &:r424_1, m423_5
|
||||
# 424| r424_3(int) = Constant[10] :
|
||||
# 424| r424_4(bool) = CompareLT : r424_2, r424_3
|
||||
# 424| v424_5(void) = ConditionalBranch : r424_4
|
||||
#-----| False -> Block 2
|
||||
#-----| True -> Block 1
|
||||
|
||||
# 425| Block 1
|
||||
# 425| r425_1(glval<int>) = VariableAddress[#return] :
|
||||
# 425| r425_2(glval<int>) = VariableAddress[x] :
|
||||
# 425| r425_3(int) = Load[x] : &:r425_2, m423_5
|
||||
# 425| m425_4(int) = Store[#return] : &:r425_1, r425_3
|
||||
# 423| r423_6(glval<int>) = VariableAddress[#return] :
|
||||
# 423| v423_7(void) = ReturnValue : &:r423_6, m425_4
|
||||
# 423| v423_8(void) = AliasedUse : ~m?
|
||||
# 423| v423_9(void) = ExitFunction :
|
||||
|
||||
# 427| Block 2
|
||||
# 427| r427_1(glval<unknown>) = FunctionAddress[noreturnFunc] :
|
||||
# 427| v427_2(void) = Call[noreturnFunc] : func:r427_1
|
||||
# 427| mu427_3(unknown) = ^CallSideEffect : ~m?
|
||||
# 423| v423_10(void) = Unreached :
|
||||
|
||||
# 431| int noreturnTest2(int)
|
||||
# 431| Block 0
|
||||
# 431| v431_1(void) = EnterFunction :
|
||||
# 431| mu431_2(unknown) = AliasedDefinition :
|
||||
# 431| mu431_3(unknown) = InitializeNonLocal :
|
||||
# 431| r431_4(glval<int>) = VariableAddress[x] :
|
||||
# 431| m431_5(int) = InitializeParameter[x] : &:r431_4
|
||||
# 432| r432_1(glval<int>) = VariableAddress[x] :
|
||||
# 432| r432_2(int) = Load[x] : &:r432_1, m431_5
|
||||
# 432| r432_3(int) = Constant[10] :
|
||||
# 432| r432_4(bool) = CompareLT : r432_2, r432_3
|
||||
# 432| v432_5(void) = ConditionalBranch : r432_4
|
||||
#-----| False -> Block 2
|
||||
#-----| True -> Block 1
|
||||
|
||||
# 433| Block 1
|
||||
# 433| r433_1(glval<unknown>) = FunctionAddress[noreturnFunc] :
|
||||
# 433| v433_2(void) = Call[noreturnFunc] : func:r433_1
|
||||
# 433| mu433_3(unknown) = ^CallSideEffect : ~m?
|
||||
# 431| v431_6(void) = Unreached :
|
||||
|
||||
# 435| Block 2
|
||||
# 435| r435_1(glval<int>) = VariableAddress[#return] :
|
||||
# 435| r435_2(glval<int>) = VariableAddress[x] :
|
||||
# 435| r435_3(int) = Load[x] : &:r435_2, m431_5
|
||||
# 435| m435_4(int) = Store[#return] : &:r435_1, r435_3
|
||||
# 431| r431_7(glval<int>) = VariableAddress[#return] :
|
||||
# 431| v431_8(void) = ReturnValue : &:r431_7, m435_4
|
||||
# 431| v431_9(void) = AliasedUse : ~m?
|
||||
# 431| v431_10(void) = ExitFunction :
|
||||
|
||||
@@ -4,9 +4,7 @@ uniqueType
|
||||
uniqueNodeLocation
|
||||
missingLocation
|
||||
uniqueNodeToString
|
||||
| cpp11.cpp:50:15:50:16 | (no string representation) | Node should have one toString but has 0. |
|
||||
missingToString
|
||||
| Nodes without toString: 1 |
|
||||
parameterCallable
|
||||
localFlowIsLocal
|
||||
readStepIsLocal
|
||||
|
||||
@@ -233,14 +233,3 @@ void f_if_ternary_1(int b, int x, int y) {
|
||||
if (b ? x : y) {
|
||||
}
|
||||
}
|
||||
|
||||
struct _A
|
||||
{
|
||||
unsigned int x;
|
||||
const char *y;
|
||||
} as[];
|
||||
|
||||
void regression_test(void)
|
||||
{
|
||||
static const void *a[] = {0 ? 0 : as};
|
||||
}
|
||||
|
||||
@@ -3,7 +3,6 @@
|
||||
| nested.cpp:21:23:21:26 | fmt0 | The format string argument to snprintf should be constant to prevent security issues and other potential errors. |
|
||||
| nested.cpp:79:32:79:38 | call to get_fmt | The format string argument to diagnostic should be constant to prevent security issues and other potential errors. |
|
||||
| nested.cpp:87:18:87:20 | fmt | The format string argument to diagnostic should be constant to prevent security issues and other potential errors. |
|
||||
| test.cpp:51:10:51:21 | call to make_message | The format string argument to printf should be constant to prevent security issues and other potential errors. |
|
||||
| test.cpp:57:12:57:16 | hello | The format string argument to printf should be constant to prevent security issues and other potential errors. |
|
||||
| test.cpp:60:12:60:21 | call to const_wash | The format string argument to printf should be constant to prevent security issues and other potential errors. |
|
||||
| test.cpp:61:12:61:26 | ... + ... | The format string argument to printf should be constant to prevent security issues and other potential errors. |
|
||||
|
||||
@@ -48,7 +48,7 @@ int main(int argc, char **argv) {
|
||||
printf(choose_message(argc - 1), argc - 1); // GOOD
|
||||
printf(messages[1]); // GOOD
|
||||
printf(message); // GOOD
|
||||
printf(make_message(argc - 1)); // BAD
|
||||
printf(make_message(argc - 1)); // BAD [NOT DETECTED]
|
||||
printf("Hello, World\n"); // GOOD
|
||||
printf(_("Hello, World\n")); // GOOD
|
||||
{
|
||||
|
||||
@@ -1,7 +1,3 @@
|
||||
## 1.5.1
|
||||
|
||||
No user-facing changes.
|
||||
|
||||
## 1.5.0
|
||||
|
||||
No user-facing changes.
|
||||
|
||||
@@ -1,3 +0,0 @@
|
||||
## 1.5.1
|
||||
|
||||
No user-facing changes.
|
||||
@@ -1,2 +1,2 @@
|
||||
---
|
||||
lastReleaseVersion: 1.5.1
|
||||
lastReleaseVersion: 1.5.0
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
name: codeql/csharp-solorigate-all
|
||||
version: 1.5.2-dev
|
||||
version: 1.5.1-dev
|
||||
groups:
|
||||
- csharp
|
||||
- solorigate
|
||||
|
||||
@@ -1,7 +1,3 @@
|
||||
## 1.5.1
|
||||
|
||||
No user-facing changes.
|
||||
|
||||
## 1.5.0
|
||||
|
||||
No user-facing changes.
|
||||
|
||||
@@ -1,3 +0,0 @@
|
||||
## 1.5.1
|
||||
|
||||
No user-facing changes.
|
||||
@@ -1,2 +1,2 @@
|
||||
---
|
||||
lastReleaseVersion: 1.5.1
|
||||
lastReleaseVersion: 1.5.0
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
name: codeql/csharp-solorigate-queries
|
||||
version: 1.5.2-dev
|
||||
version: 1.5.1-dev
|
||||
groups:
|
||||
- csharp
|
||||
- solorigate
|
||||
|
||||
@@ -1,4 +1,7 @@
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL found some projects which cannot be built with .NET Core:\n\n- `test.csproj`",
|
||||
"severity": "warning",
|
||||
"source": {
|
||||
@@ -13,6 +16,9 @@
|
||||
}
|
||||
}
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL was unable to build the following projects using MSBuild:\n\n- `test.csproj`\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
|
||||
@@ -1,4 +1,7 @@
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL was unable to build the following projects using MSBuild:\n\n- `test.sln`\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
@@ -13,6 +16,9 @@
|
||||
}
|
||||
}
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "Some project files were not found when CodeQL built your project:\n\n- `Example.csproj`\n- `Example.Test.csproj`\n\nThis may lead to subsequent failures. You can check for common causes for missing project files:\n\n- Ensure that the project is built using the [intended operating system](https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#jobsjob_idruns-on) and that filenames on case-sensitive platforms are correctly specified.\n- If your repository uses Git submodules, ensure that those are [checked out](https://github.com/actions/checkout#usage) before the CodeQL Action is run.\n- If you auto-generate some project files as part of your build process, ensure that these are generated before the CodeQL Action is run.",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
|
||||
@@ -1,4 +1,7 @@
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL was unable to build the following projects using .NET Core:\n\n- `test.csproj`\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
@@ -13,6 +16,9 @@
|
||||
}
|
||||
}
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL was unable to build the following projects using MSBuild:\n\n- `test.csproj`\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
@@ -27,6 +33,9 @@
|
||||
}
|
||||
}
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "[Configure your workflow](https://docs.github.com/en/actions/automating-builds-and-tests/building-and-testing-xamarin-applications) for this SDK before running CodeQL.",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
import os
|
||||
from create_database_utils import *
|
||||
from diagnostics_test_utils import *
|
||||
|
||||
@@ -21,35 +22,35 @@ check_diagnostics()
|
||||
# no arguments, but `--`
|
||||
s = run_codeql_database_create_stdout(['dotnet clean', 'rm -rf test-db', 'dotnet run --'], "test2-db")
|
||||
check_build_out("Default reply", s)
|
||||
check_diagnostics(test_db="test2-db")
|
||||
check_diagnostics(diagnostics_dir="test2-db/diagnostic")
|
||||
|
||||
# one argument, no `--`
|
||||
s = run_codeql_database_create_stdout(['dotnet clean', 'rm -rf test2-db', 'dotnet run hello'], "test3-db")
|
||||
check_build_out("Default reply", s)
|
||||
check_diagnostics(test_db="test3-db")
|
||||
check_diagnostics(diagnostics_dir="test3-db/diagnostic")
|
||||
|
||||
# one argument, but `--`
|
||||
s = run_codeql_database_create_stdout(['dotnet clean', 'rm -rf test3-db', 'dotnet run -- hello'], "test4-db")
|
||||
check_build_out("Default reply", s)
|
||||
check_diagnostics(test_db="test4-db")
|
||||
check_diagnostics(diagnostics_dir="test4-db/diagnostic")
|
||||
|
||||
# two arguments, no `--`
|
||||
s = run_codeql_database_create_stdout(['dotnet clean', 'rm -rf test4-db', 'dotnet run hello world'], "test5-db")
|
||||
check_build_out("hello, world", s)
|
||||
check_diagnostics(test_db="test5-db")
|
||||
check_diagnostics(diagnostics_dir="test5-db/diagnostic")
|
||||
|
||||
# two arguments, and `--`
|
||||
s = run_codeql_database_create_stdout(['dotnet clean', 'rm -rf test5-db', 'dotnet run -- hello world'], "test6-db")
|
||||
check_build_out("hello, world", s)
|
||||
check_diagnostics(test_db="test6-db")
|
||||
check_diagnostics(diagnostics_dir="test6-db/diagnostic")
|
||||
|
||||
# shared compilation enabled; tracer should override by changing the command
|
||||
# to `dotnet run -p:UseSharedCompilation=true -p:UseSharedCompilation=false -- hello world`
|
||||
s = run_codeql_database_create_stdout(['dotnet clean', 'rm -rf test6-db', 'dotnet run -p:UseSharedCompilation=true -- hello world'], "test7-db")
|
||||
check_build_out("hello, world", s)
|
||||
check_diagnostics(test_db="test7-db")
|
||||
check_diagnostics(diagnostics_dir="test7-db/diagnostic")
|
||||
|
||||
# option passed into `dotnet run`
|
||||
s = run_codeql_database_create_stdout(['dotnet clean', 'rm -rf test7-db', 'dotnet build', 'dotnet run --no-build hello world'], "test8-db")
|
||||
check_build_out("hello, world", s)
|
||||
check_diagnostics(test_db="test8-db")
|
||||
check_diagnostics(diagnostics_dir="test8-db/diagnostic")
|
||||
|
||||
@@ -1,4 +1,7 @@
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL attempted to build your project using a script located at `build.sh`, which failed.\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
@@ -13,6 +16,9 @@
|
||||
}
|
||||
}
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL could not find any project or solution files in your repository.\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
|
||||
@@ -1,4 +1,7 @@
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL could not find any project or solution files in your repository.\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
@@ -13,6 +16,9 @@
|
||||
}
|
||||
}
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL found multiple potential build scripts for your project and attempted to run `build.sh`, which failed. This may not be the right build script for your project.\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
|
||||
@@ -1,4 +1,7 @@
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL attempted to build your project using a script located at `build.bat`, which failed.\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
@@ -13,6 +16,9 @@
|
||||
}
|
||||
}
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL could not find any project or solution files in your repository.\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
|
||||
@@ -1,4 +1,7 @@
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL could not find any project or solution files in your repository.\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
@@ -13,6 +16,9 @@
|
||||
}
|
||||
}
|
||||
{
|
||||
"attributes": {},
|
||||
"helpLinks": [],
|
||||
"internal": false,
|
||||
"markdownMessage": "CodeQL found multiple potential build scripts for your project and attempted to run `build.bat`, which failed. This may not be the right build script for your project.\n\nSet up a [manual build command](https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-the-codeql-workflow-for-compiled-languages).",
|
||||
"severity": "error",
|
||||
"source": {
|
||||
|
||||
@@ -1,7 +1,3 @@
|
||||
## 0.6.1
|
||||
|
||||
No user-facing changes.
|
||||
|
||||
## 0.6.0
|
||||
|
||||
### Deprecated APIs
|
||||
|
||||
@@ -1,3 +0,0 @@
|
||||
## 0.6.1
|
||||
|
||||
No user-facing changes.
|
||||
@@ -1,2 +1,2 @@
|
||||
---
|
||||
lastReleaseVersion: 0.6.1
|
||||
lastReleaseVersion: 0.6.0
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
name: codeql/csharp-all
|
||||
version: 0.6.2-dev
|
||||
version: 0.6.1-dev
|
||||
groups: csharp
|
||||
dbscheme: semmlecode.csharp.dbscheme
|
||||
extractor: csharp
|
||||
|
||||
@@ -12,9 +12,9 @@ class Attribute extends Element, @cil_attribute {
|
||||
Method getConstructor() { cil_attribute(this, _, result) }
|
||||
|
||||
/** Gets the type of this attribute. */
|
||||
Type getType() { result = this.getConstructor().getDeclaringType() }
|
||||
Type getType() { result = getConstructor().getDeclaringType() }
|
||||
|
||||
override string toString() { result = "[" + this.getType().getName() + "(...)]" }
|
||||
override string toString() { result = "[" + getType().getName() + "(...)]" }
|
||||
|
||||
/** Gets the value of the `i`th argument of this attribute. */
|
||||
string getArgument(int i) { cil_attribute_positional_argument(this, i, result) }
|
||||
@@ -23,9 +23,9 @@ class Attribute extends Element, @cil_attribute {
|
||||
string getNamedArgument(string name) { cil_attribute_named_argument(this, name, result) }
|
||||
|
||||
/** Gets an argument of this attribute, if any. */
|
||||
string getAnArgument() { result = this.getArgument(_) or result = this.getNamedArgument(_) }
|
||||
string getAnArgument() { result = getArgument(_) or result = getNamedArgument(_) }
|
||||
|
||||
override CS::Location getLocation() { result = this.getDeclaration().getLocation() }
|
||||
override CS::Location getLocation() { result = getDeclaration().getLocation() }
|
||||
}
|
||||
|
||||
/** A generic attribute to a declaration. */
|
||||
|
||||
@@ -1,183 +1,156 @@
|
||||
/**
|
||||
* Provides classes for performing global (inter-procedural)
|
||||
* content-sensitive data flow analyses.
|
||||
*
|
||||
* Unlike `DataFlow::Global`, we allow for data to be stored (possibly nested) inside
|
||||
* contents of sources and sinks.
|
||||
* We track flow paths of the form
|
||||
*
|
||||
* ```
|
||||
* source --value-->* node
|
||||
* (--read--> node --value-->* node)*
|
||||
* --(non-value|value)-->* node
|
||||
* (--store--> node --value-->* node)*
|
||||
* --value-->* sink
|
||||
* ```
|
||||
*
|
||||
* where `--value-->` is a value-preserving flow step, `--read-->` is a read
|
||||
* step, `--store-->` is a store step, and `--(non-value)-->` is a
|
||||
* non-value-preserving flow step.
|
||||
*
|
||||
* That is, first a sequence of 0 or more reads, followed by 0 or more additional
|
||||
* steps, followed by 0 or more stores, with value-preserving steps allowed in
|
||||
* between all other steps.
|
||||
*/
|
||||
|
||||
private import csharp
|
||||
private import codeql.util.Boolean
|
||||
private import DataFlowImplCommon
|
||||
private import DataFlowImplSpecific::Private
|
||||
private import DataFlowImplSpecific::Private as DataFlowPrivate
|
||||
|
||||
/**
|
||||
* An input configuration for content data flow.
|
||||
*/
|
||||
signature module ConfigSig {
|
||||
module ContentDataFlow {
|
||||
private import DataFlowImplSpecific::Private
|
||||
private import DataFlowImplSpecific::Private as DataFlowPrivate
|
||||
private import DataFlowImplForContentDataFlow as DF
|
||||
|
||||
class Node = DF::Node;
|
||||
|
||||
class FlowFeature = DF::FlowFeature;
|
||||
|
||||
class ContentSet = DF::ContentSet;
|
||||
|
||||
// predicate stageStats = DF::stageStats/8;
|
||||
/**
|
||||
* Holds if `source` is a relevant data flow source.
|
||||
*/
|
||||
predicate isSource(DataFlow::Node source);
|
||||
|
||||
/**
|
||||
* Holds if `sink` is a relevant data flow sink.
|
||||
*/
|
||||
predicate isSink(DataFlow::Node sink);
|
||||
|
||||
/**
|
||||
* Holds if data may flow from `node1` to `node2` in addition to the normal data-flow steps.
|
||||
*/
|
||||
default predicate isAdditionalFlowStep(DataFlow::Node node1, DataFlow::Node node2) { none() }
|
||||
|
||||
/** Holds if data flow into `node` is prohibited. */
|
||||
default predicate isBarrier(DataFlow::Node node) { none() }
|
||||
|
||||
/**
|
||||
* Gets a data flow configuration feature to add restrictions to the set of
|
||||
* valid flow paths.
|
||||
* A configuration of interprocedural data flow analysis. This defines
|
||||
* sources, sinks, and any other configurable aspect of the analysis. Each
|
||||
* use of the global data flow library must define its own unique extension
|
||||
* of this abstract class. To create a configuration, extend this class with
|
||||
* a subclass whose characteristic predicate is a unique singleton string.
|
||||
* For example, write
|
||||
*
|
||||
* - `FeatureHasSourceCallContext`:
|
||||
* Assume that sources have some existing call context to disallow
|
||||
* conflicting return-flow directly following the source.
|
||||
* - `FeatureHasSinkCallContext`:
|
||||
* Assume that sinks have some existing call context to disallow
|
||||
* conflicting argument-to-parameter flow directly preceding the sink.
|
||||
* - `FeatureEqualSourceSinkCallContext`:
|
||||
* Implies both of the above and additionally ensures that the entire flow
|
||||
* path preserves the call context.
|
||||
* ```ql
|
||||
* class MyAnalysisConfiguration extends ContentDataFlowConfiguration {
|
||||
* MyAnalysisConfiguration() { this = "MyAnalysisConfiguration" }
|
||||
* // Override `isSource` and `isSink`.
|
||||
* // Optionally override `isBarrier`.
|
||||
* // Optionally override `isAdditionalFlowStep`.
|
||||
* // Optionally override `getAFeature`.
|
||||
* // Optionally override `accessPathLimit`.
|
||||
* // Optionally override `isRelevantContent`.
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* Unlike `DataFlow::Configuration` (on which this class is based), we allow
|
||||
* for data to be stored (possibly nested) inside contents of sources and sinks.
|
||||
* We track flow paths of the form
|
||||
*
|
||||
* ```
|
||||
* source --value-->* node
|
||||
* (--read--> node --value-->* node)*
|
||||
* --(non-value|value)-->* node
|
||||
* (--store--> node --value-->* node)*
|
||||
* --value-->* sink
|
||||
* ```
|
||||
*
|
||||
* where `--value-->` is a value-preserving flow step, `--read-->` is a read
|
||||
* step, `--store-->` is a store step, and `--(non-value)-->` is a
|
||||
* non-value-preserving flow step.
|
||||
*
|
||||
* That is, first a sequence of 0 or more reads, followed by 0 or more additional
|
||||
* steps, followed by 0 or more stores, with value-preserving steps allowed in
|
||||
* between all other steps.
|
||||
*/
|
||||
default DataFlow::FlowFeature getAFeature() { none() }
|
||||
abstract class Configuration extends string {
|
||||
bindingset[this]
|
||||
Configuration() { any() }
|
||||
|
||||
/** Gets a limit on the number of reads out of sources and number of stores into sinks. */
|
||||
default int accessPathLimit() { result = DataFlowPrivate::accessPathLimit() }
|
||||
/**
|
||||
* Holds if `source` is a relevant data flow source.
|
||||
*/
|
||||
abstract predicate isSource(Node source);
|
||||
|
||||
/** Holds if `c` is relevant for reads out of sources or stores into sinks. */
|
||||
default predicate isRelevantContent(DataFlow::ContentSet c) { any() }
|
||||
}
|
||||
/**
|
||||
* Holds if `sink` is a relevant data flow sink.
|
||||
*/
|
||||
abstract predicate isSink(Node sink);
|
||||
|
||||
/**
|
||||
* Constructs a global content data flow computation.
|
||||
*/
|
||||
module Global<ConfigSig ContentConfig> {
|
||||
private module FlowConfig implements DataFlow::StateConfigSig {
|
||||
class FlowState = State;
|
||||
/**
|
||||
* Holds if data may flow from `node1` to `node2` in addition to the normal data-flow steps.
|
||||
*/
|
||||
predicate isAdditionalFlowStep(Node node1, Node node2) { none() }
|
||||
|
||||
predicate isSource(DataFlow::Node source, FlowState state) {
|
||||
ContentConfig::isSource(source) and
|
||||
state.(InitState).decode(true)
|
||||
}
|
||||
/** Holds if data flow into `node` is prohibited. */
|
||||
predicate isBarrier(Node node) { none() }
|
||||
|
||||
predicate isSink(DataFlow::Node sink, FlowState state) {
|
||||
ContentConfig::isSink(sink) and
|
||||
(
|
||||
state instanceof InitState or
|
||||
state instanceof StoreState or
|
||||
state instanceof ReadState
|
||||
/**
|
||||
* Gets a data flow configuration feature to add restrictions to the set of
|
||||
* valid flow paths.
|
||||
*
|
||||
* - `FeatureHasSourceCallContext`:
|
||||
* Assume that sources have some existing call context to disallow
|
||||
* conflicting return-flow directly following the source.
|
||||
* - `FeatureHasSinkCallContext`:
|
||||
* Assume that sinks have some existing call context to disallow
|
||||
* conflicting argument-to-parameter flow directly preceding the sink.
|
||||
* - `FeatureEqualSourceSinkCallContext`:
|
||||
* Implies both of the above and additionally ensures that the entire flow
|
||||
* path preserves the call context.
|
||||
*/
|
||||
FlowFeature getAFeature() { none() }
|
||||
|
||||
/** Gets a limit on the number of reads out of sources and number of stores into sinks. */
|
||||
int accessPathLimit() { result = DataFlowPrivate::accessPathLimit() }
|
||||
|
||||
/** Holds if `c` is relevant for reads out of sources or stores into sinks. */
|
||||
predicate isRelevantContent(ContentSet c) { any() }
|
||||
|
||||
/**
|
||||
* Holds if data stored inside `sourceAp` on `source` flows to `sinkAp` inside `sink`
|
||||
* for this configuration. `preservesValue` indicates whether any of the additional
|
||||
* flow steps defined by `isAdditionalFlowStep` are needed.
|
||||
*
|
||||
* For the source access path, `sourceAp`, the top of the stack represents the content
|
||||
* that was last read from. That is, if `sourceAp` is `Field1.Field2` (with `Field1`
|
||||
* being the top of the stack), then there is flow from `source.Field2.Field1`.
|
||||
*
|
||||
* For the sink access path, `sinkAp`, the top of the stack represents the content
|
||||
* that was last stored into. That is, if `sinkAp` is `Field1.Field2` (with `Field1`
|
||||
* being the top of the stack), then there is flow into `sink.Field1.Field2`.
|
||||
*/
|
||||
final predicate hasFlow(
|
||||
Node source, AccessPath sourceAp, Node sink, AccessPath sinkAp, boolean preservesValue
|
||||
) {
|
||||
exists(DF::PathNode pathSource, DF::PathNode pathSink |
|
||||
this.(ConfigurationAdapter).hasFlowPath(pathSource, pathSink) and
|
||||
nodeReaches(pathSource, TAccessPathNil(), TAccessPathNil(), pathSink, sourceAp, sinkAp) and
|
||||
source = pathSource.getNode() and
|
||||
sink = pathSink.getNode()
|
||||
|
|
||||
pathSink.getState().(InitState).decode(preservesValue)
|
||||
or
|
||||
pathSink.getState().(ReadState).decode(_, preservesValue)
|
||||
or
|
||||
pathSink.getState().(StoreState).decode(_, preservesValue)
|
||||
)
|
||||
}
|
||||
|
||||
predicate isAdditionalFlowStep(
|
||||
DataFlow::Node node1, FlowState state1, DataFlow::Node node2, FlowState state2
|
||||
) {
|
||||
storeStep(node1, state1, _, node2, state2) or
|
||||
readStep(node1, state1, _, node2, state2) or
|
||||
additionalStep(node1, state1, node2, state2)
|
||||
}
|
||||
|
||||
predicate isAdditionalFlowStep = ContentConfig::isAdditionalFlowStep/2;
|
||||
|
||||
predicate isBarrier = ContentConfig::isBarrier/1;
|
||||
|
||||
predicate isBarrier(DataFlow::Node node, FlowState state) { none() }
|
||||
|
||||
DataFlow::FlowFeature getAFeature() { result = ContentConfig::getAFeature() }
|
||||
|
||||
// needed to record reads/stores inside summarized callables
|
||||
predicate includeHiddenNodes() { any() }
|
||||
}
|
||||
|
||||
private module Flow = DataFlow::GlobalWithState<FlowConfig>;
|
||||
|
||||
/**
|
||||
* Holds if data stored inside `sourceAp` on `source` flows to `sinkAp` inside `sink`
|
||||
* for this configuration. `preservesValue` indicates whether any of the additional
|
||||
* flow steps defined by `isAdditionalFlowStep` are needed.
|
||||
*
|
||||
* For the source access path, `sourceAp`, the top of the stack represents the content
|
||||
* that was last read from. That is, if `sourceAp` is `Field1.Field2` (with `Field1`
|
||||
* being the top of the stack), then there is flow from `source.Field2.Field1`.
|
||||
*
|
||||
* For the sink access path, `sinkAp`, the top of the stack represents the content
|
||||
* that was last stored into. That is, if `sinkAp` is `Field1.Field2` (with `Field1`
|
||||
* being the top of the stack), then there is flow into `sink.Field1.Field2`.
|
||||
*/
|
||||
predicate flow(
|
||||
DataFlow::Node source, AccessPath sourceAp, DataFlow::Node sink, AccessPath sinkAp,
|
||||
boolean preservesValue
|
||||
) {
|
||||
exists(Flow::PathNode pathSource, Flow::PathNode pathSink |
|
||||
Flow::flowPath(pathSource, pathSink) and
|
||||
nodeReaches(pathSource, TAccessPathNil(), TAccessPathNil(), pathSink, sourceAp, sinkAp) and
|
||||
source = pathSource.getNode() and
|
||||
sink = pathSink.getNode()
|
||||
|
|
||||
pathSink.getState().(InitState).decode(preservesValue)
|
||||
or
|
||||
pathSink.getState().(ReadState).decode(_, preservesValue)
|
||||
or
|
||||
pathSink.getState().(StoreState).decode(_, preservesValue)
|
||||
)
|
||||
}
|
||||
|
||||
private newtype TState =
|
||||
TInitState(Boolean preservesValue) or
|
||||
TStoreState(int size, Boolean preservesValue) {
|
||||
size in [1 .. ContentConfig::accessPathLimit()]
|
||||
} or
|
||||
TReadState(int size, Boolean preservesValue) { size in [1 .. ContentConfig::accessPathLimit()] }
|
||||
|
||||
abstract private class State extends TState {
|
||||
abstract string toString();
|
||||
}
|
||||
|
||||
/** A flow state representing no reads or stores. */
|
||||
private class InitState extends State, TInitState {
|
||||
private class InitState extends DF::FlowState {
|
||||
private boolean preservesValue_;
|
||||
|
||||
InitState() { this = TInitState(preservesValue_) }
|
||||
|
||||
override string toString() { result = "Init(" + preservesValue_ + ")" }
|
||||
InitState() { this = "Init(" + preservesValue_ + ")" and preservesValue_ in [false, true] }
|
||||
|
||||
predicate decode(boolean preservesValue) { preservesValue = preservesValue_ }
|
||||
}
|
||||
|
||||
/** A flow state representing that content has been stored into. */
|
||||
private class StoreState extends State, TStoreState {
|
||||
private class StoreState extends DF::FlowState {
|
||||
private boolean preservesValue_;
|
||||
private int size_;
|
||||
|
||||
StoreState() { this = TStoreState(size_, preservesValue_) }
|
||||
|
||||
override string toString() { result = "StoreState(" + size_ + "," + preservesValue_ + ")" }
|
||||
StoreState() {
|
||||
preservesValue_ in [false, true] and
|
||||
size_ in [1 .. any(Configuration c).accessPathLimit()] and
|
||||
this = "StoreState(" + size_ + "," + preservesValue_ + ")"
|
||||
}
|
||||
|
||||
predicate decode(int size, boolean preservesValue) {
|
||||
size = size_ and preservesValue = preservesValue_
|
||||
@@ -185,13 +158,15 @@ module Global<ConfigSig ContentConfig> {
|
||||
}
|
||||
|
||||
/** A flow state representing that content has been read from. */
|
||||
private class ReadState extends State, TReadState {
|
||||
private class ReadState extends DF::FlowState {
|
||||
private boolean preservesValue_;
|
||||
private int size_;
|
||||
|
||||
ReadState() { this = TReadState(size_, preservesValue_) }
|
||||
|
||||
override string toString() { result = "ReadState(" + size_ + "," + preservesValue_ + ")" }
|
||||
ReadState() {
|
||||
preservesValue_ in [false, true] and
|
||||
size_ in [1 .. any(Configuration c).accessPathLimit()] and
|
||||
this = "ReadState(" + size_ + "," + preservesValue_ + ")"
|
||||
}
|
||||
|
||||
predicate decode(int size, boolean preservesValue) {
|
||||
size = size_ and preservesValue = preservesValue_
|
||||
@@ -199,12 +174,12 @@ module Global<ConfigSig ContentConfig> {
|
||||
}
|
||||
|
||||
private predicate storeStep(
|
||||
DataFlow::Node node1, State state1, DataFlow::ContentSet c, DataFlow::Node node2,
|
||||
StoreState state2
|
||||
Node node1, DF::FlowState state1, ContentSet c, Node node2, StoreState state2,
|
||||
Configuration config
|
||||
) {
|
||||
exists(boolean preservesValue, int size |
|
||||
storeSet(node1, c, node2, _, _) and
|
||||
ContentConfig::isRelevantContent(c) and
|
||||
config.isRelevantContent(c) and
|
||||
state2.decode(size + 1, preservesValue)
|
||||
|
|
||||
state1.(InitState).decode(preservesValue) and size = 0
|
||||
@@ -216,12 +191,12 @@ module Global<ConfigSig ContentConfig> {
|
||||
}
|
||||
|
||||
private predicate readStep(
|
||||
DataFlow::Node node1, State state1, DataFlow::ContentSet c, DataFlow::Node node2,
|
||||
ReadState state2
|
||||
Node node1, DF::FlowState state1, ContentSet c, Node node2, ReadState state2,
|
||||
Configuration config
|
||||
) {
|
||||
exists(int size |
|
||||
readSet(node1, c, node2) and
|
||||
ContentConfig::isRelevantContent(c) and
|
||||
config.isRelevantContent(c) and
|
||||
state2.decode(size + 1, true)
|
||||
|
|
||||
state1.(InitState).decode(true) and
|
||||
@@ -232,9 +207,9 @@ module Global<ConfigSig ContentConfig> {
|
||||
}
|
||||
|
||||
private predicate additionalStep(
|
||||
DataFlow::Node node1, State state1, DataFlow::Node node2, State state2
|
||||
Node node1, DF::FlowState state1, Node node2, DF::FlowState state2, Configuration config
|
||||
) {
|
||||
ContentConfig::isAdditionalFlowStep(node1, node2) and
|
||||
config.isAdditionalFlowStep(node1, node2) and
|
||||
(
|
||||
state1 instanceof InitState and
|
||||
state2.(InitState).decode(false)
|
||||
@@ -246,9 +221,40 @@ module Global<ConfigSig ContentConfig> {
|
||||
)
|
||||
}
|
||||
|
||||
private class ConfigurationAdapter extends DF::Configuration instanceof Configuration {
|
||||
final override predicate isSource(Node source, DF::FlowState state) {
|
||||
Configuration.super.isSource(source) and
|
||||
state.(InitState).decode(true)
|
||||
}
|
||||
|
||||
final override predicate isSink(Node sink, DF::FlowState state) {
|
||||
Configuration.super.isSink(sink) and
|
||||
(
|
||||
state instanceof InitState or
|
||||
state instanceof StoreState or
|
||||
state instanceof ReadState
|
||||
)
|
||||
}
|
||||
|
||||
final override predicate isAdditionalFlowStep(
|
||||
Node node1, DF::FlowState state1, Node node2, DF::FlowState state2
|
||||
) {
|
||||
storeStep(node1, state1, _, node2, state2, this) or
|
||||
readStep(node1, state1, _, node2, state2, this) or
|
||||
additionalStep(node1, state1, node2, state2, this)
|
||||
}
|
||||
|
||||
final override predicate isBarrier(Node node) { Configuration.super.isBarrier(node) }
|
||||
|
||||
final override FlowFeature getAFeature() { result = Configuration.super.getAFeature() }
|
||||
|
||||
// needed to record reads/stores inside summarized callables
|
||||
final override predicate includeHiddenNodes() { any() }
|
||||
}
|
||||
|
||||
private newtype TAccessPath =
|
||||
TAccessPathNil() or
|
||||
TAccessPathCons(DataFlow::ContentSet head, AccessPath tail) {
|
||||
TAccessPathCons(ContentSet head, AccessPath tail) {
|
||||
nodeReachesStore(_, _, _, _, head, _, tail)
|
||||
or
|
||||
nodeReachesRead(_, _, _, _, head, tail, _)
|
||||
@@ -257,7 +263,7 @@ module Global<ConfigSig ContentConfig> {
|
||||
/** An access path. */
|
||||
class AccessPath extends TAccessPath {
|
||||
/** Gets the head of this access path, if any. */
|
||||
DataFlow::ContentSet getHead() { this = TAccessPathCons(result, _) }
|
||||
ContentSet getHead() { this = TAccessPathCons(result, _) }
|
||||
|
||||
/** Gets the tail of this access path, if any. */
|
||||
AccessPath getTail() { this = TAccessPathCons(_, result) }
|
||||
@@ -272,7 +278,7 @@ module Global<ConfigSig ContentConfig> {
|
||||
this = TAccessPathNil() and
|
||||
result = ""
|
||||
or
|
||||
exists(DataFlow::ContentSet head, AccessPath tail |
|
||||
exists(ContentSet head, AccessPath tail |
|
||||
this = TAccessPathCons(head, tail) and
|
||||
result = head + "." + tail
|
||||
)
|
||||
@@ -281,7 +287,7 @@ module Global<ConfigSig ContentConfig> {
|
||||
|
||||
// important to use `edges` and not `PathNode::getASuccessor()`, as the latter
|
||||
// is not pruned for reachability
|
||||
private predicate pathSucc = Flow::PathGraph::edges/2;
|
||||
private predicate pathSucc = DF::PathGraph::edges/2;
|
||||
|
||||
/**
|
||||
* Provides a big-step flow relation, where flow stops at read/store steps that
|
||||
@@ -289,10 +295,10 @@ module Global<ConfigSig ContentConfig> {
|
||||
* summarized callables can be recorded as well.
|
||||
*/
|
||||
private module BigStepFlow {
|
||||
private predicate reachesSink(Flow::PathNode node) {
|
||||
FlowConfig::isSink(node.getNode(), node.getState())
|
||||
private predicate reachesSink(DF::PathNode node) {
|
||||
any(ConfigurationAdapter config).isSink(node.getNode(), node.getState())
|
||||
or
|
||||
exists(Flow::PathNode mid |
|
||||
exists(DF::PathNode mid |
|
||||
pathSucc(node, mid) and
|
||||
reachesSink(mid)
|
||||
)
|
||||
@@ -303,72 +309,76 @@ module Global<ConfigSig ContentConfig> {
|
||||
* in the big-step relation.
|
||||
*/
|
||||
pragma[nomagic]
|
||||
private predicate excludeStep(Flow::PathNode pred, Flow::PathNode succ) {
|
||||
private predicate excludeStep(DF::PathNode pred, DF::PathNode succ) {
|
||||
pathSucc(pred, succ) and
|
||||
(
|
||||
// we need to record reads/stores inside summarized callables
|
||||
Flow::PathGraph::subpaths(pred, _, _, succ)
|
||||
DF::PathGraph::subpaths(pred, _, _, succ)
|
||||
or
|
||||
// only allow flow into a summarized callable, as part of the big-step
|
||||
// relation, when flow can reach a sink without going back out
|
||||
Flow::PathGraph::subpaths(pred, succ, _, _) and
|
||||
DF::PathGraph::subpaths(pred, succ, _, _) and
|
||||
not reachesSink(succ)
|
||||
or
|
||||
// needed to record store steps
|
||||
storeStep(pred.getNode(), pred.getState(), _, succ.getNode(), succ.getState())
|
||||
storeStep(pred.getNode(), pred.getState(), _, succ.getNode(), succ.getState(),
|
||||
pred.getConfiguration())
|
||||
or
|
||||
// needed to record read steps
|
||||
readStep(pred.getNode(), pred.getState(), _, succ.getNode(), succ.getState())
|
||||
readStep(pred.getNode(), pred.getState(), _, succ.getNode(), succ.getState(),
|
||||
pred.getConfiguration())
|
||||
)
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
private DataFlowCallable getEnclosingCallableImpl(Flow::PathNode node) {
|
||||
private DataFlowCallable getEnclosingCallableImpl(DF::PathNode node) {
|
||||
result = getNodeEnclosingCallable(node.getNode())
|
||||
}
|
||||
|
||||
pragma[inline]
|
||||
private DataFlowCallable getEnclosingCallable(Flow::PathNode node) {
|
||||
private DataFlowCallable getEnclosingCallable(DF::PathNode node) {
|
||||
pragma[only_bind_into](result) = getEnclosingCallableImpl(pragma[only_bind_out](node))
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate bigStepEntry(Flow::PathNode node) {
|
||||
private predicate bigStepEntry(DF::PathNode node) {
|
||||
node.getConfiguration() instanceof Configuration and
|
||||
(
|
||||
FlowConfig::isSource(node.getNode(), node.getState())
|
||||
any(ConfigurationAdapter config).isSource(node.getNode(), node.getState())
|
||||
or
|
||||
excludeStep(_, node)
|
||||
or
|
||||
Flow::PathGraph::subpaths(_, node, _, _)
|
||||
DF::PathGraph::subpaths(_, node, _, _)
|
||||
)
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate bigStepExit(Flow::PathNode node) {
|
||||
private predicate bigStepExit(DF::PathNode node) {
|
||||
node.getConfiguration() instanceof Configuration and
|
||||
(
|
||||
bigStepEntry(node)
|
||||
or
|
||||
FlowConfig::isSink(node.getNode(), node.getState())
|
||||
any(ConfigurationAdapter config).isSink(node.getNode(), node.getState())
|
||||
or
|
||||
excludeStep(node, _)
|
||||
or
|
||||
Flow::PathGraph::subpaths(_, _, node, _)
|
||||
DF::PathGraph::subpaths(_, _, node, _)
|
||||
)
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate step(Flow::PathNode pred, Flow::PathNode succ) {
|
||||
private predicate step(DF::PathNode pred, DF::PathNode succ) {
|
||||
pathSucc(pred, succ) and
|
||||
not excludeStep(pred, succ)
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate stepRec(Flow::PathNode pred, Flow::PathNode succ) {
|
||||
private predicate stepRec(DF::PathNode pred, DF::PathNode succ) {
|
||||
step(pred, succ) and
|
||||
not bigStepEntry(pred)
|
||||
}
|
||||
|
||||
private predicate stepRecPlus(Flow::PathNode n1, Flow::PathNode n2) = fastTC(stepRec/2)(n1, n2)
|
||||
private predicate stepRecPlus(DF::PathNode n1, DF::PathNode n2) = fastTC(stepRec/2)(n1, n2)
|
||||
|
||||
/**
|
||||
* Holds if there is flow `pathSucc+(pred) = succ`, and such a flow path does
|
||||
@@ -376,8 +386,8 @@ module Global<ConfigSig ContentConfig> {
|
||||
* steps.
|
||||
*/
|
||||
pragma[nomagic]
|
||||
private predicate bigStep(Flow::PathNode pred, Flow::PathNode succ) {
|
||||
exists(Flow::PathNode mid |
|
||||
private predicate bigStep(DF::PathNode pred, DF::PathNode succ) {
|
||||
exists(DF::PathNode mid |
|
||||
bigStepEntry(pred) and
|
||||
step(pred, mid)
|
||||
|
|
||||
@@ -389,13 +399,13 @@ module Global<ConfigSig ContentConfig> {
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
predicate bigStepNotLocal(Flow::PathNode pred, Flow::PathNode succ) {
|
||||
predicate bigStepNotLocal(DF::PathNode pred, DF::PathNode succ) {
|
||||
bigStep(pred, succ) and
|
||||
not getEnclosingCallable(pred) = getEnclosingCallable(succ)
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
predicate bigStepMaybeLocal(Flow::PathNode pred, Flow::PathNode succ) {
|
||||
predicate bigStepMaybeLocal(DF::PathNode pred, DF::PathNode succ) {
|
||||
bigStep(pred, succ) and
|
||||
getEnclosingCallable(pred) = getEnclosingCallable(succ)
|
||||
}
|
||||
@@ -412,54 +422,55 @@ module Global<ConfigSig ContentConfig> {
|
||||
*/
|
||||
pragma[nomagic]
|
||||
private predicate nodeReaches(
|
||||
Flow::PathNode source, AccessPath scReads, AccessPath scStores, Flow::PathNode node,
|
||||
DF::PathNode source, AccessPath scReads, AccessPath scStores, DF::PathNode node,
|
||||
AccessPath reads, AccessPath stores
|
||||
) {
|
||||
node = source and
|
||||
reads = scReads and
|
||||
stores = scStores and
|
||||
(
|
||||
Flow::flowPath(source, _) and
|
||||
exists(ConfigurationAdapter config |
|
||||
node = source and
|
||||
reads = scReads and
|
||||
stores = scStores
|
||||
|
|
||||
config.hasFlowPath(source, _) and
|
||||
scReads = TAccessPathNil() and
|
||||
scStores = TAccessPathNil()
|
||||
or
|
||||
// the argument in a sub path can be reached, so we start flow from the sub path
|
||||
// parameter, while recording the read/store summary context
|
||||
exists(Flow::PathNode arg |
|
||||
exists(DF::PathNode arg |
|
||||
nodeReachesSubpathArg(_, _, _, arg, scReads, scStores) and
|
||||
Flow::PathGraph::subpaths(arg, source, _, _)
|
||||
DF::PathGraph::subpaths(arg, source, _, _)
|
||||
)
|
||||
)
|
||||
or
|
||||
exists(Flow::PathNode mid |
|
||||
exists(DF::PathNode mid |
|
||||
nodeReaches(source, scReads, scStores, mid, reads, stores) and
|
||||
BigStepFlow::bigStepMaybeLocal(mid, node)
|
||||
)
|
||||
or
|
||||
exists(Flow::PathNode mid |
|
||||
exists(DF::PathNode mid |
|
||||
nodeReaches(source, scReads, scStores, mid, reads, stores) and
|
||||
BigStepFlow::bigStepNotLocal(mid, node) and
|
||||
// when flow is not local, we cannot flow back out, so we may stop
|
||||
// flow early when computing summary flow
|
||||
Flow::flowPath(source, _) and
|
||||
any(ConfigurationAdapter config).hasFlowPath(source, _) and
|
||||
scReads = TAccessPathNil() and
|
||||
scStores = TAccessPathNil()
|
||||
)
|
||||
or
|
||||
// store step
|
||||
exists(AccessPath storesMid, DataFlow::ContentSet c |
|
||||
exists(AccessPath storesMid, ContentSet c |
|
||||
nodeReachesStore(source, scReads, scStores, node, c, reads, storesMid) and
|
||||
stores = TAccessPathCons(c, storesMid)
|
||||
)
|
||||
or
|
||||
// read step
|
||||
exists(AccessPath readsMid, DataFlow::ContentSet c |
|
||||
exists(AccessPath readsMid, ContentSet c |
|
||||
nodeReachesRead(source, scReads, scStores, node, c, readsMid, stores) and
|
||||
reads = TAccessPathCons(c, readsMid)
|
||||
)
|
||||
or
|
||||
// flow-through step; match outer stores/reads with inner store/read summary contexts
|
||||
exists(Flow::PathNode mid, AccessPath innerScReads, AccessPath innerScStores |
|
||||
exists(DF::PathNode mid, AccessPath innerScReads, AccessPath innerScStores |
|
||||
nodeReachesSubpathArg(source, scReads, scStores, mid, innerScReads, innerScStores) and
|
||||
subpathArgReachesOut(mid, innerScReads, innerScStores, node, reads, stores)
|
||||
)
|
||||
@@ -467,45 +478,47 @@ module Global<ConfigSig ContentConfig> {
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate nodeReachesStore(
|
||||
Flow::PathNode source, AccessPath scReads, AccessPath scStores, Flow::PathNode node,
|
||||
DataFlow::ContentSet c, AccessPath reads, AccessPath stores
|
||||
DF::PathNode source, AccessPath scReads, AccessPath scStores, DF::PathNode node, ContentSet c,
|
||||
AccessPath reads, AccessPath stores
|
||||
) {
|
||||
exists(Flow::PathNode mid |
|
||||
exists(DF::PathNode mid |
|
||||
nodeReaches(source, scReads, scStores, mid, reads, stores) and
|
||||
storeStep(mid.getNode(), mid.getState(), c, node.getNode(), node.getState()) and
|
||||
storeStep(mid.getNode(), mid.getState(), c, node.getNode(), node.getState(),
|
||||
node.getConfiguration()) and
|
||||
pathSucc(mid, node)
|
||||
)
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate nodeReachesRead(
|
||||
Flow::PathNode source, AccessPath scReads, AccessPath scStores, Flow::PathNode node,
|
||||
DataFlow::ContentSet c, AccessPath reads, AccessPath stores
|
||||
DF::PathNode source, AccessPath scReads, AccessPath scStores, DF::PathNode node, ContentSet c,
|
||||
AccessPath reads, AccessPath stores
|
||||
) {
|
||||
exists(Flow::PathNode mid |
|
||||
exists(DF::PathNode mid |
|
||||
nodeReaches(source, scReads, scStores, mid, reads, stores) and
|
||||
readStep(mid.getNode(), mid.getState(), c, node.getNode(), node.getState()) and
|
||||
readStep(mid.getNode(), mid.getState(), c, node.getNode(), node.getState(),
|
||||
node.getConfiguration()) and
|
||||
pathSucc(mid, node)
|
||||
)
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate nodeReachesSubpathArg(
|
||||
Flow::PathNode source, AccessPath scReads, AccessPath scStores, Flow::PathNode arg,
|
||||
DF::PathNode source, AccessPath scReads, AccessPath scStores, DF::PathNode arg,
|
||||
AccessPath reads, AccessPath stores
|
||||
) {
|
||||
nodeReaches(source, scReads, scStores, arg, reads, stores) and
|
||||
Flow::PathGraph::subpaths(arg, _, _, _)
|
||||
DF::PathGraph::subpaths(arg, _, _, _)
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate subpathArgReachesOut(
|
||||
Flow::PathNode arg, AccessPath scReads, AccessPath scStores, Flow::PathNode out,
|
||||
AccessPath reads, AccessPath stores
|
||||
DF::PathNode arg, AccessPath scReads, AccessPath scStores, DF::PathNode out, AccessPath reads,
|
||||
AccessPath stores
|
||||
) {
|
||||
exists(Flow::PathNode source, Flow::PathNode ret |
|
||||
exists(DF::PathNode source, DF::PathNode ret |
|
||||
nodeReaches(source, scReads, scStores, ret, reads, stores) and
|
||||
Flow::PathGraph::subpaths(arg, source, ret, out)
|
||||
DF::PathGraph::subpaths(arg, source, ret, out)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -815,15 +815,7 @@ private module Cached {
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if data can flow from `node1` to `node2` via a direct assignment to
|
||||
* `c`.
|
||||
*
|
||||
* This includes reverse steps through reads when the result of the read has
|
||||
* been stored into, in order to handle cases like `x.f1.f2 = y`.
|
||||
*/
|
||||
cached
|
||||
predicate store(
|
||||
private predicate store(
|
||||
Node node1, Content c, Node node2, DataFlowType contentType, DataFlowType containerType
|
||||
) {
|
||||
exists(ContentSet cs |
|
||||
@@ -831,6 +823,18 @@ private module Cached {
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if data can flow from `node1` to `node2` via a direct assignment to
|
||||
* `f`.
|
||||
*
|
||||
* This includes reverse steps through reads when the result of the read has
|
||||
* been stored into, in order to handle cases like `x.f1.f2 = y`.
|
||||
*/
|
||||
cached
|
||||
predicate store(Node node1, TypedContent tc, Node node2, DataFlowType contentType) {
|
||||
store(node1, tc.getContent(), node2, contentType, tc.getContainerType())
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if data can flow from `fromNode` to `toNode` because they are the post-update
|
||||
* nodes of some function output and input respectively, where the output and input
|
||||
@@ -928,15 +932,36 @@ private module Cached {
|
||||
TReturnCtxNoFlowThrough() or
|
||||
TReturnCtxMaybeFlowThrough(ReturnPosition pos)
|
||||
|
||||
cached
|
||||
newtype TTypedContentApprox =
|
||||
MkTypedContentApprox(ContentApprox c, DataFlowType t) {
|
||||
exists(Content cont |
|
||||
c = getContentApprox(cont) and
|
||||
store(_, cont, _, _, t)
|
||||
)
|
||||
}
|
||||
|
||||
cached
|
||||
newtype TTypedContent = MkTypedContent(Content c, DataFlowType t) { store(_, c, _, _, t) }
|
||||
|
||||
cached
|
||||
TypedContent getATypedContent(TypedContentApprox c) {
|
||||
exists(ContentApprox cls, DataFlowType t, Content cont |
|
||||
c = MkTypedContentApprox(cls, pragma[only_bind_into](t)) and
|
||||
result = MkTypedContent(cont, pragma[only_bind_into](t)) and
|
||||
cls = getContentApprox(cont)
|
||||
)
|
||||
}
|
||||
|
||||
cached
|
||||
newtype TAccessPathFront =
|
||||
TFrontNil() or
|
||||
TFrontHead(Content c)
|
||||
TFrontNil(DataFlowType t) or
|
||||
TFrontHead(TypedContent tc)
|
||||
|
||||
cached
|
||||
newtype TApproxAccessPathFront =
|
||||
TApproxFrontNil() or
|
||||
TApproxFrontHead(ContentApprox c)
|
||||
TApproxFrontNil(DataFlowType t) or
|
||||
TApproxFrontHead(TypedContentApprox tc)
|
||||
|
||||
cached
|
||||
newtype TAccessPathFrontOption =
|
||||
@@ -961,16 +986,8 @@ predicate recordDataFlowCallSite(DataFlowCall call, DataFlowCallable callable) {
|
||||
/**
|
||||
* A `Node` at which a cast can occur such that the type should be checked.
|
||||
*/
|
||||
class CastingNode instanceof Node {
|
||||
class CastingNode extends Node {
|
||||
CastingNode() { castingNode(this) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
}
|
||||
|
||||
private predicate readStepWithTypes(
|
||||
@@ -1118,17 +1135,9 @@ LocalCallContext getLocalCallContext(CallContext ctx, DataFlowCallable callable)
|
||||
* The value of a parameter at function entry, viewed as a node in a data
|
||||
* flow graph.
|
||||
*/
|
||||
class ParamNode instanceof Node {
|
||||
class ParamNode extends Node {
|
||||
ParamNode() { parameterNode(this, _, _) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if this node is the parameter of callable `c` at the specified
|
||||
* position.
|
||||
@@ -1137,17 +1146,9 @@ class ParamNode instanceof Node {
|
||||
}
|
||||
|
||||
/** A data-flow node that represents a call argument. */
|
||||
class ArgNode instanceof Node {
|
||||
class ArgNode extends Node {
|
||||
ArgNode() { argumentNode(this, _, _) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
|
||||
/** Holds if this argument occurs at the given position in the given call. */
|
||||
final predicate argumentOf(DataFlowCall call, ArgumentPosition pos) {
|
||||
argumentNode(this, call, pos)
|
||||
@@ -1158,17 +1159,9 @@ class ArgNode instanceof Node {
|
||||
* A node from which flow can return to the caller. This is either a regular
|
||||
* `ReturnNode` or a `PostUpdateNode` corresponding to the value of a parameter.
|
||||
*/
|
||||
class ReturnNodeExt instanceof Node {
|
||||
class ReturnNodeExt extends Node {
|
||||
ReturnNodeExt() { returnNodeExt(this, _) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
|
||||
/** Gets the kind of this returned value. */
|
||||
ReturnKindExt getKind() { returnNodeExt(this, result) }
|
||||
}
|
||||
@@ -1177,16 +1170,8 @@ class ReturnNodeExt instanceof Node {
|
||||
* A node to which data can flow from a call. Either an ordinary out node
|
||||
* or a post-update node associated with a call argument.
|
||||
*/
|
||||
class OutNodeExt instanceof Node {
|
||||
class OutNodeExt extends Node {
|
||||
OutNodeExt() { outNodeExt(this) }
|
||||
|
||||
string toString() { result = super.toString() }
|
||||
|
||||
predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1402,37 +1387,67 @@ class ReturnCtx extends TReturnCtx {
|
||||
}
|
||||
}
|
||||
|
||||
/** An approximated `Content` tagged with the type of a containing object. */
|
||||
class TypedContentApprox extends MkTypedContentApprox {
|
||||
private ContentApprox c;
|
||||
private DataFlowType t;
|
||||
|
||||
TypedContentApprox() { this = MkTypedContentApprox(c, t) }
|
||||
|
||||
/** Gets a typed content approximated by this value. */
|
||||
TypedContent getATypedContent() { result = getATypedContent(this) }
|
||||
|
||||
/** Gets the content. */
|
||||
ContentApprox getContent() { result = c }
|
||||
|
||||
/** Gets the container type. */
|
||||
DataFlowType getContainerType() { result = t }
|
||||
|
||||
/** Gets a textual representation of this approximated content. */
|
||||
string toString() { result = c.toString() }
|
||||
}
|
||||
|
||||
/**
|
||||
* The front of an approximated access path. This is either a head or a nil.
|
||||
*/
|
||||
abstract class ApproxAccessPathFront extends TApproxAccessPathFront {
|
||||
abstract string toString();
|
||||
|
||||
abstract DataFlowType getType();
|
||||
|
||||
abstract boolean toBoolNonEmpty();
|
||||
|
||||
ContentApprox getHead() { this = TApproxFrontHead(result) }
|
||||
TypedContentApprox getHead() { this = TApproxFrontHead(result) }
|
||||
|
||||
pragma[nomagic]
|
||||
Content getAHead() {
|
||||
exists(ContentApprox cont |
|
||||
TypedContent getAHead() {
|
||||
exists(TypedContentApprox cont |
|
||||
this = TApproxFrontHead(cont) and
|
||||
cont = getContentApprox(result)
|
||||
result = cont.getATypedContent()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
class ApproxAccessPathFrontNil extends ApproxAccessPathFront, TApproxFrontNil {
|
||||
override string toString() { result = "nil" }
|
||||
private DataFlowType t;
|
||||
|
||||
ApproxAccessPathFrontNil() { this = TApproxFrontNil(t) }
|
||||
|
||||
override string toString() { result = ppReprType(t) }
|
||||
|
||||
override DataFlowType getType() { result = t }
|
||||
|
||||
override boolean toBoolNonEmpty() { result = false }
|
||||
}
|
||||
|
||||
class ApproxAccessPathFrontHead extends ApproxAccessPathFront, TApproxFrontHead {
|
||||
private ContentApprox c;
|
||||
private TypedContentApprox tc;
|
||||
|
||||
ApproxAccessPathFrontHead() { this = TApproxFrontHead(c) }
|
||||
ApproxAccessPathFrontHead() { this = TApproxFrontHead(tc) }
|
||||
|
||||
override string toString() { result = c.toString() }
|
||||
override string toString() { result = tc.toString() }
|
||||
|
||||
override DataFlowType getType() { result = tc.getContainerType() }
|
||||
|
||||
override boolean toBoolNonEmpty() { result = true }
|
||||
}
|
||||
@@ -1446,31 +1461,65 @@ class ApproxAccessPathFrontOption extends TApproxAccessPathFrontOption {
|
||||
}
|
||||
}
|
||||
|
||||
/** A `Content` tagged with the type of a containing object. */
|
||||
class TypedContent extends MkTypedContent {
|
||||
private Content c;
|
||||
private DataFlowType t;
|
||||
|
||||
TypedContent() { this = MkTypedContent(c, t) }
|
||||
|
||||
/** Gets the content. */
|
||||
Content getContent() { result = c }
|
||||
|
||||
/** Gets the container type. */
|
||||
DataFlowType getContainerType() { result = t }
|
||||
|
||||
/** Gets a textual representation of this content. */
|
||||
string toString() { result = c.toString() }
|
||||
|
||||
/**
|
||||
* Holds if access paths with this `TypedContent` at their head always should
|
||||
* be tracked at high precision. This disables adaptive access path precision
|
||||
* for such access paths.
|
||||
*/
|
||||
predicate forceHighPrecision() { forceHighPrecision(c) }
|
||||
}
|
||||
|
||||
/**
|
||||
* The front of an access path. This is either a head or a nil.
|
||||
*/
|
||||
abstract class AccessPathFront extends TAccessPathFront {
|
||||
abstract string toString();
|
||||
|
||||
abstract DataFlowType getType();
|
||||
|
||||
abstract ApproxAccessPathFront toApprox();
|
||||
|
||||
Content getHead() { this = TFrontHead(result) }
|
||||
TypedContent getHead() { this = TFrontHead(result) }
|
||||
}
|
||||
|
||||
class AccessPathFrontNil extends AccessPathFront, TFrontNil {
|
||||
override string toString() { result = "nil" }
|
||||
private DataFlowType t;
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result = TApproxFrontNil() }
|
||||
AccessPathFrontNil() { this = TFrontNil(t) }
|
||||
|
||||
override string toString() { result = ppReprType(t) }
|
||||
|
||||
override DataFlowType getType() { result = t }
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result = TApproxFrontNil(t) }
|
||||
}
|
||||
|
||||
class AccessPathFrontHead extends AccessPathFront, TFrontHead {
|
||||
private Content c;
|
||||
private TypedContent tc;
|
||||
|
||||
AccessPathFrontHead() { this = TFrontHead(c) }
|
||||
AccessPathFrontHead() { this = TFrontHead(tc) }
|
||||
|
||||
override string toString() { result = c.toString() }
|
||||
override string toString() { result = tc.toString() }
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result.getAHead() = c }
|
||||
override DataFlowType getType() { result = tc.getContainerType() }
|
||||
|
||||
override ApproxAccessPathFront toApprox() { result.getAHead() = tc }
|
||||
}
|
||||
|
||||
/** An optional access path front. */
|
||||
|
||||
@@ -0,0 +1,398 @@
|
||||
/**
|
||||
* DEPRECATED: Use `Global` and `GlobalWithState` instead.
|
||||
*
|
||||
* Provides a `Configuration` class backwards-compatible interface to the data
|
||||
* flow library.
|
||||
*/
|
||||
|
||||
private import DataFlowImplCommon
|
||||
private import DataFlowImplSpecific::Private
|
||||
import DataFlowImplSpecific::Public
|
||||
private import DataFlowImpl
|
||||
import DataFlowImplCommonPublic
|
||||
import FlowStateString
|
||||
private import codeql.util.Unit
|
||||
|
||||
/**
|
||||
* A configuration of interprocedural data flow analysis. This defines
|
||||
* sources, sinks, and any other configurable aspect of the analysis. Each
|
||||
* use of the global data flow library must define its own unique extension
|
||||
* of this abstract class. To create a configuration, extend this class with
|
||||
* a subclass whose characteristic predicate is a unique singleton string.
|
||||
* For example, write
|
||||
*
|
||||
* ```ql
|
||||
* class MyAnalysisConfiguration extends DataFlow::Configuration {
|
||||
* MyAnalysisConfiguration() { this = "MyAnalysisConfiguration" }
|
||||
* // Override `isSource` and `isSink`.
|
||||
* // Optionally override `isBarrier`.
|
||||
* // Optionally override `isAdditionalFlowStep`.
|
||||
* }
|
||||
* ```
|
||||
* Conceptually, this defines a graph where the nodes are `DataFlow::Node`s and
|
||||
* the edges are those data-flow steps that preserve the value of the node
|
||||
* along with any additional edges defined by `isAdditionalFlowStep`.
|
||||
* Specifying nodes in `isBarrier` will remove those nodes from the graph, and
|
||||
* specifying nodes in `isBarrierIn` and/or `isBarrierOut` will remove in-going
|
||||
* and/or out-going edges from those nodes, respectively.
|
||||
*
|
||||
* Then, to query whether there is flow between some `source` and `sink`,
|
||||
* write
|
||||
*
|
||||
* ```ql
|
||||
* exists(MyAnalysisConfiguration cfg | cfg.hasFlow(source, sink))
|
||||
* ```
|
||||
*
|
||||
* Multiple configurations can coexist, but two classes extending
|
||||
* `DataFlow::Configuration` should never depend on each other. One of them
|
||||
* should instead depend on a `DataFlow2::Configuration`, a
|
||||
* `DataFlow3::Configuration`, or a `DataFlow4::Configuration`.
|
||||
*/
|
||||
abstract class Configuration extends string {
|
||||
bindingset[this]
|
||||
Configuration() { any() }
|
||||
|
||||
/**
|
||||
* Holds if `source` is a relevant data flow source.
|
||||
*/
|
||||
predicate isSource(Node source) { none() }
|
||||
|
||||
/**
|
||||
* Holds if `source` is a relevant data flow source with the given initial
|
||||
* `state`.
|
||||
*/
|
||||
predicate isSource(Node source, FlowState state) { none() }
|
||||
|
||||
/**
|
||||
* Holds if `sink` is a relevant data flow sink.
|
||||
*/
|
||||
predicate isSink(Node sink) { none() }
|
||||
|
||||
/**
|
||||
* Holds if `sink` is a relevant data flow sink accepting `state`.
|
||||
*/
|
||||
predicate isSink(Node sink, FlowState state) { none() }
|
||||
|
||||
/**
|
||||
* Holds if data flow through `node` is prohibited. This completely removes
|
||||
* `node` from the data flow graph.
|
||||
*/
|
||||
predicate isBarrier(Node node) { none() }
|
||||
|
||||
/**
|
||||
* Holds if data flow through `node` is prohibited when the flow state is
|
||||
* `state`.
|
||||
*/
|
||||
predicate isBarrier(Node node, FlowState state) { none() }
|
||||
|
||||
/** Holds if data flow into `node` is prohibited. */
|
||||
predicate isBarrierIn(Node node) { none() }
|
||||
|
||||
/** Holds if data flow out of `node` is prohibited. */
|
||||
predicate isBarrierOut(Node node) { none() }
|
||||
|
||||
/**
|
||||
* DEPRECATED: Use `isBarrier` and `BarrierGuard` module instead.
|
||||
*
|
||||
* Holds if data flow through nodes guarded by `guard` is prohibited.
|
||||
*/
|
||||
deprecated predicate isBarrierGuard(BarrierGuard guard) { none() }
|
||||
|
||||
/**
|
||||
* DEPRECATED: Use `isBarrier` and `BarrierGuard` module instead.
|
||||
*
|
||||
* Holds if data flow through nodes guarded by `guard` is prohibited when
|
||||
* the flow state is `state`
|
||||
*/
|
||||
deprecated predicate isBarrierGuard(BarrierGuard guard, FlowState state) { none() }
|
||||
|
||||
/**
|
||||
* Holds if data may flow from `node1` to `node2` in addition to the normal data-flow steps.
|
||||
*/
|
||||
predicate isAdditionalFlowStep(Node node1, Node node2) { none() }
|
||||
|
||||
/**
|
||||
* Holds if data may flow from `node1` to `node2` in addition to the normal data-flow steps.
|
||||
* This step is only applicable in `state1` and updates the flow state to `state2`.
|
||||
*/
|
||||
predicate isAdditionalFlowStep(Node node1, FlowState state1, Node node2, FlowState state2) {
|
||||
none()
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if an arbitrary number of implicit read steps of content `c` may be
|
||||
* taken at `node`.
|
||||
*/
|
||||
predicate allowImplicitRead(Node node, ContentSet c) { none() }
|
||||
|
||||
/**
|
||||
* Gets the virtual dispatch branching limit when calculating field flow.
|
||||
* This can be overridden to a smaller value to improve performance (a
|
||||
* value of 0 disables field flow), or a larger value to get more results.
|
||||
*/
|
||||
int fieldFlowBranchLimit() { result = 2 }
|
||||
|
||||
/**
|
||||
* Gets a data flow configuration feature to add restrictions to the set of
|
||||
* valid flow paths.
|
||||
*
|
||||
* - `FeatureHasSourceCallContext`:
|
||||
* Assume that sources have some existing call context to disallow
|
||||
* conflicting return-flow directly following the source.
|
||||
* - `FeatureHasSinkCallContext`:
|
||||
* Assume that sinks have some existing call context to disallow
|
||||
* conflicting argument-to-parameter flow directly preceding the sink.
|
||||
* - `FeatureEqualSourceSinkCallContext`:
|
||||
* Implies both of the above and additionally ensures that the entire flow
|
||||
* path preserves the call context.
|
||||
*
|
||||
* These features are generally not relevant for typical end-to-end data flow
|
||||
* queries, but should only be used for constructing paths that need to
|
||||
* somehow be pluggable in another path context.
|
||||
*/
|
||||
FlowFeature getAFeature() { none() }
|
||||
|
||||
/** Holds if sources should be grouped in the result of `hasFlowPath`. */
|
||||
predicate sourceGrouping(Node source, string sourceGroup) { none() }
|
||||
|
||||
/** Holds if sinks should be grouped in the result of `hasFlowPath`. */
|
||||
predicate sinkGrouping(Node sink, string sinkGroup) { none() }
|
||||
|
||||
/**
|
||||
* Holds if data may flow from `source` to `sink` for this configuration.
|
||||
*/
|
||||
predicate hasFlow(Node source, Node sink) { hasFlow(source, sink, this) }
|
||||
|
||||
/**
|
||||
* Holds if data may flow from `source` to `sink` for this configuration.
|
||||
*
|
||||
* The corresponding paths are generated from the end-points and the graph
|
||||
* included in the module `PathGraph`.
|
||||
*/
|
||||
predicate hasFlowPath(PathNode source, PathNode sink) { hasFlowPath(source, sink, this) }
|
||||
|
||||
/**
|
||||
* Holds if data may flow from some source to `sink` for this configuration.
|
||||
*/
|
||||
predicate hasFlowTo(Node sink) { hasFlowTo(sink, this) }
|
||||
|
||||
/**
|
||||
* Holds if data may flow from some source to `sink` for this configuration.
|
||||
*/
|
||||
predicate hasFlowToExpr(DataFlowExpr sink) { this.hasFlowTo(exprNode(sink)) }
|
||||
|
||||
/**
|
||||
* DEPRECATED: Use `FlowExploration<explorationLimit>` instead.
|
||||
*
|
||||
* Gets the exploration limit for `hasPartialFlow` and `hasPartialFlowRev`
|
||||
* measured in approximate number of interprocedural steps.
|
||||
*/
|
||||
deprecated int explorationLimit() { none() }
|
||||
|
||||
/**
|
||||
* Holds if hidden nodes should be included in the data flow graph.
|
||||
*
|
||||
* This feature should only be used for debugging or when the data flow graph
|
||||
* is not visualized (for example in a `path-problem` query).
|
||||
*/
|
||||
predicate includeHiddenNodes() { none() }
|
||||
}
|
||||
|
||||
/**
|
||||
* This class exists to prevent mutual recursion between the user-overridden
|
||||
* member predicates of `Configuration` and the rest of the data-flow library.
|
||||
* Good performance cannot be guaranteed in the presence of such recursion, so
|
||||
* it should be replaced by using more than one copy of the data flow library.
|
||||
*/
|
||||
abstract private class ConfigurationRecursionPrevention extends Configuration {
|
||||
bindingset[this]
|
||||
ConfigurationRecursionPrevention() { any() }
|
||||
|
||||
override predicate hasFlow(Node source, Node sink) {
|
||||
strictcount(Node n | this.isSource(n)) < 0
|
||||
or
|
||||
strictcount(Node n | this.isSource(n, _)) < 0
|
||||
or
|
||||
strictcount(Node n | this.isSink(n)) < 0
|
||||
or
|
||||
strictcount(Node n | this.isSink(n, _)) < 0
|
||||
or
|
||||
strictcount(Node n1, Node n2 | this.isAdditionalFlowStep(n1, n2)) < 0
|
||||
or
|
||||
strictcount(Node n1, Node n2 | this.isAdditionalFlowStep(n1, _, n2, _)) < 0
|
||||
or
|
||||
super.hasFlow(source, sink)
|
||||
}
|
||||
}
|
||||
|
||||
/** A bridge class to access the deprecated `isBarrierGuard`. */
|
||||
private class BarrierGuardGuardedNodeBridge extends Unit {
|
||||
abstract predicate guardedNode(Node n, Configuration config);
|
||||
|
||||
abstract predicate guardedNode(Node n, FlowState state, Configuration config);
|
||||
}
|
||||
|
||||
private class BarrierGuardGuardedNode extends BarrierGuardGuardedNodeBridge {
|
||||
deprecated override predicate guardedNode(Node n, Configuration config) {
|
||||
exists(BarrierGuard g |
|
||||
config.isBarrierGuard(g) and
|
||||
n = g.getAGuardedNode()
|
||||
)
|
||||
}
|
||||
|
||||
deprecated override predicate guardedNode(Node n, FlowState state, Configuration config) {
|
||||
exists(BarrierGuard g |
|
||||
config.isBarrierGuard(g, state) and
|
||||
n = g.getAGuardedNode()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
private FlowState relevantState(Configuration config) {
|
||||
config.isSource(_, result) or
|
||||
config.isSink(_, result) or
|
||||
config.isBarrier(_, result) or
|
||||
config.isAdditionalFlowStep(_, result, _, _) or
|
||||
config.isAdditionalFlowStep(_, _, _, result)
|
||||
}
|
||||
|
||||
private newtype TConfigState =
|
||||
TMkConfigState(Configuration config, FlowState state) {
|
||||
state = relevantState(config) or state instanceof FlowStateEmpty
|
||||
}
|
||||
|
||||
private Configuration getConfig(TConfigState state) { state = TMkConfigState(result, _) }
|
||||
|
||||
private FlowState getState(TConfigState state) { state = TMkConfigState(_, result) }
|
||||
|
||||
private predicate singleConfiguration() { 1 = strictcount(Configuration c) }
|
||||
|
||||
private module Config implements FullStateConfigSig {
|
||||
class FlowState = TConfigState;
|
||||
|
||||
predicate isSource(Node source, FlowState state) {
|
||||
getConfig(state).isSource(source, getState(state))
|
||||
or
|
||||
getConfig(state).isSource(source) and getState(state) instanceof FlowStateEmpty
|
||||
}
|
||||
|
||||
predicate isSink(Node sink, FlowState state) {
|
||||
getConfig(state).isSink(sink, getState(state))
|
||||
or
|
||||
getConfig(state).isSink(sink) and getState(state) instanceof FlowStateEmpty
|
||||
}
|
||||
|
||||
predicate isBarrier(Node node) { none() }
|
||||
|
||||
predicate isBarrier(Node node, FlowState state) {
|
||||
getConfig(state).isBarrier(node, getState(state)) or
|
||||
getConfig(state).isBarrier(node) or
|
||||
any(BarrierGuardGuardedNodeBridge b).guardedNode(node, getState(state), getConfig(state)) or
|
||||
any(BarrierGuardGuardedNodeBridge b).guardedNode(node, getConfig(state))
|
||||
}
|
||||
|
||||
predicate isBarrierIn(Node node) { any(Configuration config).isBarrierIn(node) }
|
||||
|
||||
predicate isBarrierOut(Node node) { any(Configuration config).isBarrierOut(node) }
|
||||
|
||||
predicate isAdditionalFlowStep(Node node1, Node node2) {
|
||||
singleConfiguration() and
|
||||
any(Configuration config).isAdditionalFlowStep(node1, node2)
|
||||
}
|
||||
|
||||
predicate isAdditionalFlowStep(Node node1, FlowState state1, Node node2, FlowState state2) {
|
||||
getConfig(state1).isAdditionalFlowStep(node1, getState(state1), node2, getState(state2)) and
|
||||
getConfig(state2) = getConfig(state1)
|
||||
or
|
||||
not singleConfiguration() and
|
||||
getConfig(state1).isAdditionalFlowStep(node1, node2) and
|
||||
state2 = state1
|
||||
}
|
||||
|
||||
predicate allowImplicitRead(Node node, ContentSet c) {
|
||||
any(Configuration config).allowImplicitRead(node, c)
|
||||
}
|
||||
|
||||
int fieldFlowBranchLimit() { result = min(any(Configuration config).fieldFlowBranchLimit()) }
|
||||
|
||||
FlowFeature getAFeature() { result = any(Configuration config).getAFeature() }
|
||||
|
||||
predicate sourceGrouping(Node source, string sourceGroup) {
|
||||
any(Configuration config).sourceGrouping(source, sourceGroup)
|
||||
}
|
||||
|
||||
predicate sinkGrouping(Node sink, string sinkGroup) {
|
||||
any(Configuration config).sinkGrouping(sink, sinkGroup)
|
||||
}
|
||||
|
||||
predicate includeHiddenNodes() { any(Configuration config).includeHiddenNodes() }
|
||||
}
|
||||
|
||||
private import Impl<Config> as I
|
||||
|
||||
/**
|
||||
* A `Node` augmented with a call context (except for sinks), an access path, and a configuration.
|
||||
* Only those `PathNode`s that are reachable from a source, and which can reach a sink, are generated.
|
||||
*/
|
||||
class PathNode instanceof I::PathNode {
|
||||
/** Gets a textual representation of this element. */
|
||||
final string toString() { result = super.toString() }
|
||||
|
||||
/**
|
||||
* Gets a textual representation of this element, including a textual
|
||||
* representation of the call context.
|
||||
*/
|
||||
final string toStringWithContext() { result = super.toStringWithContext() }
|
||||
|
||||
/**
|
||||
* Holds if this element is at the specified location.
|
||||
* The location spans column `startcolumn` of line `startline` to
|
||||
* column `endcolumn` of line `endline` in file `filepath`.
|
||||
* For more information, see
|
||||
* [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
|
||||
*/
|
||||
final predicate hasLocationInfo(
|
||||
string filepath, int startline, int startcolumn, int endline, int endcolumn
|
||||
) {
|
||||
super.hasLocationInfo(filepath, startline, startcolumn, endline, endcolumn)
|
||||
}
|
||||
|
||||
/** Gets the underlying `Node`. */
|
||||
final Node getNode() { result = super.getNode() }
|
||||
|
||||
/** Gets the `FlowState` of this node. */
|
||||
final FlowState getState() { result = getState(super.getState()) }
|
||||
|
||||
/** Gets the associated configuration. */
|
||||
final Configuration getConfiguration() { result = getConfig(super.getState()) }
|
||||
|
||||
/** Gets a successor of this node, if any. */
|
||||
final PathNode getASuccessor() { result = super.getASuccessor() }
|
||||
|
||||
/** Holds if this node is a source. */
|
||||
final predicate isSource() { super.isSource() }
|
||||
|
||||
/** Holds if this node is a grouping of source nodes. */
|
||||
final predicate isSourceGroup(string group) { super.isSourceGroup(group) }
|
||||
|
||||
/** Holds if this node is a grouping of sink nodes. */
|
||||
final predicate isSinkGroup(string group) { super.isSinkGroup(group) }
|
||||
}
|
||||
|
||||
module PathGraph = I::PathGraph;
|
||||
|
||||
private predicate hasFlow(Node source, Node sink, Configuration config) {
|
||||
exists(PathNode source0, PathNode sink0 |
|
||||
hasFlowPath(source0, sink0, config) and
|
||||
source0.getNode() = source and
|
||||
sink0.getNode() = sink
|
||||
)
|
||||
}
|
||||
|
||||
private predicate hasFlowPath(PathNode source, PathNode sink, Configuration config) {
|
||||
I::flowPath(source, sink) and source.getConfiguration() = config
|
||||
}
|
||||
|
||||
private predicate hasFlowTo(Node sink, Configuration config) { hasFlow(_, sink, config) }
|
||||
|
||||
predicate flowsTo = hasFlow/3;
|
||||
@@ -1,9 +1,3 @@
|
||||
## 0.6.1
|
||||
|
||||
### Minor Analysis Improvements
|
||||
|
||||
* Additional sinks modelling writes to unencrypted local files have been added to `ExternalLocationSink`, used by the `cs/cleartext-storage` and `cs/exposure-of-sensitive-information` queries.
|
||||
|
||||
## 0.6.0
|
||||
|
||||
### Minor Analysis Improvements
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
## 0.6.1
|
||||
|
||||
### Minor Analysis Improvements
|
||||
|
||||
* Additional sinks modelling writes to unencrypted local files have been added to `ExternalLocationSink`, used by the `cs/cleartext-storage` and `cs/exposure-of-sensitive-information` queries.
|
||||
---
|
||||
category: minorAnalysis
|
||||
---
|
||||
* Additional sinks modelling writes to unencrypted local files have been added to `ExternalLocationSink`, used by the `cs/cleartext-storage` and `cs/exposure-of-sensitive-information` queries.
|
||||
@@ -1,2 +1,2 @@
|
||||
---
|
||||
lastReleaseVersion: 0.6.1
|
||||
lastReleaseVersion: 0.6.0
|
||||
|
||||
@@ -6,7 +6,7 @@ private import IRFunctionBaseInternal
|
||||
|
||||
private newtype TIRFunction =
|
||||
TFunctionIRFunction(Language::Function func) { IRConstruction::Raw::functionHasIR(func) } or
|
||||
TVarInitIRFunction(Language::Variable var) { IRConstruction::Raw::varHasIRFunc(var) }
|
||||
TVarInitIRFunction(Language::GlobalVariable var) { IRConstruction::Raw::varHasIRFunc(var) }
|
||||
|
||||
/**
|
||||
* The IR for a function. This base class contains only the predicates that are the same between all
|
||||
|
||||
@@ -19,6 +19,9 @@ newtype TInstruction =
|
||||
) {
|
||||
IRConstruction::Raw::hasInstruction(tag1, tag2)
|
||||
} or
|
||||
TRawUnreachedInstruction(IRFunctionBase irFunc) {
|
||||
IRConstruction::hasUnreachedInstruction(irFunc)
|
||||
} or
|
||||
TUnaliasedSsaPhiInstruction(
|
||||
TRawInstruction blockStartInstr, UnaliasedSsa::Ssa::MemoryLocation memoryLocation
|
||||
) {
|
||||
|
||||
@@ -414,6 +414,8 @@ private module Cached {
|
||||
}
|
||||
}
|
||||
|
||||
predicate hasUnreachedInstruction(IRFunction func) { none() }
|
||||
|
||||
import CachedForDebugging
|
||||
|
||||
cached
|
||||
|
||||
@@ -34,9 +34,13 @@ private module Cached {
|
||||
|
||||
cached
|
||||
predicate hasUnreachedInstructionCached(IRFunction irFunc) {
|
||||
exists(OldInstruction oldInstruction |
|
||||
exists(OldIR::Instruction oldInstruction |
|
||||
irFunc = oldInstruction.getEnclosingIRFunction() and
|
||||
Reachability::isInfeasibleInstructionSuccessor(oldInstruction, _)
|
||||
(
|
||||
Reachability::isInfeasibleInstructionSuccessor(oldInstruction, _)
|
||||
or
|
||||
oldInstruction.getOpcode() instanceof Opcode::Unreached
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
@@ -366,21 +370,19 @@ private module Cached {
|
||||
then
|
||||
result = getChi(getOldInstruction(instruction)) and
|
||||
kind instanceof GotoEdge
|
||||
else (
|
||||
else
|
||||
exists(OldInstruction oldInstruction |
|
||||
oldInstruction = getOldInstruction(instruction) and
|
||||
(
|
||||
oldInstruction = getOldInstruction(instruction)
|
||||
or
|
||||
instruction = getChi(oldInstruction)
|
||||
) and
|
||||
(
|
||||
if Reachability::isInfeasibleInstructionSuccessor(oldInstruction, kind)
|
||||
then result = unreachedInstruction(instruction.getEnclosingIRFunction())
|
||||
else result = getNewInstruction(oldInstruction.getSuccessor(kind))
|
||||
)
|
||||
)
|
||||
or
|
||||
exists(OldInstruction oldInstruction |
|
||||
instruction = getChi(oldInstruction) and
|
||||
result = getNewInstruction(oldInstruction.getSuccessor(kind))
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
cached
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
name: codeql/csharp-queries
|
||||
version: 0.6.2-dev
|
||||
version: 0.6.1-dev
|
||||
groups:
|
||||
- csharp
|
||||
- queries
|
||||
|
||||
@@ -139,9 +139,9 @@ module ThroughFlowConfig implements DataFlow::StateConfigSig {
|
||||
predicate isAdditionalFlowStep(
|
||||
DataFlow::Node node1, FlowState state1, DataFlow::Node node2, FlowState state2
|
||||
) {
|
||||
exists(DataFlow::Content c |
|
||||
DataFlowImplCommon::store(node1, c, node2, _, _) and
|
||||
isRelevantContent(c) and
|
||||
exists(DataFlowImplCommon::TypedContent tc |
|
||||
DataFlowImplCommon::store(node1, tc, node2, _) and
|
||||
isRelevantContent(tc.getContent()) and
|
||||
(
|
||||
state1 instanceof TaintRead and state2.(TaintStore).getStep() = 1
|
||||
or
|
||||
@@ -178,7 +178,7 @@ string captureThroughFlow(DataFlowTargetApi api) {
|
||||
string output
|
||||
|
|
||||
ThroughFlow::flow(p, returnNodeExt) and
|
||||
returnNodeExt.(DataFlow::Node).getEnclosingCallable() = api and
|
||||
returnNodeExt.getEnclosingCallable() = api and
|
||||
input = parameterNodeAsInput(p) and
|
||||
output = returnNodeAsOutput(returnNodeExt) and
|
||||
input != output and
|
||||
|
||||
@@ -121,7 +121,7 @@ class InstanceParameterNode = DataFlowPrivate::InstanceParameterNode;
|
||||
|
||||
pragma[nomagic]
|
||||
private CS::Parameter getParameter(DataFlowImplCommon::ReturnNodeExt node, ParameterPosition pos) {
|
||||
result = node.(DataFlow::Node).getEnclosingCallable().getParameter(pos.getPosition())
|
||||
result = node.getEnclosingCallable().getParameter(pos.getPosition())
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -7,11 +7,11 @@ edges
|
||||
| CSharp7.cs:55:11:55:19 | "tainted" : String | CSharp7.cs:55:30:55:31 | SSA def(t4) : String |
|
||||
| CSharp7.cs:55:30:55:31 | SSA def(t4) : String | CSharp7.cs:56:18:56:19 | access to local variable t4 |
|
||||
| CSharp7.cs:80:21:80:21 | x : String | CSharp7.cs:82:20:82:20 | access to parameter x : String |
|
||||
| CSharp7.cs:82:16:82:24 | (..., ...) : ValueTuple<String,Int32> [field Item1] : String | CSharp7.cs:82:16:82:26 | access to field Item1 : String |
|
||||
| CSharp7.cs:82:20:82:20 | access to parameter x : String | CSharp7.cs:82:16:82:24 | (..., ...) : ValueTuple<String,Int32> [field Item1] : String |
|
||||
| CSharp7.cs:87:18:87:34 | (..., ...) : ValueTuple<String,String> [field Item1] : String | CSharp7.cs:90:20:90:21 | access to local variable t1 : ValueTuple<String,String> [field Item1] : String |
|
||||
| CSharp7.cs:87:19:87:27 | "tainted" : String | CSharp7.cs:87:18:87:34 | (..., ...) : ValueTuple<String,String> [field Item1] : String |
|
||||
| CSharp7.cs:90:20:90:21 | access to local variable t1 : ValueTuple<String,String> [field Item1] : String | CSharp7.cs:90:20:90:27 | access to field Item1 : String |
|
||||
| CSharp7.cs:82:16:82:24 | (..., ...) [field Item1] : String | CSharp7.cs:82:16:82:26 | access to field Item1 : String |
|
||||
| CSharp7.cs:82:20:82:20 | access to parameter x : String | CSharp7.cs:82:16:82:24 | (..., ...) [field Item1] : String |
|
||||
| CSharp7.cs:87:18:87:34 | (..., ...) [field Item1] : String | CSharp7.cs:90:20:90:21 | access to local variable t1 [field Item1] : String |
|
||||
| CSharp7.cs:87:19:87:27 | "tainted" : String | CSharp7.cs:87:18:87:34 | (..., ...) [field Item1] : String |
|
||||
| CSharp7.cs:90:20:90:21 | access to local variable t1 [field Item1] : String | CSharp7.cs:90:20:90:27 | access to field Item1 : String |
|
||||
| CSharp7.cs:90:20:90:27 | access to field Item1 : String | CSharp7.cs:80:21:80:21 | x : String |
|
||||
| CSharp7.cs:90:20:90:27 | access to field Item1 : String | CSharp7.cs:90:18:90:28 | call to method I |
|
||||
| CSharp7.cs:175:22:175:30 | "tainted" : String | CSharp7.cs:181:23:181:25 | access to local variable src : String |
|
||||
@@ -33,13 +33,13 @@ nodes
|
||||
| CSharp7.cs:55:30:55:31 | SSA def(t4) : String | semmle.label | SSA def(t4) : String |
|
||||
| CSharp7.cs:56:18:56:19 | access to local variable t4 | semmle.label | access to local variable t4 |
|
||||
| CSharp7.cs:80:21:80:21 | x : String | semmle.label | x : String |
|
||||
| CSharp7.cs:82:16:82:24 | (..., ...) : ValueTuple<String,Int32> [field Item1] : String | semmle.label | (..., ...) : ValueTuple<String,Int32> [field Item1] : String |
|
||||
| CSharp7.cs:82:16:82:24 | (..., ...) [field Item1] : String | semmle.label | (..., ...) [field Item1] : String |
|
||||
| CSharp7.cs:82:16:82:26 | access to field Item1 : String | semmle.label | access to field Item1 : String |
|
||||
| CSharp7.cs:82:20:82:20 | access to parameter x : String | semmle.label | access to parameter x : String |
|
||||
| CSharp7.cs:87:18:87:34 | (..., ...) : ValueTuple<String,String> [field Item1] : String | semmle.label | (..., ...) : ValueTuple<String,String> [field Item1] : String |
|
||||
| CSharp7.cs:87:18:87:34 | (..., ...) [field Item1] : String | semmle.label | (..., ...) [field Item1] : String |
|
||||
| CSharp7.cs:87:19:87:27 | "tainted" : String | semmle.label | "tainted" : String |
|
||||
| CSharp7.cs:90:18:90:28 | call to method I | semmle.label | call to method I |
|
||||
| CSharp7.cs:90:20:90:21 | access to local variable t1 : ValueTuple<String,String> [field Item1] : String | semmle.label | access to local variable t1 : ValueTuple<String,String> [field Item1] : String |
|
||||
| CSharp7.cs:90:20:90:21 | access to local variable t1 [field Item1] : String | semmle.label | access to local variable t1 [field Item1] : String |
|
||||
| CSharp7.cs:90:20:90:27 | access to field Item1 : String | semmle.label | access to field Item1 : String |
|
||||
| CSharp7.cs:175:22:175:30 | "tainted" | semmle.label | "tainted" |
|
||||
| CSharp7.cs:175:22:175:30 | "tainted" : String | semmle.label | "tainted" : String |
|
||||
|
||||
@@ -7,11 +7,11 @@ edges
|
||||
| CSharp7.cs:55:11:55:19 | "tainted" : String | CSharp7.cs:55:30:55:31 | SSA def(t4) : String |
|
||||
| CSharp7.cs:55:30:55:31 | SSA def(t4) : String | CSharp7.cs:56:18:56:19 | access to local variable t4 |
|
||||
| CSharp7.cs:80:21:80:21 | x : String | CSharp7.cs:82:20:82:20 | access to parameter x : String |
|
||||
| CSharp7.cs:82:16:82:24 | (..., ...) : ValueTuple<String,Int32> [field Item1] : String | CSharp7.cs:82:16:82:26 | access to field Item1 : String |
|
||||
| CSharp7.cs:82:20:82:20 | access to parameter x : String | CSharp7.cs:82:16:82:24 | (..., ...) : ValueTuple<String,Int32> [field Item1] : String |
|
||||
| CSharp7.cs:87:18:87:34 | (..., ...) : ValueTuple<String,String> [field Item1] : String | CSharp7.cs:90:20:90:21 | access to local variable t1 : ValueTuple<String,String> [field Item1] : String |
|
||||
| CSharp7.cs:87:19:87:27 | "tainted" : String | CSharp7.cs:87:18:87:34 | (..., ...) : ValueTuple<String,String> [field Item1] : String |
|
||||
| CSharp7.cs:90:20:90:21 | access to local variable t1 : ValueTuple<String,String> [field Item1] : String | CSharp7.cs:90:20:90:27 | access to field Item1 : String |
|
||||
| CSharp7.cs:82:16:82:24 | (..., ...) [field Item1] : String | CSharp7.cs:82:16:82:26 | access to field Item1 : String |
|
||||
| CSharp7.cs:82:20:82:20 | access to parameter x : String | CSharp7.cs:82:16:82:24 | (..., ...) [field Item1] : String |
|
||||
| CSharp7.cs:87:18:87:34 | (..., ...) [field Item1] : String | CSharp7.cs:90:20:90:21 | access to local variable t1 [field Item1] : String |
|
||||
| CSharp7.cs:87:19:87:27 | "tainted" : String | CSharp7.cs:87:18:87:34 | (..., ...) [field Item1] : String |
|
||||
| CSharp7.cs:90:20:90:21 | access to local variable t1 [field Item1] : String | CSharp7.cs:90:20:90:27 | access to field Item1 : String |
|
||||
| CSharp7.cs:90:20:90:27 | access to field Item1 : String | CSharp7.cs:80:21:80:21 | x : String |
|
||||
| CSharp7.cs:90:20:90:27 | access to field Item1 : String | CSharp7.cs:90:18:90:28 | call to method I |
|
||||
| CSharp7.cs:175:22:175:30 | "tainted" : String | CSharp7.cs:180:23:180:25 | access to local variable src : String |
|
||||
@@ -40,13 +40,13 @@ nodes
|
||||
| CSharp7.cs:55:30:55:31 | SSA def(t4) : String | semmle.label | SSA def(t4) : String |
|
||||
| CSharp7.cs:56:18:56:19 | access to local variable t4 | semmle.label | access to local variable t4 |
|
||||
| CSharp7.cs:80:21:80:21 | x : String | semmle.label | x : String |
|
||||
| CSharp7.cs:82:16:82:24 | (..., ...) : ValueTuple<String,Int32> [field Item1] : String | semmle.label | (..., ...) : ValueTuple<String,Int32> [field Item1] : String |
|
||||
| CSharp7.cs:82:16:82:24 | (..., ...) [field Item1] : String | semmle.label | (..., ...) [field Item1] : String |
|
||||
| CSharp7.cs:82:16:82:26 | access to field Item1 : String | semmle.label | access to field Item1 : String |
|
||||
| CSharp7.cs:82:20:82:20 | access to parameter x : String | semmle.label | access to parameter x : String |
|
||||
| CSharp7.cs:87:18:87:34 | (..., ...) : ValueTuple<String,String> [field Item1] : String | semmle.label | (..., ...) : ValueTuple<String,String> [field Item1] : String |
|
||||
| CSharp7.cs:87:18:87:34 | (..., ...) [field Item1] : String | semmle.label | (..., ...) [field Item1] : String |
|
||||
| CSharp7.cs:87:19:87:27 | "tainted" : String | semmle.label | "tainted" : String |
|
||||
| CSharp7.cs:90:18:90:28 | call to method I | semmle.label | call to method I |
|
||||
| CSharp7.cs:90:20:90:21 | access to local variable t1 : ValueTuple<String,String> [field Item1] : String | semmle.label | access to local variable t1 : ValueTuple<String,String> [field Item1] : String |
|
||||
| CSharp7.cs:90:20:90:21 | access to local variable t1 [field Item1] : String | semmle.label | access to local variable t1 [field Item1] : String |
|
||||
| CSharp7.cs:90:20:90:27 | access to field Item1 : String | semmle.label | access to field Item1 : String |
|
||||
| CSharp7.cs:175:22:175:30 | "tainted" | semmle.label | "tainted" |
|
||||
| CSharp7.cs:175:22:175:30 | "tainted" : String | semmle.label | "tainted" : String |
|
||||
|
||||
@@ -6,34 +6,34 @@ edges
|
||||
| Async.cs:14:34:14:34 | x : String | Async.cs:16:16:16:16 | access to parameter x : String |
|
||||
| Async.cs:16:16:16:16 | access to parameter x : String | Async.cs:11:14:11:26 | call to method Return |
|
||||
| Async.cs:19:41:19:45 | input : String | Async.cs:21:32:21:36 | access to parameter input : String |
|
||||
| Async.cs:21:20:21:37 | call to method ReturnAwait : Task<String> [property Result] : String | Async.cs:21:14:21:37 | await ... |
|
||||
| Async.cs:21:32:21:36 | access to parameter input : String | Async.cs:21:20:21:37 | call to method ReturnAwait : Task<String> [property Result] : String |
|
||||
| Async.cs:21:20:21:37 | call to method ReturnAwait [property Result] : String | Async.cs:21:14:21:37 | await ... |
|
||||
| Async.cs:21:32:21:36 | access to parameter input : String | Async.cs:21:20:21:37 | call to method ReturnAwait [property Result] : String |
|
||||
| Async.cs:21:32:21:36 | access to parameter input : String | Async.cs:35:51:35:51 | x : String |
|
||||
| Async.cs:24:41:24:45 | input : String | Async.cs:26:35:26:39 | access to parameter input : String |
|
||||
| Async.cs:26:17:26:40 | await ... : String | Async.cs:27:14:27:14 | access to local variable x |
|
||||
| Async.cs:26:23:26:40 | call to method ReturnAwait : Task<String> [property Result] : String | Async.cs:26:17:26:40 | await ... : String |
|
||||
| Async.cs:26:35:26:39 | access to parameter input : String | Async.cs:26:23:26:40 | call to method ReturnAwait : Task<String> [property Result] : String |
|
||||
| Async.cs:26:23:26:40 | call to method ReturnAwait [property Result] : String | Async.cs:26:17:26:40 | await ... : String |
|
||||
| Async.cs:26:35:26:39 | access to parameter input : String | Async.cs:26:23:26:40 | call to method ReturnAwait [property Result] : String |
|
||||
| Async.cs:26:35:26:39 | access to parameter input : String | Async.cs:35:51:35:51 | x : String |
|
||||
| Async.cs:30:35:30:39 | input : String | Async.cs:32:27:32:31 | access to parameter input : String |
|
||||
| Async.cs:32:14:32:32 | call to method ReturnAwait2 : Task<String> [property Result] : String | Async.cs:32:14:32:39 | access to property Result |
|
||||
| Async.cs:32:27:32:31 | access to parameter input : String | Async.cs:32:14:32:32 | call to method ReturnAwait2 : Task<String> [property Result] : String |
|
||||
| Async.cs:32:14:32:32 | call to method ReturnAwait2 [property Result] : String | Async.cs:32:14:32:39 | access to property Result |
|
||||
| Async.cs:32:27:32:31 | access to parameter input : String | Async.cs:32:14:32:32 | call to method ReturnAwait2 [property Result] : String |
|
||||
| Async.cs:32:27:32:31 | access to parameter input : String | Async.cs:51:52:51:52 | x : String |
|
||||
| Async.cs:35:51:35:51 | x : String | Async.cs:38:16:38:16 | access to parameter x : String |
|
||||
| Async.cs:35:51:35:51 | x : String | Async.cs:38:16:38:16 | access to parameter x : String |
|
||||
| Async.cs:38:16:38:16 | access to parameter x : String | Async.cs:21:20:21:37 | call to method ReturnAwait : Task<String> [property Result] : String |
|
||||
| Async.cs:38:16:38:16 | access to parameter x : String | Async.cs:26:23:26:40 | call to method ReturnAwait : Task<String> [property Result] : String |
|
||||
| Async.cs:38:16:38:16 | access to parameter x : String | Async.cs:21:20:21:37 | call to method ReturnAwait [property Result] : String |
|
||||
| Async.cs:38:16:38:16 | access to parameter x : String | Async.cs:26:23:26:40 | call to method ReturnAwait [property Result] : String |
|
||||
| Async.cs:41:33:41:37 | input : String | Async.cs:43:25:43:29 | access to parameter input : String |
|
||||
| Async.cs:43:14:43:30 | call to method ReturnTask : Task<T> [property Result] : String | Async.cs:43:14:43:37 | access to property Result |
|
||||
| Async.cs:43:25:43:29 | access to parameter input : String | Async.cs:43:14:43:30 | call to method ReturnTask : Task<T> [property Result] : String |
|
||||
| Async.cs:43:14:43:30 | call to method ReturnTask [property Result] : String | Async.cs:43:14:43:37 | access to property Result |
|
||||
| Async.cs:43:25:43:29 | access to parameter input : String | Async.cs:43:14:43:30 | call to method ReturnTask [property Result] : String |
|
||||
| Async.cs:43:25:43:29 | access to parameter input : String | Async.cs:46:44:46:44 | x : String |
|
||||
| Async.cs:46:44:46:44 | x : String | Async.cs:48:32:48:32 | access to parameter x : String |
|
||||
| Async.cs:46:44:46:44 | x : String | Async.cs:48:32:48:32 | access to parameter x : String |
|
||||
| Async.cs:48:16:48:33 | call to method FromResult<String> : Task<T> [property Result] : String | Async.cs:43:14:43:30 | call to method ReturnTask : Task<T> [property Result] : String |
|
||||
| Async.cs:48:32:48:32 | access to parameter x : String | Async.cs:48:16:48:33 | call to method FromResult<String> : Task<T> [property Result] : String |
|
||||
| Async.cs:48:32:48:32 | access to parameter x : String | Async.cs:48:16:48:33 | call to method FromResult<String> : Task<T> [property Result] : String |
|
||||
| Async.cs:48:16:48:33 | call to method FromResult<String> [property Result] : String | Async.cs:43:14:43:30 | call to method ReturnTask [property Result] : String |
|
||||
| Async.cs:48:32:48:32 | access to parameter x : String | Async.cs:48:16:48:33 | call to method FromResult<String> [property Result] : String |
|
||||
| Async.cs:48:32:48:32 | access to parameter x : String | Async.cs:48:16:48:33 | call to method FromResult<String> [property Result] : String |
|
||||
| Async.cs:51:52:51:52 | x : String | Async.cs:51:58:51:58 | access to parameter x : String |
|
||||
| Async.cs:51:52:51:52 | x : String | Async.cs:51:58:51:58 | access to parameter x : String |
|
||||
| Async.cs:51:58:51:58 | access to parameter x : String | Async.cs:32:14:32:32 | call to method ReturnAwait2 : Task<String> [property Result] : String |
|
||||
| Async.cs:51:58:51:58 | access to parameter x : String | Async.cs:32:14:32:32 | call to method ReturnAwait2 [property Result] : String |
|
||||
nodes
|
||||
| Async.cs:9:37:9:41 | input : String | semmle.label | input : String |
|
||||
| Async.cs:11:14:11:26 | call to method Return | semmle.label | call to method Return |
|
||||
@@ -44,15 +44,15 @@ nodes
|
||||
| Async.cs:16:16:16:16 | access to parameter x : String | semmle.label | access to parameter x : String |
|
||||
| Async.cs:19:41:19:45 | input : String | semmle.label | input : String |
|
||||
| Async.cs:21:14:21:37 | await ... | semmle.label | await ... |
|
||||
| Async.cs:21:20:21:37 | call to method ReturnAwait : Task<String> [property Result] : String | semmle.label | call to method ReturnAwait : Task<String> [property Result] : String |
|
||||
| Async.cs:21:20:21:37 | call to method ReturnAwait [property Result] : String | semmle.label | call to method ReturnAwait [property Result] : String |
|
||||
| Async.cs:21:32:21:36 | access to parameter input : String | semmle.label | access to parameter input : String |
|
||||
| Async.cs:24:41:24:45 | input : String | semmle.label | input : String |
|
||||
| Async.cs:26:17:26:40 | await ... : String | semmle.label | await ... : String |
|
||||
| Async.cs:26:23:26:40 | call to method ReturnAwait : Task<String> [property Result] : String | semmle.label | call to method ReturnAwait : Task<String> [property Result] : String |
|
||||
| Async.cs:26:23:26:40 | call to method ReturnAwait [property Result] : String | semmle.label | call to method ReturnAwait [property Result] : String |
|
||||
| Async.cs:26:35:26:39 | access to parameter input : String | semmle.label | access to parameter input : String |
|
||||
| Async.cs:27:14:27:14 | access to local variable x | semmle.label | access to local variable x |
|
||||
| Async.cs:30:35:30:39 | input : String | semmle.label | input : String |
|
||||
| Async.cs:32:14:32:32 | call to method ReturnAwait2 : Task<String> [property Result] : String | semmle.label | call to method ReturnAwait2 : Task<String> [property Result] : String |
|
||||
| Async.cs:32:14:32:32 | call to method ReturnAwait2 [property Result] : String | semmle.label | call to method ReturnAwait2 [property Result] : String |
|
||||
| Async.cs:32:14:32:39 | access to property Result | semmle.label | access to property Result |
|
||||
| Async.cs:32:27:32:31 | access to parameter input : String | semmle.label | access to parameter input : String |
|
||||
| Async.cs:35:51:35:51 | x : String | semmle.label | x : String |
|
||||
@@ -60,13 +60,13 @@ nodes
|
||||
| Async.cs:38:16:38:16 | access to parameter x : String | semmle.label | access to parameter x : String |
|
||||
| Async.cs:38:16:38:16 | access to parameter x : String | semmle.label | access to parameter x : String |
|
||||
| Async.cs:41:33:41:37 | input : String | semmle.label | input : String |
|
||||
| Async.cs:43:14:43:30 | call to method ReturnTask : Task<T> [property Result] : String | semmle.label | call to method ReturnTask : Task<T> [property Result] : String |
|
||||
| Async.cs:43:14:43:30 | call to method ReturnTask [property Result] : String | semmle.label | call to method ReturnTask [property Result] : String |
|
||||
| Async.cs:43:14:43:37 | access to property Result | semmle.label | access to property Result |
|
||||
| Async.cs:43:25:43:29 | access to parameter input : String | semmle.label | access to parameter input : String |
|
||||
| Async.cs:46:44:46:44 | x : String | semmle.label | x : String |
|
||||
| Async.cs:46:44:46:44 | x : String | semmle.label | x : String |
|
||||
| Async.cs:48:16:48:33 | call to method FromResult<String> : Task<T> [property Result] : String | semmle.label | call to method FromResult<String> : Task<T> [property Result] : String |
|
||||
| Async.cs:48:16:48:33 | call to method FromResult<String> : Task<T> [property Result] : String | semmle.label | call to method FromResult<String> : Task<T> [property Result] : String |
|
||||
| Async.cs:48:16:48:33 | call to method FromResult<String> [property Result] : String | semmle.label | call to method FromResult<String> [property Result] : String |
|
||||
| Async.cs:48:16:48:33 | call to method FromResult<String> [property Result] : String | semmle.label | call to method FromResult<String> [property Result] : String |
|
||||
| Async.cs:48:32:48:32 | access to parameter x : String | semmle.label | access to parameter x : String |
|
||||
| Async.cs:48:32:48:32 | access to parameter x : String | semmle.label | access to parameter x : String |
|
||||
| Async.cs:51:52:51:52 | x : String | semmle.label | x : String |
|
||||
@@ -75,10 +75,10 @@ nodes
|
||||
| Async.cs:51:58:51:58 | access to parameter x : String | semmle.label | access to parameter x : String |
|
||||
subpaths
|
||||
| Async.cs:11:21:11:25 | access to parameter input : String | Async.cs:14:34:14:34 | x : String | Async.cs:16:16:16:16 | access to parameter x : String | Async.cs:11:14:11:26 | call to method Return |
|
||||
| Async.cs:21:32:21:36 | access to parameter input : String | Async.cs:35:51:35:51 | x : String | Async.cs:38:16:38:16 | access to parameter x : String | Async.cs:21:20:21:37 | call to method ReturnAwait : Task<String> [property Result] : String |
|
||||
| Async.cs:26:35:26:39 | access to parameter input : String | Async.cs:35:51:35:51 | x : String | Async.cs:38:16:38:16 | access to parameter x : String | Async.cs:26:23:26:40 | call to method ReturnAwait : Task<String> [property Result] : String |
|
||||
| Async.cs:32:27:32:31 | access to parameter input : String | Async.cs:51:52:51:52 | x : String | Async.cs:51:58:51:58 | access to parameter x : String | Async.cs:32:14:32:32 | call to method ReturnAwait2 : Task<String> [property Result] : String |
|
||||
| Async.cs:43:25:43:29 | access to parameter input : String | Async.cs:46:44:46:44 | x : String | Async.cs:48:16:48:33 | call to method FromResult<String> : Task<T> [property Result] : String | Async.cs:43:14:43:30 | call to method ReturnTask : Task<T> [property Result] : String |
|
||||
| Async.cs:21:32:21:36 | access to parameter input : String | Async.cs:35:51:35:51 | x : String | Async.cs:38:16:38:16 | access to parameter x : String | Async.cs:21:20:21:37 | call to method ReturnAwait [property Result] : String |
|
||||
| Async.cs:26:35:26:39 | access to parameter input : String | Async.cs:35:51:35:51 | x : String | Async.cs:38:16:38:16 | access to parameter x : String | Async.cs:26:23:26:40 | call to method ReturnAwait [property Result] : String |
|
||||
| Async.cs:32:27:32:31 | access to parameter input : String | Async.cs:51:52:51:52 | x : String | Async.cs:51:58:51:58 | access to parameter x : String | Async.cs:32:14:32:32 | call to method ReturnAwait2 [property Result] : String |
|
||||
| Async.cs:43:25:43:29 | access to parameter input : String | Async.cs:46:44:46:44 | x : String | Async.cs:48:16:48:33 | call to method FromResult<String> [property Result] : String | Async.cs:43:14:43:30 | call to method ReturnTask [property Result] : String |
|
||||
#select
|
||||
| Async.cs:11:14:11:26 | call to method Return | Async.cs:9:37:9:41 | input : String | Async.cs:11:14:11:26 | call to method Return | $@ flows to here and is used. | Async.cs:9:37:9:41 | input | User-provided value |
|
||||
| Async.cs:11:14:11:26 | call to method Return | Async.cs:14:34:14:34 | x : String | Async.cs:11:14:11:26 | call to method Return | $@ flows to here and is used. | Async.cs:14:34:14:34 | x | User-provided value |
|
||||
|
||||
@@ -1,488 +1,488 @@
|
||||
edges
|
||||
| CollectionFlow.cs:13:17:13:23 | object creation of type A : A | CollectionFlow.cs:14:27:14:27 | access to local variable a : A |
|
||||
| CollectionFlow.cs:14:25:14:29 | { ..., ... } : null [element] : A | CollectionFlow.cs:15:14:15:16 | access to local variable as : null [element] : A |
|
||||
| CollectionFlow.cs:14:25:14:29 | { ..., ... } : null [element] : A | CollectionFlow.cs:16:18:16:20 | access to local variable as : null [element] : A |
|
||||
| CollectionFlow.cs:14:25:14:29 | { ..., ... } : null [element] : A | CollectionFlow.cs:17:20:17:22 | access to local variable as : null [element] : A |
|
||||
| CollectionFlow.cs:14:27:14:27 | access to local variable a : A | CollectionFlow.cs:14:25:14:29 | { ..., ... } : null [element] : A |
|
||||
| CollectionFlow.cs:15:14:15:16 | access to local variable as : null [element] : A | CollectionFlow.cs:15:14:15:19 | access to array element |
|
||||
| CollectionFlow.cs:16:18:16:20 | access to local variable as : null [element] : A | CollectionFlow.cs:373:40:373:41 | ts : null [element] : A |
|
||||
| CollectionFlow.cs:17:20:17:22 | access to local variable as : null [element] : A | CollectionFlow.cs:17:14:17:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:17:20:17:22 | access to local variable as : null [element] : A | CollectionFlow.cs:381:34:381:35 | ts : null [element] : A |
|
||||
| CollectionFlow.cs:14:25:14:29 | { ..., ... } [element] : A | CollectionFlow.cs:15:14:15:16 | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:14:25:14:29 | { ..., ... } [element] : A | CollectionFlow.cs:16:18:16:20 | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:14:25:14:29 | { ..., ... } [element] : A | CollectionFlow.cs:17:20:17:22 | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:14:27:14:27 | access to local variable a : A | CollectionFlow.cs:14:25:14:29 | { ..., ... } [element] : A |
|
||||
| CollectionFlow.cs:15:14:15:16 | access to local variable as [element] : A | CollectionFlow.cs:15:14:15:19 | access to array element |
|
||||
| CollectionFlow.cs:16:18:16:20 | access to local variable as [element] : A | CollectionFlow.cs:373:40:373:41 | ts [element] : A |
|
||||
| CollectionFlow.cs:17:20:17:22 | access to local variable as [element] : A | CollectionFlow.cs:17:14:17:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:17:20:17:22 | access to local variable as [element] : A | CollectionFlow.cs:381:34:381:35 | ts [element] : A |
|
||||
| CollectionFlow.cs:31:17:31:23 | object creation of type A : A | CollectionFlow.cs:32:53:32:53 | access to local variable a : A |
|
||||
| CollectionFlow.cs:32:38:32:57 | { ..., ... } : CollectionFlow [field As, element] : A | CollectionFlow.cs:33:14:33:14 | access to local variable c : CollectionFlow [field As, element] : A |
|
||||
| CollectionFlow.cs:32:38:32:57 | { ..., ... } : CollectionFlow [field As, element] : A | CollectionFlow.cs:34:18:34:18 | access to local variable c : CollectionFlow [field As, element] : A |
|
||||
| CollectionFlow.cs:32:38:32:57 | { ..., ... } : CollectionFlow [field As, element] : A | CollectionFlow.cs:35:20:35:20 | access to local variable c : CollectionFlow [field As, element] : A |
|
||||
| CollectionFlow.cs:32:45:32:55 | { ..., ... } : A[] [element] : A | CollectionFlow.cs:32:38:32:57 | { ..., ... } : CollectionFlow [field As, element] : A |
|
||||
| CollectionFlow.cs:32:53:32:53 | access to local variable a : A | CollectionFlow.cs:32:45:32:55 | { ..., ... } : A[] [element] : A |
|
||||
| CollectionFlow.cs:33:14:33:14 | access to local variable c : CollectionFlow [field As, element] : A | CollectionFlow.cs:33:14:33:17 | access to field As : A[] [element] : A |
|
||||
| CollectionFlow.cs:33:14:33:17 | access to field As : A[] [element] : A | CollectionFlow.cs:33:14:33:20 | access to array element |
|
||||
| CollectionFlow.cs:34:18:34:18 | access to local variable c : CollectionFlow [field As, element] : A | CollectionFlow.cs:34:18:34:21 | access to field As : A[] [element] : A |
|
||||
| CollectionFlow.cs:34:18:34:21 | access to field As : A[] [element] : A | CollectionFlow.cs:373:40:373:41 | ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:35:20:35:20 | access to local variable c : CollectionFlow [field As, element] : A | CollectionFlow.cs:35:20:35:23 | access to field As : A[] [element] : A |
|
||||
| CollectionFlow.cs:35:20:35:23 | access to field As : A[] [element] : A | CollectionFlow.cs:35:14:35:24 | call to method First<A> |
|
||||
| CollectionFlow.cs:35:20:35:23 | access to field As : A[] [element] : A | CollectionFlow.cs:381:34:381:35 | ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:32:38:32:57 | { ..., ... } [field As, element] : A | CollectionFlow.cs:33:14:33:14 | access to local variable c [field As, element] : A |
|
||||
| CollectionFlow.cs:32:38:32:57 | { ..., ... } [field As, element] : A | CollectionFlow.cs:34:18:34:18 | access to local variable c [field As, element] : A |
|
||||
| CollectionFlow.cs:32:38:32:57 | { ..., ... } [field As, element] : A | CollectionFlow.cs:35:20:35:20 | access to local variable c [field As, element] : A |
|
||||
| CollectionFlow.cs:32:45:32:55 | { ..., ... } [element] : A | CollectionFlow.cs:32:38:32:57 | { ..., ... } [field As, element] : A |
|
||||
| CollectionFlow.cs:32:53:32:53 | access to local variable a : A | CollectionFlow.cs:32:45:32:55 | { ..., ... } [element] : A |
|
||||
| CollectionFlow.cs:33:14:33:14 | access to local variable c [field As, element] : A | CollectionFlow.cs:33:14:33:17 | access to field As [element] : A |
|
||||
| CollectionFlow.cs:33:14:33:17 | access to field As [element] : A | CollectionFlow.cs:33:14:33:20 | access to array element |
|
||||
| CollectionFlow.cs:34:18:34:18 | access to local variable c [field As, element] : A | CollectionFlow.cs:34:18:34:21 | access to field As [element] : A |
|
||||
| CollectionFlow.cs:34:18:34:21 | access to field As [element] : A | CollectionFlow.cs:373:40:373:41 | ts [element] : A |
|
||||
| CollectionFlow.cs:35:20:35:20 | access to local variable c [field As, element] : A | CollectionFlow.cs:35:20:35:23 | access to field As [element] : A |
|
||||
| CollectionFlow.cs:35:20:35:23 | access to field As [element] : A | CollectionFlow.cs:35:14:35:24 | call to method First<A> |
|
||||
| CollectionFlow.cs:35:20:35:23 | access to field As [element] : A | CollectionFlow.cs:381:34:381:35 | ts [element] : A |
|
||||
| CollectionFlow.cs:49:17:49:23 | object creation of type A : A | CollectionFlow.cs:51:18:51:18 | access to local variable a : A |
|
||||
| CollectionFlow.cs:51:9:51:11 | [post] access to local variable as : A[] [element] : A | CollectionFlow.cs:52:14:52:16 | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:51:9:51:11 | [post] access to local variable as : A[] [element] : A | CollectionFlow.cs:53:18:53:20 | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:51:9:51:11 | [post] access to local variable as : A[] [element] : A | CollectionFlow.cs:54:20:54:22 | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:51:18:51:18 | access to local variable a : A | CollectionFlow.cs:51:9:51:11 | [post] access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:52:14:52:16 | access to local variable as : A[] [element] : A | CollectionFlow.cs:52:14:52:19 | access to array element |
|
||||
| CollectionFlow.cs:53:18:53:20 | access to local variable as : A[] [element] : A | CollectionFlow.cs:373:40:373:41 | ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:54:20:54:22 | access to local variable as : A[] [element] : A | CollectionFlow.cs:54:14:54:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:54:20:54:22 | access to local variable as : A[] [element] : A | CollectionFlow.cs:381:34:381:35 | ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:51:9:51:11 | [post] access to local variable as [element] : A | CollectionFlow.cs:52:14:52:16 | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:51:9:51:11 | [post] access to local variable as [element] : A | CollectionFlow.cs:53:18:53:20 | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:51:9:51:11 | [post] access to local variable as [element] : A | CollectionFlow.cs:54:20:54:22 | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:51:18:51:18 | access to local variable a : A | CollectionFlow.cs:51:9:51:11 | [post] access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:52:14:52:16 | access to local variable as [element] : A | CollectionFlow.cs:52:14:52:19 | access to array element |
|
||||
| CollectionFlow.cs:53:18:53:20 | access to local variable as [element] : A | CollectionFlow.cs:373:40:373:41 | ts [element] : A |
|
||||
| CollectionFlow.cs:54:20:54:22 | access to local variable as [element] : A | CollectionFlow.cs:54:14:54:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:54:20:54:22 | access to local variable as [element] : A | CollectionFlow.cs:381:34:381:35 | ts [element] : A |
|
||||
| CollectionFlow.cs:69:17:69:23 | object creation of type A : A | CollectionFlow.cs:71:19:71:19 | access to local variable a : A |
|
||||
| CollectionFlow.cs:71:9:71:12 | [post] access to local variable list : List<T> [element] : A | CollectionFlow.cs:72:14:72:17 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:71:9:71:12 | [post] access to local variable list : List<T> [element] : A | CollectionFlow.cs:73:22:73:25 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:71:9:71:12 | [post] access to local variable list : List<T> [element] : A | CollectionFlow.cs:74:24:74:27 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:71:19:71:19 | access to local variable a : A | CollectionFlow.cs:71:9:71:12 | [post] access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:72:14:72:17 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:72:14:72:20 | access to indexer |
|
||||
| CollectionFlow.cs:73:22:73:25 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:74:24:74:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:74:14:74:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:74:24:74:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:71:9:71:12 | [post] access to local variable list [element] : A | CollectionFlow.cs:72:14:72:17 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:71:9:71:12 | [post] access to local variable list [element] : A | CollectionFlow.cs:73:22:73:25 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:71:9:71:12 | [post] access to local variable list [element] : A | CollectionFlow.cs:74:24:74:27 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:71:19:71:19 | access to local variable a : A | CollectionFlow.cs:71:9:71:12 | [post] access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:72:14:72:17 | access to local variable list [element] : A | CollectionFlow.cs:72:14:72:20 | access to indexer |
|
||||
| CollectionFlow.cs:73:22:73:25 | access to local variable list [element] : A | CollectionFlow.cs:375:49:375:52 | list [element] : A |
|
||||
| CollectionFlow.cs:74:24:74:27 | access to local variable list [element] : A | CollectionFlow.cs:74:14:74:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:74:24:74:27 | access to local variable list [element] : A | CollectionFlow.cs:383:43:383:46 | list [element] : A |
|
||||
| CollectionFlow.cs:88:17:88:23 | object creation of type A : A | CollectionFlow.cs:89:36:89:36 | access to local variable a : A |
|
||||
| CollectionFlow.cs:89:20:89:38 | object creation of type List<A> : List<T> [element] : A | CollectionFlow.cs:90:14:90:17 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:89:20:89:38 | object creation of type List<A> : List<T> [element] : A | CollectionFlow.cs:91:22:91:25 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:89:20:89:38 | object creation of type List<A> : List<T> [element] : A | CollectionFlow.cs:92:24:92:27 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:89:36:89:36 | access to local variable a : A | CollectionFlow.cs:89:20:89:38 | object creation of type List<A> : List<T> [element] : A |
|
||||
| CollectionFlow.cs:90:14:90:17 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:90:14:90:20 | access to indexer |
|
||||
| CollectionFlow.cs:91:22:91:25 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:92:24:92:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:92:14:92:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:92:24:92:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:89:20:89:38 | object creation of type List<A> [element] : A | CollectionFlow.cs:90:14:90:17 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:89:20:89:38 | object creation of type List<A> [element] : A | CollectionFlow.cs:91:22:91:25 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:89:20:89:38 | object creation of type List<A> [element] : A | CollectionFlow.cs:92:24:92:27 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:89:36:89:36 | access to local variable a : A | CollectionFlow.cs:89:20:89:38 | object creation of type List<A> [element] : A |
|
||||
| CollectionFlow.cs:90:14:90:17 | access to local variable list [element] : A | CollectionFlow.cs:90:14:90:20 | access to indexer |
|
||||
| CollectionFlow.cs:91:22:91:25 | access to local variable list [element] : A | CollectionFlow.cs:375:49:375:52 | list [element] : A |
|
||||
| CollectionFlow.cs:92:24:92:27 | access to local variable list [element] : A | CollectionFlow.cs:92:14:92:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:92:24:92:27 | access to local variable list [element] : A | CollectionFlow.cs:383:43:383:46 | list [element] : A |
|
||||
| CollectionFlow.cs:105:17:105:23 | object creation of type A : A | CollectionFlow.cs:107:18:107:18 | access to local variable a : A |
|
||||
| CollectionFlow.cs:107:9:107:12 | [post] access to local variable list : List<T> [element] : A | CollectionFlow.cs:108:14:108:17 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:107:9:107:12 | [post] access to local variable list : List<T> [element] : A | CollectionFlow.cs:109:22:109:25 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:107:9:107:12 | [post] access to local variable list : List<T> [element] : A | CollectionFlow.cs:110:24:110:27 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:107:18:107:18 | access to local variable a : A | CollectionFlow.cs:107:9:107:12 | [post] access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:108:14:108:17 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:108:14:108:20 | access to indexer |
|
||||
| CollectionFlow.cs:109:22:109:25 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:110:24:110:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:110:14:110:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:110:24:110:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:107:9:107:12 | [post] access to local variable list [element] : A | CollectionFlow.cs:108:14:108:17 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:107:9:107:12 | [post] access to local variable list [element] : A | CollectionFlow.cs:109:22:109:25 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:107:9:107:12 | [post] access to local variable list [element] : A | CollectionFlow.cs:110:24:110:27 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:107:18:107:18 | access to local variable a : A | CollectionFlow.cs:107:9:107:12 | [post] access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:108:14:108:17 | access to local variable list [element] : A | CollectionFlow.cs:108:14:108:20 | access to indexer |
|
||||
| CollectionFlow.cs:109:22:109:25 | access to local variable list [element] : A | CollectionFlow.cs:375:49:375:52 | list [element] : A |
|
||||
| CollectionFlow.cs:110:24:110:27 | access to local variable list [element] : A | CollectionFlow.cs:110:14:110:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:110:24:110:27 | access to local variable list [element] : A | CollectionFlow.cs:383:43:383:46 | list [element] : A |
|
||||
| CollectionFlow.cs:124:17:124:23 | object creation of type A : A | CollectionFlow.cs:126:19:126:19 | access to local variable a : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:127:14:127:17 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:128:23:128:26 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:129:28:129:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:130:29:130:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:131:30:131:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:19:126:19 | access to local variable a : A | CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:127:14:127:17 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:127:14:127:20 | access to indexer |
|
||||
| CollectionFlow.cs:128:23:128:26 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:377:61:377:64 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:129:28:129:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:129:14:129:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:129:28:129:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:130:29:130:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:130:14:130:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:130:29:130:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:131:30:131:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:131:14:131:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:131:30:131:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict [element, property Value] : A | CollectionFlow.cs:127:14:127:17 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict [element, property Value] : A | CollectionFlow.cs:128:23:128:26 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict [element, property Value] : A | CollectionFlow.cs:129:28:129:31 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict [element, property Value] : A | CollectionFlow.cs:130:29:130:32 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict [element, property Value] : A | CollectionFlow.cs:131:30:131:33 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:19:126:19 | access to local variable a : A | CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:127:14:127:17 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:127:14:127:20 | access to indexer |
|
||||
| CollectionFlow.cs:128:23:128:26 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:377:61:377:64 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:129:28:129:31 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:129:14:129:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:129:28:129:31 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:130:29:130:32 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:130:14:130:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:130:29:130:32 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:131:30:131:33 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:131:14:131:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:131:30:131:33 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:147:17:147:23 | object creation of type A : A | CollectionFlow.cs:148:52:148:52 | access to local variable a : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:149:14:149:17 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:150:23:150:26 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:151:28:151:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:152:29:152:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:153:30:153:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:52:148:52 | access to local variable a : A | CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:149:14:149:17 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:149:14:149:20 | access to indexer |
|
||||
| CollectionFlow.cs:150:23:150:26 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:377:61:377:64 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:151:28:151:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:151:14:151:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:151:28:151:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:152:29:152:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:152:14:152:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:152:29:152:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:153:30:153:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:153:14:153:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:153:30:153:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> [element, property Value] : A | CollectionFlow.cs:149:14:149:17 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> [element, property Value] : A | CollectionFlow.cs:150:23:150:26 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> [element, property Value] : A | CollectionFlow.cs:151:28:151:31 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> [element, property Value] : A | CollectionFlow.cs:152:29:152:32 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> [element, property Value] : A | CollectionFlow.cs:153:30:153:33 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:52:148:52 | access to local variable a : A | CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> [element, property Value] : A |
|
||||
| CollectionFlow.cs:149:14:149:17 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:149:14:149:20 | access to indexer |
|
||||
| CollectionFlow.cs:150:23:150:26 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:377:61:377:64 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:151:28:151:31 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:151:14:151:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:151:28:151:31 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:152:29:152:32 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:152:14:152:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:152:29:152:32 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:153:30:153:33 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:153:14:153:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:153:30:153:33 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:168:17:168:23 | object creation of type A : A | CollectionFlow.cs:169:53:169:53 | access to local variable a : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:170:14:170:17 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:171:23:171:26 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:172:28:172:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:173:29:173:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:174:30:174:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:53:169:53 | access to local variable a : A | CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:170:14:170:17 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:170:14:170:20 | access to indexer |
|
||||
| CollectionFlow.cs:171:23:171:26 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:377:61:377:64 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:172:28:172:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:172:14:172:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:172:28:172:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:173:29:173:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:173:14:173:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:173:29:173:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:174:30:174:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:174:14:174:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:174:30:174:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> [element, property Value] : A | CollectionFlow.cs:170:14:170:17 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> [element, property Value] : A | CollectionFlow.cs:171:23:171:26 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> [element, property Value] : A | CollectionFlow.cs:172:28:172:31 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> [element, property Value] : A | CollectionFlow.cs:173:29:173:32 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> [element, property Value] : A | CollectionFlow.cs:174:30:174:33 | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:53:169:53 | access to local variable a : A | CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> [element, property Value] : A |
|
||||
| CollectionFlow.cs:170:14:170:17 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:170:14:170:20 | access to indexer |
|
||||
| CollectionFlow.cs:171:23:171:26 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:377:61:377:64 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:172:28:172:31 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:172:14:172:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:172:28:172:31 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:173:29:173:32 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:173:14:173:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:173:29:173:32 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:174:30:174:33 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:174:14:174:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:174:30:174:33 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:190:17:190:23 | object creation of type A : A | CollectionFlow.cs:191:49:191:49 | access to local variable a : A |
|
||||
| CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:192:14:192:17 | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:193:21:193:24 | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:194:28:194:31 | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:195:27:195:30 | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:191:49:191:49 | access to local variable a : A | CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:192:14:192:17 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:192:14:192:22 | access to property Keys : Dictionary<T,T>.KeyCollection [element] : A |
|
||||
| CollectionFlow.cs:192:14:192:22 | access to property Keys : Dictionary<T,T>.KeyCollection [element] : A | CollectionFlow.cs:192:14:192:30 | call to method First<A> |
|
||||
| CollectionFlow.cs:193:21:193:24 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:379:59:379:62 | dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:194:28:194:31 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:194:14:194:32 | call to method DictKeysFirst<A> |
|
||||
| CollectionFlow.cs:194:28:194:31 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:391:58:391:61 | dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:195:27:195:30 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:195:14:195:31 | call to method DictFirstKey<A> |
|
||||
| CollectionFlow.cs:195:27:195:30 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:393:57:393:60 | dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> [element, property Key] : A | CollectionFlow.cs:192:14:192:17 | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> [element, property Key] : A | CollectionFlow.cs:193:21:193:24 | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> [element, property Key] : A | CollectionFlow.cs:194:28:194:31 | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> [element, property Key] : A | CollectionFlow.cs:195:27:195:30 | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:191:49:191:49 | access to local variable a : A | CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> [element, property Key] : A |
|
||||
| CollectionFlow.cs:192:14:192:17 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:192:14:192:22 | access to property Keys [element] : A |
|
||||
| CollectionFlow.cs:192:14:192:22 | access to property Keys [element] : A | CollectionFlow.cs:192:14:192:30 | call to method First<A> |
|
||||
| CollectionFlow.cs:193:21:193:24 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:379:59:379:62 | dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:194:28:194:31 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:194:14:194:32 | call to method DictKeysFirst<A> |
|
||||
| CollectionFlow.cs:194:28:194:31 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:391:58:391:61 | dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:195:27:195:30 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:195:14:195:31 | call to method DictFirstKey<A> |
|
||||
| CollectionFlow.cs:195:27:195:30 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:393:57:393:60 | dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:209:17:209:23 | object creation of type A : A | CollectionFlow.cs:210:48:210:48 | access to local variable a : A |
|
||||
| CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:211:14:211:17 | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:212:21:212:24 | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:213:28:213:31 | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:214:27:214:30 | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:210:48:210:48 | access to local variable a : A | CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:211:14:211:17 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:211:14:211:22 | access to property Keys : Dictionary<T,T>.KeyCollection [element] : A |
|
||||
| CollectionFlow.cs:211:14:211:22 | access to property Keys : Dictionary<T,T>.KeyCollection [element] : A | CollectionFlow.cs:211:14:211:30 | call to method First<A> |
|
||||
| CollectionFlow.cs:212:21:212:24 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:379:59:379:62 | dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:213:28:213:31 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:213:14:213:32 | call to method DictKeysFirst<A> |
|
||||
| CollectionFlow.cs:213:28:213:31 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:391:58:391:61 | dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:214:27:214:30 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:214:14:214:31 | call to method DictFirstKey<A> |
|
||||
| CollectionFlow.cs:214:27:214:30 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:393:57:393:60 | dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> [element, property Key] : A | CollectionFlow.cs:211:14:211:17 | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> [element, property Key] : A | CollectionFlow.cs:212:21:212:24 | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> [element, property Key] : A | CollectionFlow.cs:213:28:213:31 | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> [element, property Key] : A | CollectionFlow.cs:214:27:214:30 | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:210:48:210:48 | access to local variable a : A | CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> [element, property Key] : A |
|
||||
| CollectionFlow.cs:211:14:211:17 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:211:14:211:22 | access to property Keys [element] : A |
|
||||
| CollectionFlow.cs:211:14:211:22 | access to property Keys [element] : A | CollectionFlow.cs:211:14:211:30 | call to method First<A> |
|
||||
| CollectionFlow.cs:212:21:212:24 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:379:59:379:62 | dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:213:28:213:31 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:213:14:213:32 | call to method DictKeysFirst<A> |
|
||||
| CollectionFlow.cs:213:28:213:31 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:391:58:391:61 | dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:214:27:214:30 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:214:14:214:31 | call to method DictFirstKey<A> |
|
||||
| CollectionFlow.cs:214:27:214:30 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:393:57:393:60 | dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:228:17:228:23 | object creation of type A : A | CollectionFlow.cs:229:27:229:27 | access to local variable a : A |
|
||||
| CollectionFlow.cs:229:25:229:29 | { ..., ... } : null [element] : A | CollectionFlow.cs:230:27:230:29 | access to local variable as : null [element] : A |
|
||||
| CollectionFlow.cs:229:27:229:27 | access to local variable a : A | CollectionFlow.cs:229:25:229:29 | { ..., ... } : null [element] : A |
|
||||
| CollectionFlow.cs:229:25:229:29 | { ..., ... } [element] : A | CollectionFlow.cs:230:27:230:29 | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:229:27:229:27 | access to local variable a : A | CollectionFlow.cs:229:25:229:29 | { ..., ... } [element] : A |
|
||||
| CollectionFlow.cs:230:22:230:22 | SSA def(x) : A | CollectionFlow.cs:231:18:231:18 | access to local variable x |
|
||||
| CollectionFlow.cs:230:27:230:29 | access to local variable as : null [element] : A | CollectionFlow.cs:230:22:230:22 | SSA def(x) : A |
|
||||
| CollectionFlow.cs:230:27:230:29 | access to local variable as [element] : A | CollectionFlow.cs:230:22:230:22 | SSA def(x) : A |
|
||||
| CollectionFlow.cs:243:17:243:23 | object creation of type A : A | CollectionFlow.cs:244:27:244:27 | access to local variable a : A |
|
||||
| CollectionFlow.cs:244:25:244:29 | { ..., ... } : null [element] : A | CollectionFlow.cs:245:26:245:28 | access to local variable as : null [element] : A |
|
||||
| CollectionFlow.cs:244:27:244:27 | access to local variable a : A | CollectionFlow.cs:244:25:244:29 | { ..., ... } : null [element] : A |
|
||||
| CollectionFlow.cs:245:26:245:28 | access to local variable as : null [element] : A | CollectionFlow.cs:245:26:245:44 | call to method GetEnumerator : IEnumerator [property Current] : A |
|
||||
| CollectionFlow.cs:245:26:245:44 | call to method GetEnumerator : IEnumerator [property Current] : A | CollectionFlow.cs:247:18:247:27 | access to local variable enumerator : IEnumerator [property Current] : A |
|
||||
| CollectionFlow.cs:247:18:247:27 | access to local variable enumerator : IEnumerator [property Current] : A | CollectionFlow.cs:247:18:247:35 | access to property Current |
|
||||
| CollectionFlow.cs:244:25:244:29 | { ..., ... } [element] : A | CollectionFlow.cs:245:26:245:28 | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:244:27:244:27 | access to local variable a : A | CollectionFlow.cs:244:25:244:29 | { ..., ... } [element] : A |
|
||||
| CollectionFlow.cs:245:26:245:28 | access to local variable as [element] : A | CollectionFlow.cs:245:26:245:44 | call to method GetEnumerator [property Current] : A |
|
||||
| CollectionFlow.cs:245:26:245:44 | call to method GetEnumerator [property Current] : A | CollectionFlow.cs:247:18:247:27 | access to local variable enumerator [property Current] : A |
|
||||
| CollectionFlow.cs:247:18:247:27 | access to local variable enumerator [property Current] : A | CollectionFlow.cs:247:18:247:35 | access to property Current |
|
||||
| CollectionFlow.cs:260:17:260:23 | object creation of type A : A | CollectionFlow.cs:262:18:262:18 | access to local variable a : A |
|
||||
| CollectionFlow.cs:262:9:262:12 | [post] access to local variable list : List<T> [element] : A | CollectionFlow.cs:263:26:263:29 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:262:18:262:18 | access to local variable a : A | CollectionFlow.cs:262:9:262:12 | [post] access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:263:26:263:29 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:263:26:263:45 | call to method GetEnumerator : List<T>.Enumerator [property Current] : A |
|
||||
| CollectionFlow.cs:263:26:263:45 | call to method GetEnumerator : List<T>.Enumerator [property Current] : A | CollectionFlow.cs:265:18:265:27 | access to local variable enumerator : List<T>.Enumerator [property Current] : A |
|
||||
| CollectionFlow.cs:265:18:265:27 | access to local variable enumerator : List<T>.Enumerator [property Current] : A | CollectionFlow.cs:265:18:265:35 | access to property Current |
|
||||
| CollectionFlow.cs:262:9:262:12 | [post] access to local variable list [element] : A | CollectionFlow.cs:263:26:263:29 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:262:18:262:18 | access to local variable a : A | CollectionFlow.cs:262:9:262:12 | [post] access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:263:26:263:29 | access to local variable list [element] : A | CollectionFlow.cs:263:26:263:45 | call to method GetEnumerator [property Current] : A |
|
||||
| CollectionFlow.cs:263:26:263:45 | call to method GetEnumerator [property Current] : A | CollectionFlow.cs:265:18:265:27 | access to local variable enumerator [property Current] : A |
|
||||
| CollectionFlow.cs:265:18:265:27 | access to local variable enumerator [property Current] : A | CollectionFlow.cs:265:18:265:35 | access to property Current |
|
||||
| CollectionFlow.cs:279:17:279:23 | object creation of type A : A | CollectionFlow.cs:281:43:281:43 | access to local variable a : A |
|
||||
| CollectionFlow.cs:281:9:281:12 | [post] access to local variable list : List<T> [element, property Key] : A | CollectionFlow.cs:282:9:282:12 | access to local variable list : List<T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:281:18:281:47 | object creation of type KeyValuePair<A,Int32> : KeyValuePair<T,T> [property Key] : A | CollectionFlow.cs:281:9:281:12 | [post] access to local variable list : List<T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:281:43:281:43 | access to local variable a : A | CollectionFlow.cs:281:18:281:47 | object creation of type KeyValuePair<A,Int32> : KeyValuePair<T,T> [property Key] : A |
|
||||
| CollectionFlow.cs:282:9:282:12 | access to local variable list : List<T> [element, property Key] : A | CollectionFlow.cs:282:21:282:23 | kvp : KeyValuePair<T,T> [property Key] : A |
|
||||
| CollectionFlow.cs:282:21:282:23 | kvp : KeyValuePair<T,T> [property Key] : A | CollectionFlow.cs:284:18:284:20 | access to parameter kvp : KeyValuePair<T,T> [property Key] : A |
|
||||
| CollectionFlow.cs:284:18:284:20 | access to parameter kvp : KeyValuePair<T,T> [property Key] : A | CollectionFlow.cs:284:18:284:24 | access to property Key |
|
||||
| CollectionFlow.cs:281:9:281:12 | [post] access to local variable list [element, property Key] : A | CollectionFlow.cs:282:9:282:12 | access to local variable list [element, property Key] : A |
|
||||
| CollectionFlow.cs:281:18:281:47 | object creation of type KeyValuePair<A,Int32> [property Key] : A | CollectionFlow.cs:281:9:281:12 | [post] access to local variable list [element, property Key] : A |
|
||||
| CollectionFlow.cs:281:43:281:43 | access to local variable a : A | CollectionFlow.cs:281:18:281:47 | object creation of type KeyValuePair<A,Int32> [property Key] : A |
|
||||
| CollectionFlow.cs:282:9:282:12 | access to local variable list [element, property Key] : A | CollectionFlow.cs:282:21:282:23 | kvp [property Key] : A |
|
||||
| CollectionFlow.cs:282:21:282:23 | kvp [property Key] : A | CollectionFlow.cs:284:18:284:20 | access to parameter kvp [property Key] : A |
|
||||
| CollectionFlow.cs:284:18:284:20 | access to parameter kvp [property Key] : A | CollectionFlow.cs:284:18:284:24 | access to property Key |
|
||||
| CollectionFlow.cs:301:32:301:38 | element : A | CollectionFlow.cs:301:55:301:61 | access to parameter element : A |
|
||||
| CollectionFlow.cs:301:55:301:61 | access to parameter element : A | CollectionFlow.cs:301:44:301:48 | [post] access to parameter array : A[] [element] : A |
|
||||
| CollectionFlow.cs:301:55:301:61 | access to parameter element : A | CollectionFlow.cs:301:44:301:48 | [post] access to parameter array [element] : A |
|
||||
| CollectionFlow.cs:305:17:305:23 | object creation of type A : A | CollectionFlow.cs:307:23:307:23 | access to local variable a : A |
|
||||
| CollectionFlow.cs:307:18:307:20 | [post] access to local variable as : A[] [element] : A | CollectionFlow.cs:308:14:308:16 | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:307:18:307:20 | [post] access to local variable as : A[] [element] : A | CollectionFlow.cs:309:18:309:20 | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:307:18:307:20 | [post] access to local variable as : A[] [element] : A | CollectionFlow.cs:310:20:310:22 | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:307:18:307:20 | [post] access to local variable as [element] : A | CollectionFlow.cs:308:14:308:16 | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:307:18:307:20 | [post] access to local variable as [element] : A | CollectionFlow.cs:309:18:309:20 | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:307:18:307:20 | [post] access to local variable as [element] : A | CollectionFlow.cs:310:20:310:22 | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:307:23:307:23 | access to local variable a : A | CollectionFlow.cs:301:32:301:38 | element : A |
|
||||
| CollectionFlow.cs:307:23:307:23 | access to local variable a : A | CollectionFlow.cs:307:18:307:20 | [post] access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:308:14:308:16 | access to local variable as : A[] [element] : A | CollectionFlow.cs:308:14:308:19 | access to array element |
|
||||
| CollectionFlow.cs:309:18:309:20 | access to local variable as : A[] [element] : A | CollectionFlow.cs:373:40:373:41 | ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:310:20:310:22 | access to local variable as : A[] [element] : A | CollectionFlow.cs:310:14:310:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:310:20:310:22 | access to local variable as : A[] [element] : A | CollectionFlow.cs:381:34:381:35 | ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:307:23:307:23 | access to local variable a : A | CollectionFlow.cs:307:18:307:20 | [post] access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:308:14:308:16 | access to local variable as [element] : A | CollectionFlow.cs:308:14:308:19 | access to array element |
|
||||
| CollectionFlow.cs:309:18:309:20 | access to local variable as [element] : A | CollectionFlow.cs:373:40:373:41 | ts [element] : A |
|
||||
| CollectionFlow.cs:310:20:310:22 | access to local variable as [element] : A | CollectionFlow.cs:310:14:310:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:310:20:310:22 | access to local variable as [element] : A | CollectionFlow.cs:381:34:381:35 | ts [element] : A |
|
||||
| CollectionFlow.cs:323:34:323:40 | element : A | CollectionFlow.cs:323:55:323:61 | access to parameter element : A |
|
||||
| CollectionFlow.cs:323:55:323:61 | access to parameter element : A | CollectionFlow.cs:323:46:323:49 | [post] access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:323:55:323:61 | access to parameter element : A | CollectionFlow.cs:323:46:323:49 | [post] access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:327:17:327:23 | object creation of type A : A | CollectionFlow.cs:329:23:329:23 | access to local variable a : A |
|
||||
| CollectionFlow.cs:329:17:329:20 | [post] access to local variable list : List<T> [element] : A | CollectionFlow.cs:330:14:330:17 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:329:17:329:20 | [post] access to local variable list : List<T> [element] : A | CollectionFlow.cs:331:22:331:25 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:329:17:329:20 | [post] access to local variable list : List<T> [element] : A | CollectionFlow.cs:332:24:332:27 | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:329:17:329:20 | [post] access to local variable list [element] : A | CollectionFlow.cs:330:14:330:17 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:329:17:329:20 | [post] access to local variable list [element] : A | CollectionFlow.cs:331:22:331:25 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:329:17:329:20 | [post] access to local variable list [element] : A | CollectionFlow.cs:332:24:332:27 | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:329:23:329:23 | access to local variable a : A | CollectionFlow.cs:323:34:323:40 | element : A |
|
||||
| CollectionFlow.cs:329:23:329:23 | access to local variable a : A | CollectionFlow.cs:329:17:329:20 | [post] access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:330:14:330:17 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:330:14:330:20 | access to indexer |
|
||||
| CollectionFlow.cs:331:22:331:25 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:332:24:332:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:332:14:332:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:332:24:332:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:346:20:346:26 | object creation of type A : A | CollectionFlow.cs:395:49:395:52 | args : A[] [element] : A |
|
||||
| CollectionFlow.cs:347:26:347:32 | object creation of type A : A | CollectionFlow.cs:395:49:395:52 | args : A[] [element] : A |
|
||||
| CollectionFlow.cs:348:26:348:32 | object creation of type A : A | CollectionFlow.cs:395:49:395:52 | args : A[] [element] : A |
|
||||
| CollectionFlow.cs:349:20:349:38 | array creation of type A[] : null [element] : A | CollectionFlow.cs:395:49:395:52 | args : null [element] : A |
|
||||
| CollectionFlow.cs:349:28:349:38 | { ..., ... } : null [element] : A | CollectionFlow.cs:349:20:349:38 | array creation of type A[] : null [element] : A |
|
||||
| CollectionFlow.cs:349:30:349:36 | object creation of type A : A | CollectionFlow.cs:349:28:349:38 | { ..., ... } : null [element] : A |
|
||||
| CollectionFlow.cs:373:40:373:41 | ts : A[] [element] : A | CollectionFlow.cs:373:52:373:53 | access to parameter ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:373:40:373:41 | ts : null [element] : A | CollectionFlow.cs:373:52:373:53 | access to parameter ts : null [element] : A |
|
||||
| CollectionFlow.cs:373:52:373:53 | access to parameter ts : A[] [element] : A | CollectionFlow.cs:373:52:373:56 | access to array element |
|
||||
| CollectionFlow.cs:373:52:373:53 | access to parameter ts : null [element] : A | CollectionFlow.cs:373:52:373:56 | access to array element |
|
||||
| CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A | CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A | CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A | CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A | CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A | CollectionFlow.cs:375:63:375:69 | access to indexer |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A | CollectionFlow.cs:375:63:375:69 | access to indexer |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A | CollectionFlow.cs:375:63:375:69 | access to indexer |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A | CollectionFlow.cs:375:63:375:69 | access to indexer |
|
||||
| CollectionFlow.cs:377:61:377:64 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:377:75:377:78 | access to parameter dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:377:75:377:78 | access to parameter dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:377:75:377:81 | access to indexer |
|
||||
| CollectionFlow.cs:379:59:379:62 | dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:379:73:379:76 | access to parameter dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:379:73:379:76 | access to parameter dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:379:73:379:81 | access to property Keys : ICollection<T> [element] : A |
|
||||
| CollectionFlow.cs:379:73:379:81 | access to property Keys : ICollection<T> [element] : A | CollectionFlow.cs:379:73:379:89 | call to method First<T> |
|
||||
| CollectionFlow.cs:381:34:381:35 | ts : A[] [element] : A | CollectionFlow.cs:381:41:381:42 | access to parameter ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:381:34:381:35 | ts : null [element] : A | CollectionFlow.cs:381:41:381:42 | access to parameter ts : null [element] : A |
|
||||
| CollectionFlow.cs:381:41:381:42 | access to parameter ts : A[] [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A |
|
||||
| CollectionFlow.cs:381:41:381:42 | access to parameter ts : null [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A |
|
||||
| CollectionFlow.cs:385:58:385:61 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:385:67:385:70 | access to parameter dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:385:67:385:70 | access to parameter dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:385:67:385:73 | access to indexer : A |
|
||||
| CollectionFlow.cs:387:59:387:62 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:387:68:387:71 | access to parameter dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:387:68:387:71 | access to parameter dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:387:68:387:79 | call to method First<KeyValuePair<Int32,T>> : Object [property Value] : A |
|
||||
| CollectionFlow.cs:387:68:387:79 | call to method First<KeyValuePair<Int32,T>> : Object [property Value] : A | CollectionFlow.cs:387:68:387:85 | access to property Value : A |
|
||||
| CollectionFlow.cs:389:60:389:63 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:389:69:389:72 | access to parameter dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:389:69:389:72 | access to parameter dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:389:69:389:79 | access to property Values : ICollection<T> [element] : A |
|
||||
| CollectionFlow.cs:389:69:389:79 | access to property Values : ICollection<T> [element] : A | CollectionFlow.cs:389:69:389:87 | call to method First<T> : A |
|
||||
| CollectionFlow.cs:391:58:391:61 | dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:391:67:391:70 | access to parameter dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:391:67:391:70 | access to parameter dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:391:67:391:75 | access to property Keys : ICollection<T> [element] : A |
|
||||
| CollectionFlow.cs:391:67:391:75 | access to property Keys : ICollection<T> [element] : A | CollectionFlow.cs:391:67:391:83 | call to method First<T> : A |
|
||||
| CollectionFlow.cs:393:57:393:60 | dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:393:66:393:69 | access to parameter dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:393:66:393:69 | access to parameter dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:393:66:393:77 | call to method First<KeyValuePair<T,Int32>> : Object [property Key] : A |
|
||||
| CollectionFlow.cs:393:66:393:77 | call to method First<KeyValuePair<T,Int32>> : Object [property Key] : A | CollectionFlow.cs:393:66:393:81 | access to property Key : A |
|
||||
| CollectionFlow.cs:395:49:395:52 | args : A[] [element] : A | CollectionFlow.cs:395:63:395:66 | access to parameter args : A[] [element] : A |
|
||||
| CollectionFlow.cs:395:49:395:52 | args : null [element] : A | CollectionFlow.cs:395:63:395:66 | access to parameter args : null [element] : A |
|
||||
| CollectionFlow.cs:395:63:395:66 | access to parameter args : A[] [element] : A | CollectionFlow.cs:395:63:395:69 | access to array element |
|
||||
| CollectionFlow.cs:395:63:395:66 | access to parameter args : null [element] : A | CollectionFlow.cs:395:63:395:69 | access to array element |
|
||||
| CollectionFlow.cs:329:23:329:23 | access to local variable a : A | CollectionFlow.cs:329:17:329:20 | [post] access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:330:14:330:17 | access to local variable list [element] : A | CollectionFlow.cs:330:14:330:20 | access to indexer |
|
||||
| CollectionFlow.cs:331:22:331:25 | access to local variable list [element] : A | CollectionFlow.cs:375:49:375:52 | list [element] : A |
|
||||
| CollectionFlow.cs:332:24:332:27 | access to local variable list [element] : A | CollectionFlow.cs:332:14:332:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:332:24:332:27 | access to local variable list [element] : A | CollectionFlow.cs:383:43:383:46 | list [element] : A |
|
||||
| CollectionFlow.cs:346:20:346:26 | object creation of type A : A | CollectionFlow.cs:395:49:395:52 | args [element] : A |
|
||||
| CollectionFlow.cs:347:26:347:32 | object creation of type A : A | CollectionFlow.cs:395:49:395:52 | args [element] : A |
|
||||
| CollectionFlow.cs:348:26:348:32 | object creation of type A : A | CollectionFlow.cs:395:49:395:52 | args [element] : A |
|
||||
| CollectionFlow.cs:349:20:349:38 | array creation of type A[] [element] : A | CollectionFlow.cs:395:49:395:52 | args [element] : A |
|
||||
| CollectionFlow.cs:349:28:349:38 | { ..., ... } [element] : A | CollectionFlow.cs:349:20:349:38 | array creation of type A[] [element] : A |
|
||||
| CollectionFlow.cs:349:30:349:36 | object creation of type A : A | CollectionFlow.cs:349:28:349:38 | { ..., ... } [element] : A |
|
||||
| CollectionFlow.cs:373:40:373:41 | ts [element] : A | CollectionFlow.cs:373:52:373:53 | access to parameter ts [element] : A |
|
||||
| CollectionFlow.cs:373:40:373:41 | ts [element] : A | CollectionFlow.cs:373:52:373:53 | access to parameter ts [element] : A |
|
||||
| CollectionFlow.cs:373:52:373:53 | access to parameter ts [element] : A | CollectionFlow.cs:373:52:373:56 | access to array element |
|
||||
| CollectionFlow.cs:373:52:373:53 | access to parameter ts [element] : A | CollectionFlow.cs:373:52:373:56 | access to array element |
|
||||
| CollectionFlow.cs:375:49:375:52 | list [element] : A | CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list [element] : A | CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list [element] : A | CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list [element] : A | CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A | CollectionFlow.cs:375:63:375:69 | access to indexer |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A | CollectionFlow.cs:375:63:375:69 | access to indexer |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A | CollectionFlow.cs:375:63:375:69 | access to indexer |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A | CollectionFlow.cs:375:63:375:69 | access to indexer |
|
||||
| CollectionFlow.cs:377:61:377:64 | dict [element, property Value] : A | CollectionFlow.cs:377:75:377:78 | access to parameter dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:377:75:377:78 | access to parameter dict [element, property Value] : A | CollectionFlow.cs:377:75:377:81 | access to indexer |
|
||||
| CollectionFlow.cs:379:59:379:62 | dict [element, property Key] : A | CollectionFlow.cs:379:73:379:76 | access to parameter dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:379:73:379:76 | access to parameter dict [element, property Key] : A | CollectionFlow.cs:379:73:379:81 | access to property Keys [element] : A |
|
||||
| CollectionFlow.cs:379:73:379:81 | access to property Keys [element] : A | CollectionFlow.cs:379:73:379:89 | call to method First<T> |
|
||||
| CollectionFlow.cs:381:34:381:35 | ts [element] : A | CollectionFlow.cs:381:41:381:42 | access to parameter ts [element] : A |
|
||||
| CollectionFlow.cs:381:34:381:35 | ts [element] : A | CollectionFlow.cs:381:41:381:42 | access to parameter ts [element] : A |
|
||||
| CollectionFlow.cs:381:41:381:42 | access to parameter ts [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A |
|
||||
| CollectionFlow.cs:381:41:381:42 | access to parameter ts [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list [element] : A | CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list [element] : A | CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list [element] : A | CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list [element] : A | CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A |
|
||||
| CollectionFlow.cs:385:58:385:61 | dict [element, property Value] : A | CollectionFlow.cs:385:67:385:70 | access to parameter dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:385:67:385:70 | access to parameter dict [element, property Value] : A | CollectionFlow.cs:385:67:385:73 | access to indexer : A |
|
||||
| CollectionFlow.cs:387:59:387:62 | dict [element, property Value] : A | CollectionFlow.cs:387:68:387:71 | access to parameter dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:387:68:387:71 | access to parameter dict [element, property Value] : A | CollectionFlow.cs:387:68:387:79 | call to method First<KeyValuePair<Int32,T>> [property Value] : A |
|
||||
| CollectionFlow.cs:387:68:387:79 | call to method First<KeyValuePair<Int32,T>> [property Value] : A | CollectionFlow.cs:387:68:387:85 | access to property Value : A |
|
||||
| CollectionFlow.cs:389:60:389:63 | dict [element, property Value] : A | CollectionFlow.cs:389:69:389:72 | access to parameter dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:389:69:389:72 | access to parameter dict [element, property Value] : A | CollectionFlow.cs:389:69:389:79 | access to property Values [element] : A |
|
||||
| CollectionFlow.cs:389:69:389:79 | access to property Values [element] : A | CollectionFlow.cs:389:69:389:87 | call to method First<T> : A |
|
||||
| CollectionFlow.cs:391:58:391:61 | dict [element, property Key] : A | CollectionFlow.cs:391:67:391:70 | access to parameter dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:391:67:391:70 | access to parameter dict [element, property Key] : A | CollectionFlow.cs:391:67:391:75 | access to property Keys [element] : A |
|
||||
| CollectionFlow.cs:391:67:391:75 | access to property Keys [element] : A | CollectionFlow.cs:391:67:391:83 | call to method First<T> : A |
|
||||
| CollectionFlow.cs:393:57:393:60 | dict [element, property Key] : A | CollectionFlow.cs:393:66:393:69 | access to parameter dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:393:66:393:69 | access to parameter dict [element, property Key] : A | CollectionFlow.cs:393:66:393:77 | call to method First<KeyValuePair<T,Int32>> [property Key] : A |
|
||||
| CollectionFlow.cs:393:66:393:77 | call to method First<KeyValuePair<T,Int32>> [property Key] : A | CollectionFlow.cs:393:66:393:81 | access to property Key : A |
|
||||
| CollectionFlow.cs:395:49:395:52 | args [element] : A | CollectionFlow.cs:395:63:395:66 | access to parameter args [element] : A |
|
||||
| CollectionFlow.cs:395:49:395:52 | args [element] : A | CollectionFlow.cs:395:63:395:66 | access to parameter args [element] : A |
|
||||
| CollectionFlow.cs:395:63:395:66 | access to parameter args [element] : A | CollectionFlow.cs:395:63:395:69 | access to array element |
|
||||
| CollectionFlow.cs:395:63:395:66 | access to parameter args [element] : A | CollectionFlow.cs:395:63:395:69 | access to array element |
|
||||
nodes
|
||||
| CollectionFlow.cs:13:17:13:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:14:25:14:29 | { ..., ... } : null [element] : A | semmle.label | { ..., ... } : null [element] : A |
|
||||
| CollectionFlow.cs:14:25:14:29 | { ..., ... } [element] : A | semmle.label | { ..., ... } [element] : A |
|
||||
| CollectionFlow.cs:14:27:14:27 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:15:14:15:16 | access to local variable as : null [element] : A | semmle.label | access to local variable as : null [element] : A |
|
||||
| CollectionFlow.cs:15:14:15:16 | access to local variable as [element] : A | semmle.label | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:15:14:15:19 | access to array element | semmle.label | access to array element |
|
||||
| CollectionFlow.cs:16:18:16:20 | access to local variable as : null [element] : A | semmle.label | access to local variable as : null [element] : A |
|
||||
| CollectionFlow.cs:16:18:16:20 | access to local variable as [element] : A | semmle.label | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:17:14:17:23 | call to method First<A> | semmle.label | call to method First<A> |
|
||||
| CollectionFlow.cs:17:20:17:22 | access to local variable as : null [element] : A | semmle.label | access to local variable as : null [element] : A |
|
||||
| CollectionFlow.cs:17:20:17:22 | access to local variable as [element] : A | semmle.label | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:31:17:31:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:32:38:32:57 | { ..., ... } : CollectionFlow [field As, element] : A | semmle.label | { ..., ... } : CollectionFlow [field As, element] : A |
|
||||
| CollectionFlow.cs:32:45:32:55 | { ..., ... } : A[] [element] : A | semmle.label | { ..., ... } : A[] [element] : A |
|
||||
| CollectionFlow.cs:32:38:32:57 | { ..., ... } [field As, element] : A | semmle.label | { ..., ... } [field As, element] : A |
|
||||
| CollectionFlow.cs:32:45:32:55 | { ..., ... } [element] : A | semmle.label | { ..., ... } [element] : A |
|
||||
| CollectionFlow.cs:32:53:32:53 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:33:14:33:14 | access to local variable c : CollectionFlow [field As, element] : A | semmle.label | access to local variable c : CollectionFlow [field As, element] : A |
|
||||
| CollectionFlow.cs:33:14:33:17 | access to field As : A[] [element] : A | semmle.label | access to field As : A[] [element] : A |
|
||||
| CollectionFlow.cs:33:14:33:14 | access to local variable c [field As, element] : A | semmle.label | access to local variable c [field As, element] : A |
|
||||
| CollectionFlow.cs:33:14:33:17 | access to field As [element] : A | semmle.label | access to field As [element] : A |
|
||||
| CollectionFlow.cs:33:14:33:20 | access to array element | semmle.label | access to array element |
|
||||
| CollectionFlow.cs:34:18:34:18 | access to local variable c : CollectionFlow [field As, element] : A | semmle.label | access to local variable c : CollectionFlow [field As, element] : A |
|
||||
| CollectionFlow.cs:34:18:34:21 | access to field As : A[] [element] : A | semmle.label | access to field As : A[] [element] : A |
|
||||
| CollectionFlow.cs:34:18:34:18 | access to local variable c [field As, element] : A | semmle.label | access to local variable c [field As, element] : A |
|
||||
| CollectionFlow.cs:34:18:34:21 | access to field As [element] : A | semmle.label | access to field As [element] : A |
|
||||
| CollectionFlow.cs:35:14:35:24 | call to method First<A> | semmle.label | call to method First<A> |
|
||||
| CollectionFlow.cs:35:20:35:20 | access to local variable c : CollectionFlow [field As, element] : A | semmle.label | access to local variable c : CollectionFlow [field As, element] : A |
|
||||
| CollectionFlow.cs:35:20:35:23 | access to field As : A[] [element] : A | semmle.label | access to field As : A[] [element] : A |
|
||||
| CollectionFlow.cs:35:20:35:20 | access to local variable c [field As, element] : A | semmle.label | access to local variable c [field As, element] : A |
|
||||
| CollectionFlow.cs:35:20:35:23 | access to field As [element] : A | semmle.label | access to field As [element] : A |
|
||||
| CollectionFlow.cs:49:17:49:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:51:9:51:11 | [post] access to local variable as : A[] [element] : A | semmle.label | [post] access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:51:9:51:11 | [post] access to local variable as [element] : A | semmle.label | [post] access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:51:18:51:18 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:52:14:52:16 | access to local variable as : A[] [element] : A | semmle.label | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:52:14:52:16 | access to local variable as [element] : A | semmle.label | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:52:14:52:19 | access to array element | semmle.label | access to array element |
|
||||
| CollectionFlow.cs:53:18:53:20 | access to local variable as : A[] [element] : A | semmle.label | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:53:18:53:20 | access to local variable as [element] : A | semmle.label | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:54:14:54:23 | call to method First<A> | semmle.label | call to method First<A> |
|
||||
| CollectionFlow.cs:54:20:54:22 | access to local variable as : A[] [element] : A | semmle.label | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:54:20:54:22 | access to local variable as [element] : A | semmle.label | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:69:17:69:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:71:9:71:12 | [post] access to local variable list : List<T> [element] : A | semmle.label | [post] access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:71:9:71:12 | [post] access to local variable list [element] : A | semmle.label | [post] access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:71:19:71:19 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:72:14:72:17 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:72:14:72:17 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:72:14:72:20 | access to indexer | semmle.label | access to indexer |
|
||||
| CollectionFlow.cs:73:22:73:25 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:73:22:73:25 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:74:14:74:28 | call to method ListFirst<A> | semmle.label | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:74:24:74:27 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:74:24:74:27 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:88:17:88:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:89:20:89:38 | object creation of type List<A> : List<T> [element] : A | semmle.label | object creation of type List<A> : List<T> [element] : A |
|
||||
| CollectionFlow.cs:89:20:89:38 | object creation of type List<A> [element] : A | semmle.label | object creation of type List<A> [element] : A |
|
||||
| CollectionFlow.cs:89:36:89:36 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:90:14:90:17 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:90:14:90:17 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:90:14:90:20 | access to indexer | semmle.label | access to indexer |
|
||||
| CollectionFlow.cs:91:22:91:25 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:91:22:91:25 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:92:14:92:28 | call to method ListFirst<A> | semmle.label | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:92:24:92:27 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:92:24:92:27 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:105:17:105:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:107:9:107:12 | [post] access to local variable list : List<T> [element] : A | semmle.label | [post] access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:107:9:107:12 | [post] access to local variable list [element] : A | semmle.label | [post] access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:107:18:107:18 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:108:14:108:17 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:108:14:108:17 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:108:14:108:20 | access to indexer | semmle.label | access to indexer |
|
||||
| CollectionFlow.cs:109:22:109:25 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:109:22:109:25 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:110:14:110:28 | call to method ListFirst<A> | semmle.label | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:110:24:110:27 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:110:24:110:27 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:124:17:124:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | [post] access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:9:126:12 | [post] access to local variable dict [element, property Value] : A | semmle.label | [post] access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:126:19:126:19 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:127:14:127:17 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:127:14:127:17 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:127:14:127:20 | access to indexer | semmle.label | access to indexer |
|
||||
| CollectionFlow.cs:128:23:128:26 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:128:23:128:26 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:129:14:129:32 | call to method DictIndexZero<A> | semmle.label | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:129:28:129:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:129:28:129:31 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:130:14:130:33 | call to method DictFirstValue<A> | semmle.label | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:130:29:130:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:130:29:130:32 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:131:14:131:34 | call to method DictValuesFirst<A> | semmle.label | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:131:30:131:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:131:30:131:33 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:147:17:147:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | semmle.label | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:20:148:56 | object creation of type Dictionary<Int32,A> [element, property Value] : A | semmle.label | object creation of type Dictionary<Int32,A> [element, property Value] : A |
|
||||
| CollectionFlow.cs:148:52:148:52 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:149:14:149:17 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:149:14:149:17 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:149:14:149:20 | access to indexer | semmle.label | access to indexer |
|
||||
| CollectionFlow.cs:150:23:150:26 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:150:23:150:26 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:151:14:151:32 | call to method DictIndexZero<A> | semmle.label | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:151:28:151:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:151:28:151:31 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:152:14:152:33 | call to method DictFirstValue<A> | semmle.label | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:152:29:152:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:152:29:152:32 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:153:14:153:34 | call to method DictValuesFirst<A> | semmle.label | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:153:30:153:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:153:30:153:33 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:168:17:168:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A | semmle.label | object creation of type Dictionary<Int32,A> : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:20:169:55 | object creation of type Dictionary<Int32,A> [element, property Value] : A | semmle.label | object creation of type Dictionary<Int32,A> [element, property Value] : A |
|
||||
| CollectionFlow.cs:169:53:169:53 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:170:14:170:17 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:170:14:170:17 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:170:14:170:20 | access to indexer | semmle.label | access to indexer |
|
||||
| CollectionFlow.cs:171:23:171:26 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:171:23:171:26 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:172:14:172:32 | call to method DictIndexZero<A> | semmle.label | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:172:28:172:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:172:28:172:31 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:173:14:173:33 | call to method DictFirstValue<A> | semmle.label | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:173:29:173:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:173:29:173:32 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:174:14:174:34 | call to method DictValuesFirst<A> | semmle.label | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:174:30:174:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:174:30:174:33 | access to local variable dict [element, property Value] : A | semmle.label | access to local variable dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:190:17:190:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A | semmle.label | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:191:20:191:56 | object creation of type Dictionary<A,Int32> [element, property Key] : A | semmle.label | object creation of type Dictionary<A,Int32> [element, property Key] : A |
|
||||
| CollectionFlow.cs:191:49:191:49 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:192:14:192:17 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:192:14:192:22 | access to property Keys : Dictionary<T,T>.KeyCollection [element] : A | semmle.label | access to property Keys : Dictionary<T,T>.KeyCollection [element] : A |
|
||||
| CollectionFlow.cs:192:14:192:17 | access to local variable dict [element, property Key] : A | semmle.label | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:192:14:192:22 | access to property Keys [element] : A | semmle.label | access to property Keys [element] : A |
|
||||
| CollectionFlow.cs:192:14:192:30 | call to method First<A> | semmle.label | call to method First<A> |
|
||||
| CollectionFlow.cs:193:21:193:24 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:193:21:193:24 | access to local variable dict [element, property Key] : A | semmle.label | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:194:14:194:32 | call to method DictKeysFirst<A> | semmle.label | call to method DictKeysFirst<A> |
|
||||
| CollectionFlow.cs:194:28:194:31 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:194:28:194:31 | access to local variable dict [element, property Key] : A | semmle.label | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:195:14:195:31 | call to method DictFirstKey<A> | semmle.label | call to method DictFirstKey<A> |
|
||||
| CollectionFlow.cs:195:27:195:30 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:195:27:195:30 | access to local variable dict [element, property Key] : A | semmle.label | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:209:17:209:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A | semmle.label | object creation of type Dictionary<A,Int32> : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:210:20:210:55 | object creation of type Dictionary<A,Int32> [element, property Key] : A | semmle.label | object creation of type Dictionary<A,Int32> [element, property Key] : A |
|
||||
| CollectionFlow.cs:210:48:210:48 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:211:14:211:17 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:211:14:211:22 | access to property Keys : Dictionary<T,T>.KeyCollection [element] : A | semmle.label | access to property Keys : Dictionary<T,T>.KeyCollection [element] : A |
|
||||
| CollectionFlow.cs:211:14:211:17 | access to local variable dict [element, property Key] : A | semmle.label | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:211:14:211:22 | access to property Keys [element] : A | semmle.label | access to property Keys [element] : A |
|
||||
| CollectionFlow.cs:211:14:211:30 | call to method First<A> | semmle.label | call to method First<A> |
|
||||
| CollectionFlow.cs:212:21:212:24 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:212:21:212:24 | access to local variable dict [element, property Key] : A | semmle.label | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:213:14:213:32 | call to method DictKeysFirst<A> | semmle.label | call to method DictKeysFirst<A> |
|
||||
| CollectionFlow.cs:213:28:213:31 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:213:28:213:31 | access to local variable dict [element, property Key] : A | semmle.label | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:214:14:214:31 | call to method DictFirstKey<A> | semmle.label | call to method DictFirstKey<A> |
|
||||
| CollectionFlow.cs:214:27:214:30 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | semmle.label | access to local variable dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:214:27:214:30 | access to local variable dict [element, property Key] : A | semmle.label | access to local variable dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:228:17:228:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:229:25:229:29 | { ..., ... } : null [element] : A | semmle.label | { ..., ... } : null [element] : A |
|
||||
| CollectionFlow.cs:229:25:229:29 | { ..., ... } [element] : A | semmle.label | { ..., ... } [element] : A |
|
||||
| CollectionFlow.cs:229:27:229:27 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:230:22:230:22 | SSA def(x) : A | semmle.label | SSA def(x) : A |
|
||||
| CollectionFlow.cs:230:27:230:29 | access to local variable as : null [element] : A | semmle.label | access to local variable as : null [element] : A |
|
||||
| CollectionFlow.cs:230:27:230:29 | access to local variable as [element] : A | semmle.label | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:231:18:231:18 | access to local variable x | semmle.label | access to local variable x |
|
||||
| CollectionFlow.cs:243:17:243:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:244:25:244:29 | { ..., ... } : null [element] : A | semmle.label | { ..., ... } : null [element] : A |
|
||||
| CollectionFlow.cs:244:25:244:29 | { ..., ... } [element] : A | semmle.label | { ..., ... } [element] : A |
|
||||
| CollectionFlow.cs:244:27:244:27 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:245:26:245:28 | access to local variable as : null [element] : A | semmle.label | access to local variable as : null [element] : A |
|
||||
| CollectionFlow.cs:245:26:245:44 | call to method GetEnumerator : IEnumerator [property Current] : A | semmle.label | call to method GetEnumerator : IEnumerator [property Current] : A |
|
||||
| CollectionFlow.cs:247:18:247:27 | access to local variable enumerator : IEnumerator [property Current] : A | semmle.label | access to local variable enumerator : IEnumerator [property Current] : A |
|
||||
| CollectionFlow.cs:245:26:245:28 | access to local variable as [element] : A | semmle.label | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:245:26:245:44 | call to method GetEnumerator [property Current] : A | semmle.label | call to method GetEnumerator [property Current] : A |
|
||||
| CollectionFlow.cs:247:18:247:27 | access to local variable enumerator [property Current] : A | semmle.label | access to local variable enumerator [property Current] : A |
|
||||
| CollectionFlow.cs:247:18:247:35 | access to property Current | semmle.label | access to property Current |
|
||||
| CollectionFlow.cs:260:17:260:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:262:9:262:12 | [post] access to local variable list : List<T> [element] : A | semmle.label | [post] access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:262:9:262:12 | [post] access to local variable list [element] : A | semmle.label | [post] access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:262:18:262:18 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:263:26:263:29 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:263:26:263:45 | call to method GetEnumerator : List<T>.Enumerator [property Current] : A | semmle.label | call to method GetEnumerator : List<T>.Enumerator [property Current] : A |
|
||||
| CollectionFlow.cs:265:18:265:27 | access to local variable enumerator : List<T>.Enumerator [property Current] : A | semmle.label | access to local variable enumerator : List<T>.Enumerator [property Current] : A |
|
||||
| CollectionFlow.cs:263:26:263:29 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:263:26:263:45 | call to method GetEnumerator [property Current] : A | semmle.label | call to method GetEnumerator [property Current] : A |
|
||||
| CollectionFlow.cs:265:18:265:27 | access to local variable enumerator [property Current] : A | semmle.label | access to local variable enumerator [property Current] : A |
|
||||
| CollectionFlow.cs:265:18:265:35 | access to property Current | semmle.label | access to property Current |
|
||||
| CollectionFlow.cs:279:17:279:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:281:9:281:12 | [post] access to local variable list : List<T> [element, property Key] : A | semmle.label | [post] access to local variable list : List<T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:281:18:281:47 | object creation of type KeyValuePair<A,Int32> : KeyValuePair<T,T> [property Key] : A | semmle.label | object creation of type KeyValuePair<A,Int32> : KeyValuePair<T,T> [property Key] : A |
|
||||
| CollectionFlow.cs:281:9:281:12 | [post] access to local variable list [element, property Key] : A | semmle.label | [post] access to local variable list [element, property Key] : A |
|
||||
| CollectionFlow.cs:281:18:281:47 | object creation of type KeyValuePair<A,Int32> [property Key] : A | semmle.label | object creation of type KeyValuePair<A,Int32> [property Key] : A |
|
||||
| CollectionFlow.cs:281:43:281:43 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:282:9:282:12 | access to local variable list : List<T> [element, property Key] : A | semmle.label | access to local variable list : List<T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:282:21:282:23 | kvp : KeyValuePair<T,T> [property Key] : A | semmle.label | kvp : KeyValuePair<T,T> [property Key] : A |
|
||||
| CollectionFlow.cs:284:18:284:20 | access to parameter kvp : KeyValuePair<T,T> [property Key] : A | semmle.label | access to parameter kvp : KeyValuePair<T,T> [property Key] : A |
|
||||
| CollectionFlow.cs:282:9:282:12 | access to local variable list [element, property Key] : A | semmle.label | access to local variable list [element, property Key] : A |
|
||||
| CollectionFlow.cs:282:21:282:23 | kvp [property Key] : A | semmle.label | kvp [property Key] : A |
|
||||
| CollectionFlow.cs:284:18:284:20 | access to parameter kvp [property Key] : A | semmle.label | access to parameter kvp [property Key] : A |
|
||||
| CollectionFlow.cs:284:18:284:24 | access to property Key | semmle.label | access to property Key |
|
||||
| CollectionFlow.cs:301:32:301:38 | element : A | semmle.label | element : A |
|
||||
| CollectionFlow.cs:301:44:301:48 | [post] access to parameter array : A[] [element] : A | semmle.label | [post] access to parameter array : A[] [element] : A |
|
||||
| CollectionFlow.cs:301:44:301:48 | [post] access to parameter array [element] : A | semmle.label | [post] access to parameter array [element] : A |
|
||||
| CollectionFlow.cs:301:55:301:61 | access to parameter element : A | semmle.label | access to parameter element : A |
|
||||
| CollectionFlow.cs:305:17:305:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:307:18:307:20 | [post] access to local variable as : A[] [element] : A | semmle.label | [post] access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:307:18:307:20 | [post] access to local variable as [element] : A | semmle.label | [post] access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:307:23:307:23 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:308:14:308:16 | access to local variable as : A[] [element] : A | semmle.label | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:308:14:308:16 | access to local variable as [element] : A | semmle.label | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:308:14:308:19 | access to array element | semmle.label | access to array element |
|
||||
| CollectionFlow.cs:309:18:309:20 | access to local variable as : A[] [element] : A | semmle.label | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:309:18:309:20 | access to local variable as [element] : A | semmle.label | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:310:14:310:23 | call to method First<A> | semmle.label | call to method First<A> |
|
||||
| CollectionFlow.cs:310:20:310:22 | access to local variable as : A[] [element] : A | semmle.label | access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:310:20:310:22 | access to local variable as [element] : A | semmle.label | access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:323:34:323:40 | element : A | semmle.label | element : A |
|
||||
| CollectionFlow.cs:323:46:323:49 | [post] access to parameter list : List<T> [element] : A | semmle.label | [post] access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:323:46:323:49 | [post] access to parameter list [element] : A | semmle.label | [post] access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:323:55:323:61 | access to parameter element : A | semmle.label | access to parameter element : A |
|
||||
| CollectionFlow.cs:327:17:327:23 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:329:17:329:20 | [post] access to local variable list : List<T> [element] : A | semmle.label | [post] access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:329:17:329:20 | [post] access to local variable list [element] : A | semmle.label | [post] access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:329:23:329:23 | access to local variable a : A | semmle.label | access to local variable a : A |
|
||||
| CollectionFlow.cs:330:14:330:17 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:330:14:330:17 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:330:14:330:20 | access to indexer | semmle.label | access to indexer |
|
||||
| CollectionFlow.cs:331:22:331:25 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:331:22:331:25 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:332:14:332:28 | call to method ListFirst<A> | semmle.label | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:332:24:332:27 | access to local variable list : List<T> [element] : A | semmle.label | access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:332:24:332:27 | access to local variable list [element] : A | semmle.label | access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:346:20:346:26 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:347:26:347:32 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:348:26:348:32 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:349:20:349:38 | array creation of type A[] : null [element] : A | semmle.label | array creation of type A[] : null [element] : A |
|
||||
| CollectionFlow.cs:349:28:349:38 | { ..., ... } : null [element] : A | semmle.label | { ..., ... } : null [element] : A |
|
||||
| CollectionFlow.cs:349:20:349:38 | array creation of type A[] [element] : A | semmle.label | array creation of type A[] [element] : A |
|
||||
| CollectionFlow.cs:349:28:349:38 | { ..., ... } [element] : A | semmle.label | { ..., ... } [element] : A |
|
||||
| CollectionFlow.cs:349:30:349:36 | object creation of type A : A | semmle.label | object creation of type A : A |
|
||||
| CollectionFlow.cs:373:40:373:41 | ts : A[] [element] : A | semmle.label | ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:373:40:373:41 | ts : null [element] : A | semmle.label | ts : null [element] : A |
|
||||
| CollectionFlow.cs:373:52:373:53 | access to parameter ts : A[] [element] : A | semmle.label | access to parameter ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:373:52:373:53 | access to parameter ts : null [element] : A | semmle.label | access to parameter ts : null [element] : A |
|
||||
| CollectionFlow.cs:373:40:373:41 | ts [element] : A | semmle.label | ts [element] : A |
|
||||
| CollectionFlow.cs:373:40:373:41 | ts [element] : A | semmle.label | ts [element] : A |
|
||||
| CollectionFlow.cs:373:52:373:53 | access to parameter ts [element] : A | semmle.label | access to parameter ts [element] : A |
|
||||
| CollectionFlow.cs:373:52:373:53 | access to parameter ts [element] : A | semmle.label | access to parameter ts [element] : A |
|
||||
| CollectionFlow.cs:373:52:373:56 | access to array element | semmle.label | access to array element |
|
||||
| CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A | semmle.label | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A | semmle.label | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A | semmle.label | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list : List<T> [element] : A | semmle.label | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A | semmle.label | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A | semmle.label | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A | semmle.label | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list : List<T> [element] : A | semmle.label | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list [element] : A | semmle.label | list [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list [element] : A | semmle.label | list [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list [element] : A | semmle.label | list [element] : A |
|
||||
| CollectionFlow.cs:375:49:375:52 | list [element] : A | semmle.label | list [element] : A |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A | semmle.label | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A | semmle.label | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A | semmle.label | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:375:63:375:66 | access to parameter list [element] : A | semmle.label | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:375:63:375:69 | access to indexer | semmle.label | access to indexer |
|
||||
| CollectionFlow.cs:377:61:377:64 | dict : Dictionary<T,T> [element, property Value] : A | semmle.label | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:377:75:377:78 | access to parameter dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to parameter dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:377:61:377:64 | dict [element, property Value] : A | semmle.label | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:377:75:377:78 | access to parameter dict [element, property Value] : A | semmle.label | access to parameter dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:377:75:377:81 | access to indexer | semmle.label | access to indexer |
|
||||
| CollectionFlow.cs:379:59:379:62 | dict : Dictionary<T,T> [element, property Key] : A | semmle.label | dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:379:73:379:76 | access to parameter dict : Dictionary<T,T> [element, property Key] : A | semmle.label | access to parameter dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:379:73:379:81 | access to property Keys : ICollection<T> [element] : A | semmle.label | access to property Keys : ICollection<T> [element] : A |
|
||||
| CollectionFlow.cs:379:59:379:62 | dict [element, property Key] : A | semmle.label | dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:379:73:379:76 | access to parameter dict [element, property Key] : A | semmle.label | access to parameter dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:379:73:379:81 | access to property Keys [element] : A | semmle.label | access to property Keys [element] : A |
|
||||
| CollectionFlow.cs:379:73:379:89 | call to method First<T> | semmle.label | call to method First<T> |
|
||||
| CollectionFlow.cs:381:34:381:35 | ts : A[] [element] : A | semmle.label | ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:381:34:381:35 | ts : null [element] : A | semmle.label | ts : null [element] : A |
|
||||
| CollectionFlow.cs:381:41:381:42 | access to parameter ts : A[] [element] : A | semmle.label | access to parameter ts : A[] [element] : A |
|
||||
| CollectionFlow.cs:381:41:381:42 | access to parameter ts : null [element] : A | semmle.label | access to parameter ts : null [element] : A |
|
||||
| CollectionFlow.cs:381:34:381:35 | ts [element] : A | semmle.label | ts [element] : A |
|
||||
| CollectionFlow.cs:381:34:381:35 | ts [element] : A | semmle.label | ts [element] : A |
|
||||
| CollectionFlow.cs:381:41:381:42 | access to parameter ts [element] : A | semmle.label | access to parameter ts [element] : A |
|
||||
| CollectionFlow.cs:381:41:381:42 | access to parameter ts [element] : A | semmle.label | access to parameter ts [element] : A |
|
||||
| CollectionFlow.cs:381:41:381:45 | access to array element : A | semmle.label | access to array element : A |
|
||||
| CollectionFlow.cs:381:41:381:45 | access to array element : A | semmle.label | access to array element : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | semmle.label | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | semmle.label | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | semmle.label | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | semmle.label | list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A | semmle.label | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A | semmle.label | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A | semmle.label | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list : List<T> [element] : A | semmle.label | access to parameter list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list [element] : A | semmle.label | list [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list [element] : A | semmle.label | list [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list [element] : A | semmle.label | list [element] : A |
|
||||
| CollectionFlow.cs:383:43:383:46 | list [element] : A | semmle.label | list [element] : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A | semmle.label | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A | semmle.label | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A | semmle.label | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:383:52:383:55 | access to parameter list [element] : A | semmle.label | access to parameter list [element] : A |
|
||||
| CollectionFlow.cs:383:52:383:58 | access to indexer : A | semmle.label | access to indexer : A |
|
||||
| CollectionFlow.cs:383:52:383:58 | access to indexer : A | semmle.label | access to indexer : A |
|
||||
| CollectionFlow.cs:383:52:383:58 | access to indexer : A | semmle.label | access to indexer : A |
|
||||
| CollectionFlow.cs:383:52:383:58 | access to indexer : A | semmle.label | access to indexer : A |
|
||||
| CollectionFlow.cs:385:58:385:61 | dict : Dictionary<T,T> [element, property Value] : A | semmle.label | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:385:67:385:70 | access to parameter dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to parameter dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:385:58:385:61 | dict [element, property Value] : A | semmle.label | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:385:67:385:70 | access to parameter dict [element, property Value] : A | semmle.label | access to parameter dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:385:67:385:73 | access to indexer : A | semmle.label | access to indexer : A |
|
||||
| CollectionFlow.cs:387:59:387:62 | dict : Dictionary<T,T> [element, property Value] : A | semmle.label | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:387:68:387:71 | access to parameter dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to parameter dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:387:68:387:79 | call to method First<KeyValuePair<Int32,T>> : Object [property Value] : A | semmle.label | call to method First<KeyValuePair<Int32,T>> : Object [property Value] : A |
|
||||
| CollectionFlow.cs:387:59:387:62 | dict [element, property Value] : A | semmle.label | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:387:68:387:71 | access to parameter dict [element, property Value] : A | semmle.label | access to parameter dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:387:68:387:79 | call to method First<KeyValuePair<Int32,T>> [property Value] : A | semmle.label | call to method First<KeyValuePair<Int32,T>> [property Value] : A |
|
||||
| CollectionFlow.cs:387:68:387:85 | access to property Value : A | semmle.label | access to property Value : A |
|
||||
| CollectionFlow.cs:389:60:389:63 | dict : Dictionary<T,T> [element, property Value] : A | semmle.label | dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:389:69:389:72 | access to parameter dict : Dictionary<T,T> [element, property Value] : A | semmle.label | access to parameter dict : Dictionary<T,T> [element, property Value] : A |
|
||||
| CollectionFlow.cs:389:69:389:79 | access to property Values : ICollection<T> [element] : A | semmle.label | access to property Values : ICollection<T> [element] : A |
|
||||
| CollectionFlow.cs:389:60:389:63 | dict [element, property Value] : A | semmle.label | dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:389:69:389:72 | access to parameter dict [element, property Value] : A | semmle.label | access to parameter dict [element, property Value] : A |
|
||||
| CollectionFlow.cs:389:69:389:79 | access to property Values [element] : A | semmle.label | access to property Values [element] : A |
|
||||
| CollectionFlow.cs:389:69:389:87 | call to method First<T> : A | semmle.label | call to method First<T> : A |
|
||||
| CollectionFlow.cs:391:58:391:61 | dict : Dictionary<T,T> [element, property Key] : A | semmle.label | dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:391:67:391:70 | access to parameter dict : Dictionary<T,T> [element, property Key] : A | semmle.label | access to parameter dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:391:67:391:75 | access to property Keys : ICollection<T> [element] : A | semmle.label | access to property Keys : ICollection<T> [element] : A |
|
||||
| CollectionFlow.cs:391:58:391:61 | dict [element, property Key] : A | semmle.label | dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:391:67:391:70 | access to parameter dict [element, property Key] : A | semmle.label | access to parameter dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:391:67:391:75 | access to property Keys [element] : A | semmle.label | access to property Keys [element] : A |
|
||||
| CollectionFlow.cs:391:67:391:83 | call to method First<T> : A | semmle.label | call to method First<T> : A |
|
||||
| CollectionFlow.cs:393:57:393:60 | dict : Dictionary<T,T> [element, property Key] : A | semmle.label | dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:393:66:393:69 | access to parameter dict : Dictionary<T,T> [element, property Key] : A | semmle.label | access to parameter dict : Dictionary<T,T> [element, property Key] : A |
|
||||
| CollectionFlow.cs:393:66:393:77 | call to method First<KeyValuePair<T,Int32>> : Object [property Key] : A | semmle.label | call to method First<KeyValuePair<T,Int32>> : Object [property Key] : A |
|
||||
| CollectionFlow.cs:393:57:393:60 | dict [element, property Key] : A | semmle.label | dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:393:66:393:69 | access to parameter dict [element, property Key] : A | semmle.label | access to parameter dict [element, property Key] : A |
|
||||
| CollectionFlow.cs:393:66:393:77 | call to method First<KeyValuePair<T,Int32>> [property Key] : A | semmle.label | call to method First<KeyValuePair<T,Int32>> [property Key] : A |
|
||||
| CollectionFlow.cs:393:66:393:81 | access to property Key : A | semmle.label | access to property Key : A |
|
||||
| CollectionFlow.cs:395:49:395:52 | args : A[] [element] : A | semmle.label | args : A[] [element] : A |
|
||||
| CollectionFlow.cs:395:49:395:52 | args : null [element] : A | semmle.label | args : null [element] : A |
|
||||
| CollectionFlow.cs:395:63:395:66 | access to parameter args : A[] [element] : A | semmle.label | access to parameter args : A[] [element] : A |
|
||||
| CollectionFlow.cs:395:63:395:66 | access to parameter args : null [element] : A | semmle.label | access to parameter args : null [element] : A |
|
||||
| CollectionFlow.cs:395:49:395:52 | args [element] : A | semmle.label | args [element] : A |
|
||||
| CollectionFlow.cs:395:49:395:52 | args [element] : A | semmle.label | args [element] : A |
|
||||
| CollectionFlow.cs:395:63:395:66 | access to parameter args [element] : A | semmle.label | access to parameter args [element] : A |
|
||||
| CollectionFlow.cs:395:63:395:66 | access to parameter args [element] : A | semmle.label | access to parameter args [element] : A |
|
||||
| CollectionFlow.cs:395:63:395:69 | access to array element | semmle.label | access to array element |
|
||||
subpaths
|
||||
| CollectionFlow.cs:17:20:17:22 | access to local variable as : null [element] : A | CollectionFlow.cs:381:34:381:35 | ts : null [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A | CollectionFlow.cs:17:14:17:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:35:20:35:23 | access to field As : A[] [element] : A | CollectionFlow.cs:381:34:381:35 | ts : A[] [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A | CollectionFlow.cs:35:14:35:24 | call to method First<A> |
|
||||
| CollectionFlow.cs:54:20:54:22 | access to local variable as : A[] [element] : A | CollectionFlow.cs:381:34:381:35 | ts : A[] [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A | CollectionFlow.cs:54:14:54:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:74:24:74:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A | CollectionFlow.cs:74:14:74:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:92:24:92:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A | CollectionFlow.cs:92:14:92:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:110:24:110:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A | CollectionFlow.cs:110:14:110:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:129:28:129:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:385:67:385:73 | access to indexer : A | CollectionFlow.cs:129:14:129:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:130:29:130:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:387:68:387:85 | access to property Value : A | CollectionFlow.cs:130:14:130:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:131:30:131:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:389:69:389:87 | call to method First<T> : A | CollectionFlow.cs:131:14:131:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:151:28:151:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:385:67:385:73 | access to indexer : A | CollectionFlow.cs:151:14:151:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:152:29:152:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:387:68:387:85 | access to property Value : A | CollectionFlow.cs:152:14:152:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:153:30:153:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:389:69:389:87 | call to method First<T> : A | CollectionFlow.cs:153:14:153:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:172:28:172:31 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:385:67:385:73 | access to indexer : A | CollectionFlow.cs:172:14:172:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:173:29:173:32 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:387:68:387:85 | access to property Value : A | CollectionFlow.cs:173:14:173:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:174:30:174:33 | access to local variable dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict : Dictionary<T,T> [element, property Value] : A | CollectionFlow.cs:389:69:389:87 | call to method First<T> : A | CollectionFlow.cs:174:14:174:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:194:28:194:31 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:391:58:391:61 | dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:391:67:391:83 | call to method First<T> : A | CollectionFlow.cs:194:14:194:32 | call to method DictKeysFirst<A> |
|
||||
| CollectionFlow.cs:195:27:195:30 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:393:57:393:60 | dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:393:66:393:81 | access to property Key : A | CollectionFlow.cs:195:14:195:31 | call to method DictFirstKey<A> |
|
||||
| CollectionFlow.cs:213:28:213:31 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:391:58:391:61 | dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:391:67:391:83 | call to method First<T> : A | CollectionFlow.cs:213:14:213:32 | call to method DictKeysFirst<A> |
|
||||
| CollectionFlow.cs:214:27:214:30 | access to local variable dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:393:57:393:60 | dict : Dictionary<T,T> [element, property Key] : A | CollectionFlow.cs:393:66:393:81 | access to property Key : A | CollectionFlow.cs:214:14:214:31 | call to method DictFirstKey<A> |
|
||||
| CollectionFlow.cs:307:23:307:23 | access to local variable a : A | CollectionFlow.cs:301:32:301:38 | element : A | CollectionFlow.cs:301:44:301:48 | [post] access to parameter array : A[] [element] : A | CollectionFlow.cs:307:18:307:20 | [post] access to local variable as : A[] [element] : A |
|
||||
| CollectionFlow.cs:310:20:310:22 | access to local variable as : A[] [element] : A | CollectionFlow.cs:381:34:381:35 | ts : A[] [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A | CollectionFlow.cs:310:14:310:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:329:23:329:23 | access to local variable a : A | CollectionFlow.cs:323:34:323:40 | element : A | CollectionFlow.cs:323:46:323:49 | [post] access to parameter list : List<T> [element] : A | CollectionFlow.cs:329:17:329:20 | [post] access to local variable list : List<T> [element] : A |
|
||||
| CollectionFlow.cs:332:24:332:27 | access to local variable list : List<T> [element] : A | CollectionFlow.cs:383:43:383:46 | list : List<T> [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A | CollectionFlow.cs:332:14:332:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:17:20:17:22 | access to local variable as [element] : A | CollectionFlow.cs:381:34:381:35 | ts [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A | CollectionFlow.cs:17:14:17:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:35:20:35:23 | access to field As [element] : A | CollectionFlow.cs:381:34:381:35 | ts [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A | CollectionFlow.cs:35:14:35:24 | call to method First<A> |
|
||||
| CollectionFlow.cs:54:20:54:22 | access to local variable as [element] : A | CollectionFlow.cs:381:34:381:35 | ts [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A | CollectionFlow.cs:54:14:54:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:74:24:74:27 | access to local variable list [element] : A | CollectionFlow.cs:383:43:383:46 | list [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A | CollectionFlow.cs:74:14:74:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:92:24:92:27 | access to local variable list [element] : A | CollectionFlow.cs:383:43:383:46 | list [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A | CollectionFlow.cs:92:14:92:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:110:24:110:27 | access to local variable list [element] : A | CollectionFlow.cs:383:43:383:46 | list [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A | CollectionFlow.cs:110:14:110:28 | call to method ListFirst<A> |
|
||||
| CollectionFlow.cs:129:28:129:31 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict [element, property Value] : A | CollectionFlow.cs:385:67:385:73 | access to indexer : A | CollectionFlow.cs:129:14:129:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:130:29:130:32 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict [element, property Value] : A | CollectionFlow.cs:387:68:387:85 | access to property Value : A | CollectionFlow.cs:130:14:130:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:131:30:131:33 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict [element, property Value] : A | CollectionFlow.cs:389:69:389:87 | call to method First<T> : A | CollectionFlow.cs:131:14:131:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:151:28:151:31 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict [element, property Value] : A | CollectionFlow.cs:385:67:385:73 | access to indexer : A | CollectionFlow.cs:151:14:151:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:152:29:152:32 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict [element, property Value] : A | CollectionFlow.cs:387:68:387:85 | access to property Value : A | CollectionFlow.cs:152:14:152:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:153:30:153:33 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict [element, property Value] : A | CollectionFlow.cs:389:69:389:87 | call to method First<T> : A | CollectionFlow.cs:153:14:153:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:172:28:172:31 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:385:58:385:61 | dict [element, property Value] : A | CollectionFlow.cs:385:67:385:73 | access to indexer : A | CollectionFlow.cs:172:14:172:32 | call to method DictIndexZero<A> |
|
||||
| CollectionFlow.cs:173:29:173:32 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:387:59:387:62 | dict [element, property Value] : A | CollectionFlow.cs:387:68:387:85 | access to property Value : A | CollectionFlow.cs:173:14:173:33 | call to method DictFirstValue<A> |
|
||||
| CollectionFlow.cs:174:30:174:33 | access to local variable dict [element, property Value] : A | CollectionFlow.cs:389:60:389:63 | dict [element, property Value] : A | CollectionFlow.cs:389:69:389:87 | call to method First<T> : A | CollectionFlow.cs:174:14:174:34 | call to method DictValuesFirst<A> |
|
||||
| CollectionFlow.cs:194:28:194:31 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:391:58:391:61 | dict [element, property Key] : A | CollectionFlow.cs:391:67:391:83 | call to method First<T> : A | CollectionFlow.cs:194:14:194:32 | call to method DictKeysFirst<A> |
|
||||
| CollectionFlow.cs:195:27:195:30 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:393:57:393:60 | dict [element, property Key] : A | CollectionFlow.cs:393:66:393:81 | access to property Key : A | CollectionFlow.cs:195:14:195:31 | call to method DictFirstKey<A> |
|
||||
| CollectionFlow.cs:213:28:213:31 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:391:58:391:61 | dict [element, property Key] : A | CollectionFlow.cs:391:67:391:83 | call to method First<T> : A | CollectionFlow.cs:213:14:213:32 | call to method DictKeysFirst<A> |
|
||||
| CollectionFlow.cs:214:27:214:30 | access to local variable dict [element, property Key] : A | CollectionFlow.cs:393:57:393:60 | dict [element, property Key] : A | CollectionFlow.cs:393:66:393:81 | access to property Key : A | CollectionFlow.cs:214:14:214:31 | call to method DictFirstKey<A> |
|
||||
| CollectionFlow.cs:307:23:307:23 | access to local variable a : A | CollectionFlow.cs:301:32:301:38 | element : A | CollectionFlow.cs:301:44:301:48 | [post] access to parameter array [element] : A | CollectionFlow.cs:307:18:307:20 | [post] access to local variable as [element] : A |
|
||||
| CollectionFlow.cs:310:20:310:22 | access to local variable as [element] : A | CollectionFlow.cs:381:34:381:35 | ts [element] : A | CollectionFlow.cs:381:41:381:45 | access to array element : A | CollectionFlow.cs:310:14:310:23 | call to method First<A> |
|
||||
| CollectionFlow.cs:329:23:329:23 | access to local variable a : A | CollectionFlow.cs:323:34:323:40 | element : A | CollectionFlow.cs:323:46:323:49 | [post] access to parameter list [element] : A | CollectionFlow.cs:329:17:329:20 | [post] access to local variable list [element] : A |
|
||||
| CollectionFlow.cs:332:24:332:27 | access to local variable list [element] : A | CollectionFlow.cs:383:43:383:46 | list [element] : A | CollectionFlow.cs:383:52:383:58 | access to indexer : A | CollectionFlow.cs:332:14:332:28 | call to method ListFirst<A> |
|
||||
#select
|
||||
| CollectionFlow.cs:13:17:13:23 | object creation of type A : A | CollectionFlow.cs:13:17:13:23 | object creation of type A : A | CollectionFlow.cs:15:14:15:19 | access to array element | $@ | CollectionFlow.cs:15:14:15:19 | access to array element | access to array element |
|
||||
| CollectionFlow.cs:13:17:13:23 | object creation of type A : A | CollectionFlow.cs:13:17:13:23 | object creation of type A : A | CollectionFlow.cs:17:14:17:23 | call to method First<A> | $@ | CollectionFlow.cs:17:14:17:23 | call to method First<A> | call to method First<A> |
|
||||
|
||||
@@ -1,23 +1,23 @@
|
||||
import csharp
|
||||
import semmle.code.csharp.dataflow.internal.ContentDataFlow as ContentDataFlow
|
||||
import semmle.code.csharp.dataflow.internal.ContentDataFlow
|
||||
|
||||
module ContentConfig implements ContentDataFlow::ConfigSig {
|
||||
predicate isSource(DataFlow::Node src) { src.asExpr() instanceof ObjectCreation }
|
||||
class Conf extends ContentDataFlow::Configuration {
|
||||
Conf() { this = "ContentFlowConf" }
|
||||
|
||||
predicate isSink(DataFlow::Node sink) {
|
||||
override predicate isSource(DataFlow::Node src) { src.asExpr() instanceof ObjectCreation }
|
||||
|
||||
override predicate isSink(DataFlow::Node sink) {
|
||||
exists(MethodCall mc |
|
||||
mc.getTarget().hasUndecoratedName("Sink") and
|
||||
mc.getAnArgument() = sink.asExpr()
|
||||
)
|
||||
}
|
||||
|
||||
int accessPathLimit() { result = 2 }
|
||||
override int accessPathLimit() { result = 2 }
|
||||
}
|
||||
|
||||
module ContentFlow = ContentDataFlow::Global<ContentConfig>;
|
||||
|
||||
from
|
||||
DataFlow::Node source, ContentFlow::AccessPath sourceAp, DataFlow::Node sink,
|
||||
ContentFlow::AccessPath sinkAp, boolean preservesValue
|
||||
where ContentFlow::flow(source, sourceAp, sink, sinkAp, preservesValue)
|
||||
Conf conf, ContentDataFlow::Node source, ContentDataFlow::AccessPath sourceAp,
|
||||
ContentDataFlow::Node sink, ContentDataFlow::AccessPath sinkAp, boolean preservesValue
|
||||
where conf.hasFlow(source, sourceAp, sink, sinkAp, preservesValue)
|
||||
select source, sourceAp, sink, sinkAp, preservesValue
|
||||
|
||||
@@ -9,59 +9,59 @@ edges
|
||||
| ExternalFlow.cs:23:27:23:38 | object creation of type Object : Object | ExternalFlow.cs:24:25:24:28 | access to local variable arg2 : Object |
|
||||
| ExternalFlow.cs:24:13:24:29 | [post] this access : D | ExternalFlow.cs:25:18:25:21 | this access |
|
||||
| ExternalFlow.cs:24:25:24:28 | access to local variable arg2 : Object | ExternalFlow.cs:24:13:24:29 | [post] this access : D |
|
||||
| ExternalFlow.cs:30:13:30:16 | [post] this access : D [field Field] : Object | ExternalFlow.cs:31:18:31:21 | this access : D [field Field] : Object |
|
||||
| ExternalFlow.cs:30:26:30:37 | object creation of type Object : Object | ExternalFlow.cs:30:13:30:16 | [post] this access : D [field Field] : Object |
|
||||
| ExternalFlow.cs:31:18:31:21 | this access : D [field Field] : Object | ExternalFlow.cs:31:18:31:39 | call to method StepFieldGetter |
|
||||
| ExternalFlow.cs:36:19:36:62 | (...) ... : Object [field Field] : Object | ExternalFlow.cs:36:18:36:69 | access to field Field |
|
||||
| ExternalFlow.cs:36:22:36:25 | [post] this access : D [field Field] : Object | ExternalFlow.cs:37:18:37:21 | this access : D [field Field] : Object |
|
||||
| ExternalFlow.cs:36:22:36:55 | call to method StepFieldSetter : D [field Field2, field Field] : Object | ExternalFlow.cs:36:22:36:62 | access to field Field2 : Object [field Field] : Object |
|
||||
| ExternalFlow.cs:36:22:36:62 | access to field Field2 : Object [field Field] : Object | ExternalFlow.cs:36:19:36:62 | (...) ... : Object [field Field] : Object |
|
||||
| ExternalFlow.cs:36:43:36:54 | object creation of type Object : Object | ExternalFlow.cs:36:22:36:25 | [post] this access : D [field Field] : Object |
|
||||
| ExternalFlow.cs:36:43:36:54 | object creation of type Object : Object | ExternalFlow.cs:36:22:36:55 | call to method StepFieldSetter : D [field Field2, field Field] : Object |
|
||||
| ExternalFlow.cs:37:18:37:21 | this access : D [field Field] : Object | ExternalFlow.cs:37:18:37:27 | access to field Field |
|
||||
| ExternalFlow.cs:42:13:42:16 | [post] this access : D [property Property] : Object | ExternalFlow.cs:43:18:43:21 | this access : D [property Property] : Object |
|
||||
| ExternalFlow.cs:42:29:42:40 | object creation of type Object : Object | ExternalFlow.cs:42:13:42:16 | [post] this access : D [property Property] : Object |
|
||||
| ExternalFlow.cs:43:18:43:21 | this access : D [property Property] : Object | ExternalFlow.cs:43:18:43:42 | call to method StepPropertyGetter |
|
||||
| ExternalFlow.cs:48:13:48:16 | [post] this access : D [property Property] : Object | ExternalFlow.cs:49:18:49:21 | this access : D [property Property] : Object |
|
||||
| ExternalFlow.cs:48:37:48:48 | object creation of type Object : Object | ExternalFlow.cs:48:13:48:16 | [post] this access : D [property Property] : Object |
|
||||
| ExternalFlow.cs:49:18:49:21 | this access : D [property Property] : Object | ExternalFlow.cs:49:18:49:30 | access to property Property |
|
||||
| ExternalFlow.cs:54:13:54:16 | [post] this access : D [element] : Object | ExternalFlow.cs:55:18:55:21 | this access : D [element] : Object |
|
||||
| ExternalFlow.cs:54:36:54:47 | object creation of type Object : Object | ExternalFlow.cs:54:13:54:16 | [post] this access : D [element] : Object |
|
||||
| ExternalFlow.cs:55:18:55:21 | this access : D [element] : Object | ExternalFlow.cs:55:18:55:41 | call to method StepElementGetter |
|
||||
| ExternalFlow.cs:30:13:30:16 | [post] this access [field Field] : Object | ExternalFlow.cs:31:18:31:21 | this access [field Field] : Object |
|
||||
| ExternalFlow.cs:30:26:30:37 | object creation of type Object : Object | ExternalFlow.cs:30:13:30:16 | [post] this access [field Field] : Object |
|
||||
| ExternalFlow.cs:31:18:31:21 | this access [field Field] : Object | ExternalFlow.cs:31:18:31:39 | call to method StepFieldGetter |
|
||||
| ExternalFlow.cs:36:19:36:62 | (...) ... [field Field] : Object | ExternalFlow.cs:36:18:36:69 | access to field Field |
|
||||
| ExternalFlow.cs:36:22:36:25 | [post] this access [field Field] : Object | ExternalFlow.cs:37:18:37:21 | this access [field Field] : Object |
|
||||
| ExternalFlow.cs:36:22:36:55 | call to method StepFieldSetter [field Field2, field Field] : Object | ExternalFlow.cs:36:22:36:62 | access to field Field2 [field Field] : Object |
|
||||
| ExternalFlow.cs:36:22:36:62 | access to field Field2 [field Field] : Object | ExternalFlow.cs:36:19:36:62 | (...) ... [field Field] : Object |
|
||||
| ExternalFlow.cs:36:43:36:54 | object creation of type Object : Object | ExternalFlow.cs:36:22:36:25 | [post] this access [field Field] : Object |
|
||||
| ExternalFlow.cs:36:43:36:54 | object creation of type Object : Object | ExternalFlow.cs:36:22:36:55 | call to method StepFieldSetter [field Field2, field Field] : Object |
|
||||
| ExternalFlow.cs:37:18:37:21 | this access [field Field] : Object | ExternalFlow.cs:37:18:37:27 | access to field Field |
|
||||
| ExternalFlow.cs:42:13:42:16 | [post] this access [property Property] : Object | ExternalFlow.cs:43:18:43:21 | this access [property Property] : Object |
|
||||
| ExternalFlow.cs:42:29:42:40 | object creation of type Object : Object | ExternalFlow.cs:42:13:42:16 | [post] this access [property Property] : Object |
|
||||
| ExternalFlow.cs:43:18:43:21 | this access [property Property] : Object | ExternalFlow.cs:43:18:43:42 | call to method StepPropertyGetter |
|
||||
| ExternalFlow.cs:48:13:48:16 | [post] this access [property Property] : Object | ExternalFlow.cs:49:18:49:21 | this access [property Property] : Object |
|
||||
| ExternalFlow.cs:48:37:48:48 | object creation of type Object : Object | ExternalFlow.cs:48:13:48:16 | [post] this access [property Property] : Object |
|
||||
| ExternalFlow.cs:49:18:49:21 | this access [property Property] : Object | ExternalFlow.cs:49:18:49:30 | access to property Property |
|
||||
| ExternalFlow.cs:54:13:54:16 | [post] this access [element] : Object | ExternalFlow.cs:55:18:55:21 | this access [element] : Object |
|
||||
| ExternalFlow.cs:54:36:54:47 | object creation of type Object : Object | ExternalFlow.cs:54:13:54:16 | [post] this access [element] : Object |
|
||||
| ExternalFlow.cs:55:18:55:21 | this access [element] : Object | ExternalFlow.cs:55:18:55:41 | call to method StepElementGetter |
|
||||
| ExternalFlow.cs:60:35:60:35 | o : Object | ExternalFlow.cs:60:47:60:47 | access to parameter o |
|
||||
| ExternalFlow.cs:60:64:60:75 | object creation of type Object : Object | ExternalFlow.cs:60:35:60:35 | o : Object |
|
||||
| ExternalFlow.cs:65:21:65:60 | call to method Apply<Int32,Object> : Object | ExternalFlow.cs:66:18:66:18 | access to local variable o |
|
||||
| ExternalFlow.cs:65:45:65:56 | object creation of type Object : Object | ExternalFlow.cs:65:21:65:60 | call to method Apply<Int32,Object> : Object |
|
||||
| ExternalFlow.cs:71:30:71:45 | { ..., ... } : null [element] : Object | ExternalFlow.cs:72:17:72:20 | access to local variable objs : null [element] : Object |
|
||||
| ExternalFlow.cs:71:32:71:43 | object creation of type Object : Object | ExternalFlow.cs:71:30:71:45 | { ..., ... } : null [element] : Object |
|
||||
| ExternalFlow.cs:72:17:72:20 | access to local variable objs : null [element] : Object | ExternalFlow.cs:72:23:72:23 | o : Object |
|
||||
| ExternalFlow.cs:71:30:71:45 | { ..., ... } [element] : Object | ExternalFlow.cs:72:17:72:20 | access to local variable objs [element] : Object |
|
||||
| ExternalFlow.cs:71:32:71:43 | object creation of type Object : Object | ExternalFlow.cs:71:30:71:45 | { ..., ... } [element] : Object |
|
||||
| ExternalFlow.cs:72:17:72:20 | access to local variable objs [element] : Object | ExternalFlow.cs:72:23:72:23 | o : Object |
|
||||
| ExternalFlow.cs:72:23:72:23 | o : Object | ExternalFlow.cs:72:35:72:35 | access to parameter o |
|
||||
| ExternalFlow.cs:77:24:77:58 | call to method Map<Int32,Object> : T[] [element] : Object | ExternalFlow.cs:78:18:78:21 | access to local variable objs : T[] [element] : Object |
|
||||
| ExternalFlow.cs:77:46:77:57 | object creation of type Object : Object | ExternalFlow.cs:77:24:77:58 | call to method Map<Int32,Object> : T[] [element] : Object |
|
||||
| ExternalFlow.cs:78:18:78:21 | access to local variable objs : T[] [element] : Object | ExternalFlow.cs:78:18:78:24 | access to array element : Object |
|
||||
| ExternalFlow.cs:77:24:77:58 | call to method Map<Int32,Object> [element] : Object | ExternalFlow.cs:78:18:78:21 | access to local variable objs [element] : Object |
|
||||
| ExternalFlow.cs:77:46:77:57 | object creation of type Object : Object | ExternalFlow.cs:77:24:77:58 | call to method Map<Int32,Object> [element] : Object |
|
||||
| ExternalFlow.cs:78:18:78:21 | access to local variable objs [element] : Object | ExternalFlow.cs:78:18:78:24 | access to array element : Object |
|
||||
| ExternalFlow.cs:78:18:78:24 | access to array element : Object | ExternalFlow.cs:78:18:78:24 | (...) ... |
|
||||
| ExternalFlow.cs:83:30:83:45 | { ..., ... } : null [element] : Object | ExternalFlow.cs:84:29:84:32 | access to local variable objs : null [element] : Object |
|
||||
| ExternalFlow.cs:83:32:83:43 | object creation of type Object : Object | ExternalFlow.cs:83:30:83:45 | { ..., ... } : null [element] : Object |
|
||||
| ExternalFlow.cs:84:25:84:41 | call to method Map<Object,Object> : T[] [element] : Object | ExternalFlow.cs:85:18:85:22 | access to local variable objs2 : T[] [element] : Object |
|
||||
| ExternalFlow.cs:84:29:84:32 | access to local variable objs : null [element] : Object | ExternalFlow.cs:84:25:84:41 | call to method Map<Object,Object> : T[] [element] : Object |
|
||||
| ExternalFlow.cs:85:18:85:22 | access to local variable objs2 : T[] [element] : Object | ExternalFlow.cs:85:18:85:25 | access to array element |
|
||||
| ExternalFlow.cs:83:30:83:45 | { ..., ... } [element] : Object | ExternalFlow.cs:84:29:84:32 | access to local variable objs [element] : Object |
|
||||
| ExternalFlow.cs:83:32:83:43 | object creation of type Object : Object | ExternalFlow.cs:83:30:83:45 | { ..., ... } [element] : Object |
|
||||
| ExternalFlow.cs:84:25:84:41 | call to method Map<Object,Object> [element] : Object | ExternalFlow.cs:85:18:85:22 | access to local variable objs2 [element] : Object |
|
||||
| ExternalFlow.cs:84:29:84:32 | access to local variable objs [element] : Object | ExternalFlow.cs:84:25:84:41 | call to method Map<Object,Object> [element] : Object |
|
||||
| ExternalFlow.cs:85:18:85:22 | access to local variable objs2 [element] : Object | ExternalFlow.cs:85:18:85:25 | access to array element |
|
||||
| ExternalFlow.cs:90:21:90:34 | object creation of type String : String | ExternalFlow.cs:91:19:91:19 | access to local variable s : String |
|
||||
| ExternalFlow.cs:91:19:91:19 | access to local variable s : String | ExternalFlow.cs:91:30:91:30 | SSA def(i) : Int32 |
|
||||
| ExternalFlow.cs:91:30:91:30 | SSA def(i) : Int32 | ExternalFlow.cs:92:18:92:18 | (...) ... |
|
||||
| ExternalFlow.cs:98:13:98:14 | [post] access to local variable d1 : D [field Field] : Object | ExternalFlow.cs:103:16:103:17 | access to local variable d1 : D [field Field] : Object |
|
||||
| ExternalFlow.cs:98:13:98:14 | [post] access to local variable d1 : D [field Field] : Object | ExternalFlow.cs:104:18:104:19 | access to local variable d1 : D [field Field] : Object |
|
||||
| ExternalFlow.cs:98:24:98:35 | object creation of type Object : Object | ExternalFlow.cs:98:13:98:14 | [post] access to local variable d1 : D [field Field] : Object |
|
||||
| ExternalFlow.cs:98:13:98:14 | [post] access to local variable d1 [field Field] : Object | ExternalFlow.cs:103:16:103:17 | access to local variable d1 [field Field] : Object |
|
||||
| ExternalFlow.cs:98:13:98:14 | [post] access to local variable d1 [field Field] : Object | ExternalFlow.cs:104:18:104:19 | access to local variable d1 [field Field] : Object |
|
||||
| ExternalFlow.cs:98:24:98:35 | object creation of type Object : Object | ExternalFlow.cs:98:13:98:14 | [post] access to local variable d1 [field Field] : Object |
|
||||
| ExternalFlow.cs:100:20:100:20 | d : Object | ExternalFlow.cs:102:22:102:22 | access to parameter d |
|
||||
| ExternalFlow.cs:103:16:103:17 | access to local variable d1 : D [field Field] : Object | ExternalFlow.cs:100:20:100:20 | d : Object |
|
||||
| ExternalFlow.cs:104:18:104:19 | access to local variable d1 : D [field Field] : Object | ExternalFlow.cs:104:18:104:25 | access to field Field |
|
||||
| ExternalFlow.cs:111:13:111:13 | [post] access to local variable f : F [field MyField] : Object | ExternalFlow.cs:112:18:112:18 | access to local variable f : F [field MyField] : Object |
|
||||
| ExternalFlow.cs:111:24:111:35 | object creation of type Object : Object | ExternalFlow.cs:111:13:111:13 | [post] access to local variable f : F [field MyField] : Object |
|
||||
| ExternalFlow.cs:112:18:112:18 | access to local variable f : F [field MyField] : Object | ExternalFlow.cs:112:18:112:25 | access to property MyProp |
|
||||
| ExternalFlow.cs:117:34:117:49 | { ..., ... } : null [element] : Object | ExternalFlow.cs:118:29:118:29 | access to local variable a : null [element] : Object |
|
||||
| ExternalFlow.cs:117:36:117:47 | object creation of type Object : Object | ExternalFlow.cs:117:34:117:49 | { ..., ... } : null [element] : Object |
|
||||
| ExternalFlow.cs:118:21:118:30 | call to method Reverse : null [element] : Object | ExternalFlow.cs:120:18:120:18 | access to local variable b : null [element] : Object |
|
||||
| ExternalFlow.cs:118:29:118:29 | access to local variable a : null [element] : Object | ExternalFlow.cs:118:21:118:30 | call to method Reverse : null [element] : Object |
|
||||
| ExternalFlow.cs:120:18:120:18 | access to local variable b : null [element] : Object | ExternalFlow.cs:120:18:120:21 | access to array element |
|
||||
| ExternalFlow.cs:103:16:103:17 | access to local variable d1 [field Field] : Object | ExternalFlow.cs:100:20:100:20 | d : Object |
|
||||
| ExternalFlow.cs:104:18:104:19 | access to local variable d1 [field Field] : Object | ExternalFlow.cs:104:18:104:25 | access to field Field |
|
||||
| ExternalFlow.cs:111:13:111:13 | [post] access to local variable f [field MyField] : Object | ExternalFlow.cs:112:18:112:18 | access to local variable f [field MyField] : Object |
|
||||
| ExternalFlow.cs:111:24:111:35 | object creation of type Object : Object | ExternalFlow.cs:111:13:111:13 | [post] access to local variable f [field MyField] : Object |
|
||||
| ExternalFlow.cs:112:18:112:18 | access to local variable f [field MyField] : Object | ExternalFlow.cs:112:18:112:25 | access to property MyProp |
|
||||
| ExternalFlow.cs:117:34:117:49 | { ..., ... } [element] : Object | ExternalFlow.cs:118:29:118:29 | access to local variable a [element] : Object |
|
||||
| ExternalFlow.cs:117:36:117:47 | object creation of type Object : Object | ExternalFlow.cs:117:34:117:49 | { ..., ... } [element] : Object |
|
||||
| ExternalFlow.cs:118:21:118:30 | call to method Reverse [element] : Object | ExternalFlow.cs:120:18:120:18 | access to local variable b [element] : Object |
|
||||
| ExternalFlow.cs:118:29:118:29 | access to local variable a [element] : Object | ExternalFlow.cs:118:21:118:30 | call to method Reverse [element] : Object |
|
||||
| ExternalFlow.cs:120:18:120:18 | access to local variable b [element] : Object | ExternalFlow.cs:120:18:120:21 | access to array element |
|
||||
| ExternalFlow.cs:187:21:187:32 | object creation of type Object : Object | ExternalFlow.cs:188:32:188:32 | access to local variable o : Object |
|
||||
| ExternalFlow.cs:188:32:188:32 | access to local variable o : Object | ExternalFlow.cs:188:18:188:33 | call to method GeneratedFlow |
|
||||
| ExternalFlow.cs:193:22:193:33 | object creation of type Object : Object | ExternalFlow.cs:194:36:194:37 | access to local variable o1 : Object |
|
||||
@@ -83,29 +83,29 @@ nodes
|
||||
| ExternalFlow.cs:24:13:24:29 | [post] this access : D | semmle.label | [post] this access : D |
|
||||
| ExternalFlow.cs:24:25:24:28 | access to local variable arg2 : Object | semmle.label | access to local variable arg2 : Object |
|
||||
| ExternalFlow.cs:25:18:25:21 | this access | semmle.label | this access |
|
||||
| ExternalFlow.cs:30:13:30:16 | [post] this access : D [field Field] : Object | semmle.label | [post] this access : D [field Field] : Object |
|
||||
| ExternalFlow.cs:30:13:30:16 | [post] this access [field Field] : Object | semmle.label | [post] this access [field Field] : Object |
|
||||
| ExternalFlow.cs:30:26:30:37 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:31:18:31:21 | this access : D [field Field] : Object | semmle.label | this access : D [field Field] : Object |
|
||||
| ExternalFlow.cs:31:18:31:21 | this access [field Field] : Object | semmle.label | this access [field Field] : Object |
|
||||
| ExternalFlow.cs:31:18:31:39 | call to method StepFieldGetter | semmle.label | call to method StepFieldGetter |
|
||||
| ExternalFlow.cs:36:18:36:69 | access to field Field | semmle.label | access to field Field |
|
||||
| ExternalFlow.cs:36:19:36:62 | (...) ... : Object [field Field] : Object | semmle.label | (...) ... : Object [field Field] : Object |
|
||||
| ExternalFlow.cs:36:22:36:25 | [post] this access : D [field Field] : Object | semmle.label | [post] this access : D [field Field] : Object |
|
||||
| ExternalFlow.cs:36:22:36:55 | call to method StepFieldSetter : D [field Field2, field Field] : Object | semmle.label | call to method StepFieldSetter : D [field Field2, field Field] : Object |
|
||||
| ExternalFlow.cs:36:22:36:62 | access to field Field2 : Object [field Field] : Object | semmle.label | access to field Field2 : Object [field Field] : Object |
|
||||
| ExternalFlow.cs:36:19:36:62 | (...) ... [field Field] : Object | semmle.label | (...) ... [field Field] : Object |
|
||||
| ExternalFlow.cs:36:22:36:25 | [post] this access [field Field] : Object | semmle.label | [post] this access [field Field] : Object |
|
||||
| ExternalFlow.cs:36:22:36:55 | call to method StepFieldSetter [field Field2, field Field] : Object | semmle.label | call to method StepFieldSetter [field Field2, field Field] : Object |
|
||||
| ExternalFlow.cs:36:22:36:62 | access to field Field2 [field Field] : Object | semmle.label | access to field Field2 [field Field] : Object |
|
||||
| ExternalFlow.cs:36:43:36:54 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:37:18:37:21 | this access : D [field Field] : Object | semmle.label | this access : D [field Field] : Object |
|
||||
| ExternalFlow.cs:37:18:37:21 | this access [field Field] : Object | semmle.label | this access [field Field] : Object |
|
||||
| ExternalFlow.cs:37:18:37:27 | access to field Field | semmle.label | access to field Field |
|
||||
| ExternalFlow.cs:42:13:42:16 | [post] this access : D [property Property] : Object | semmle.label | [post] this access : D [property Property] : Object |
|
||||
| ExternalFlow.cs:42:13:42:16 | [post] this access [property Property] : Object | semmle.label | [post] this access [property Property] : Object |
|
||||
| ExternalFlow.cs:42:29:42:40 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:43:18:43:21 | this access : D [property Property] : Object | semmle.label | this access : D [property Property] : Object |
|
||||
| ExternalFlow.cs:43:18:43:21 | this access [property Property] : Object | semmle.label | this access [property Property] : Object |
|
||||
| ExternalFlow.cs:43:18:43:42 | call to method StepPropertyGetter | semmle.label | call to method StepPropertyGetter |
|
||||
| ExternalFlow.cs:48:13:48:16 | [post] this access : D [property Property] : Object | semmle.label | [post] this access : D [property Property] : Object |
|
||||
| ExternalFlow.cs:48:13:48:16 | [post] this access [property Property] : Object | semmle.label | [post] this access [property Property] : Object |
|
||||
| ExternalFlow.cs:48:37:48:48 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:49:18:49:21 | this access : D [property Property] : Object | semmle.label | this access : D [property Property] : Object |
|
||||
| ExternalFlow.cs:49:18:49:21 | this access [property Property] : Object | semmle.label | this access [property Property] : Object |
|
||||
| ExternalFlow.cs:49:18:49:30 | access to property Property | semmle.label | access to property Property |
|
||||
| ExternalFlow.cs:54:13:54:16 | [post] this access : D [element] : Object | semmle.label | [post] this access : D [element] : Object |
|
||||
| ExternalFlow.cs:54:13:54:16 | [post] this access [element] : Object | semmle.label | [post] this access [element] : Object |
|
||||
| ExternalFlow.cs:54:36:54:47 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:55:18:55:21 | this access : D [element] : Object | semmle.label | this access : D [element] : Object |
|
||||
| ExternalFlow.cs:55:18:55:21 | this access [element] : Object | semmle.label | this access [element] : Object |
|
||||
| ExternalFlow.cs:55:18:55:41 | call to method StepElementGetter | semmle.label | call to method StepElementGetter |
|
||||
| ExternalFlow.cs:60:35:60:35 | o : Object | semmle.label | o : Object |
|
||||
| ExternalFlow.cs:60:47:60:47 | access to parameter o | semmle.label | access to parameter o |
|
||||
@@ -113,42 +113,42 @@ nodes
|
||||
| ExternalFlow.cs:65:21:65:60 | call to method Apply<Int32,Object> : Object | semmle.label | call to method Apply<Int32,Object> : Object |
|
||||
| ExternalFlow.cs:65:45:65:56 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:66:18:66:18 | access to local variable o | semmle.label | access to local variable o |
|
||||
| ExternalFlow.cs:71:30:71:45 | { ..., ... } : null [element] : Object | semmle.label | { ..., ... } : null [element] : Object |
|
||||
| ExternalFlow.cs:71:30:71:45 | { ..., ... } [element] : Object | semmle.label | { ..., ... } [element] : Object |
|
||||
| ExternalFlow.cs:71:32:71:43 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:72:17:72:20 | access to local variable objs : null [element] : Object | semmle.label | access to local variable objs : null [element] : Object |
|
||||
| ExternalFlow.cs:72:17:72:20 | access to local variable objs [element] : Object | semmle.label | access to local variable objs [element] : Object |
|
||||
| ExternalFlow.cs:72:23:72:23 | o : Object | semmle.label | o : Object |
|
||||
| ExternalFlow.cs:72:35:72:35 | access to parameter o | semmle.label | access to parameter o |
|
||||
| ExternalFlow.cs:77:24:77:58 | call to method Map<Int32,Object> : T[] [element] : Object | semmle.label | call to method Map<Int32,Object> : T[] [element] : Object |
|
||||
| ExternalFlow.cs:77:24:77:58 | call to method Map<Int32,Object> [element] : Object | semmle.label | call to method Map<Int32,Object> [element] : Object |
|
||||
| ExternalFlow.cs:77:46:77:57 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:78:18:78:21 | access to local variable objs : T[] [element] : Object | semmle.label | access to local variable objs : T[] [element] : Object |
|
||||
| ExternalFlow.cs:78:18:78:21 | access to local variable objs [element] : Object | semmle.label | access to local variable objs [element] : Object |
|
||||
| ExternalFlow.cs:78:18:78:24 | (...) ... | semmle.label | (...) ... |
|
||||
| ExternalFlow.cs:78:18:78:24 | access to array element : Object | semmle.label | access to array element : Object |
|
||||
| ExternalFlow.cs:83:30:83:45 | { ..., ... } : null [element] : Object | semmle.label | { ..., ... } : null [element] : Object |
|
||||
| ExternalFlow.cs:83:30:83:45 | { ..., ... } [element] : Object | semmle.label | { ..., ... } [element] : Object |
|
||||
| ExternalFlow.cs:83:32:83:43 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:84:25:84:41 | call to method Map<Object,Object> : T[] [element] : Object | semmle.label | call to method Map<Object,Object> : T[] [element] : Object |
|
||||
| ExternalFlow.cs:84:29:84:32 | access to local variable objs : null [element] : Object | semmle.label | access to local variable objs : null [element] : Object |
|
||||
| ExternalFlow.cs:85:18:85:22 | access to local variable objs2 : T[] [element] : Object | semmle.label | access to local variable objs2 : T[] [element] : Object |
|
||||
| ExternalFlow.cs:84:25:84:41 | call to method Map<Object,Object> [element] : Object | semmle.label | call to method Map<Object,Object> [element] : Object |
|
||||
| ExternalFlow.cs:84:29:84:32 | access to local variable objs [element] : Object | semmle.label | access to local variable objs [element] : Object |
|
||||
| ExternalFlow.cs:85:18:85:22 | access to local variable objs2 [element] : Object | semmle.label | access to local variable objs2 [element] : Object |
|
||||
| ExternalFlow.cs:85:18:85:25 | access to array element | semmle.label | access to array element |
|
||||
| ExternalFlow.cs:90:21:90:34 | object creation of type String : String | semmle.label | object creation of type String : String |
|
||||
| ExternalFlow.cs:91:19:91:19 | access to local variable s : String | semmle.label | access to local variable s : String |
|
||||
| ExternalFlow.cs:91:30:91:30 | SSA def(i) : Int32 | semmle.label | SSA def(i) : Int32 |
|
||||
| ExternalFlow.cs:92:18:92:18 | (...) ... | semmle.label | (...) ... |
|
||||
| ExternalFlow.cs:98:13:98:14 | [post] access to local variable d1 : D [field Field] : Object | semmle.label | [post] access to local variable d1 : D [field Field] : Object |
|
||||
| ExternalFlow.cs:98:13:98:14 | [post] access to local variable d1 [field Field] : Object | semmle.label | [post] access to local variable d1 [field Field] : Object |
|
||||
| ExternalFlow.cs:98:24:98:35 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:100:20:100:20 | d : Object | semmle.label | d : Object |
|
||||
| ExternalFlow.cs:102:22:102:22 | access to parameter d | semmle.label | access to parameter d |
|
||||
| ExternalFlow.cs:103:16:103:17 | access to local variable d1 : D [field Field] : Object | semmle.label | access to local variable d1 : D [field Field] : Object |
|
||||
| ExternalFlow.cs:104:18:104:19 | access to local variable d1 : D [field Field] : Object | semmle.label | access to local variable d1 : D [field Field] : Object |
|
||||
| ExternalFlow.cs:103:16:103:17 | access to local variable d1 [field Field] : Object | semmle.label | access to local variable d1 [field Field] : Object |
|
||||
| ExternalFlow.cs:104:18:104:19 | access to local variable d1 [field Field] : Object | semmle.label | access to local variable d1 [field Field] : Object |
|
||||
| ExternalFlow.cs:104:18:104:25 | access to field Field | semmle.label | access to field Field |
|
||||
| ExternalFlow.cs:111:13:111:13 | [post] access to local variable f : F [field MyField] : Object | semmle.label | [post] access to local variable f : F [field MyField] : Object |
|
||||
| ExternalFlow.cs:111:13:111:13 | [post] access to local variable f [field MyField] : Object | semmle.label | [post] access to local variable f [field MyField] : Object |
|
||||
| ExternalFlow.cs:111:24:111:35 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:112:18:112:18 | access to local variable f : F [field MyField] : Object | semmle.label | access to local variable f : F [field MyField] : Object |
|
||||
| ExternalFlow.cs:112:18:112:18 | access to local variable f [field MyField] : Object | semmle.label | access to local variable f [field MyField] : Object |
|
||||
| ExternalFlow.cs:112:18:112:25 | access to property MyProp | semmle.label | access to property MyProp |
|
||||
| ExternalFlow.cs:117:34:117:49 | { ..., ... } : null [element] : Object | semmle.label | { ..., ... } : null [element] : Object |
|
||||
| ExternalFlow.cs:117:34:117:49 | { ..., ... } [element] : Object | semmle.label | { ..., ... } [element] : Object |
|
||||
| ExternalFlow.cs:117:36:117:47 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:118:21:118:30 | call to method Reverse : null [element] : Object | semmle.label | call to method Reverse : null [element] : Object |
|
||||
| ExternalFlow.cs:118:29:118:29 | access to local variable a : null [element] : Object | semmle.label | access to local variable a : null [element] : Object |
|
||||
| ExternalFlow.cs:120:18:120:18 | access to local variable b : null [element] : Object | semmle.label | access to local variable b : null [element] : Object |
|
||||
| ExternalFlow.cs:118:21:118:30 | call to method Reverse [element] : Object | semmle.label | call to method Reverse [element] : Object |
|
||||
| ExternalFlow.cs:118:29:118:29 | access to local variable a [element] : Object | semmle.label | access to local variable a [element] : Object |
|
||||
| ExternalFlow.cs:120:18:120:18 | access to local variable b [element] : Object | semmle.label | access to local variable b [element] : Object |
|
||||
| ExternalFlow.cs:120:18:120:21 | access to array element | semmle.label | access to array element |
|
||||
| ExternalFlow.cs:187:21:187:32 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
|
||||
| ExternalFlow.cs:188:18:188:33 | call to method GeneratedFlow | semmle.label | call to method GeneratedFlow |
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user