Merge pull request #8431 from erik-krogh/deadCode

Delete dead code
This commit is contained in:
Erik Krogh Kristensen
2022-03-15 20:09:06 +01:00
committed by GitHub
37 changed files with 326 additions and 304 deletions

View File

@@ -447,26 +447,6 @@ private predicate skipInitializer(Initializer init) {
)
}
/**
* Holds if `e` is an expression in a static initializer that must be evaluated
* at run time. This predicate computes "is non-const" instead of "is const" in
* order to avoid recursion through forall.
*/
private predicate runtimeExprInStaticInitializer(Expr e) {
inStaticInitializer(e) and
if e instanceof AggregateLiteral
then runtimeExprInStaticInitializer(e.getAChild())
else not e.getFullyConverted().isConstant()
}
/** Holds if `e` is part of the initializer of a local static variable. */
private predicate inStaticInitializer(Expr e) {
exists(LocalVariable local |
local.isStatic() and
e.getParent+() = local.getInitializer()
)
}
/**
* Gets the `i`th child of `n` in control-flow order, where the `i`-indexes are
* contiguous, and the first index is 0.

View File

@@ -287,20 +287,6 @@ private module SsaDefReaches {
)
}
/**
* Holds if the SSA definition of `v` at `def` reaches uncertain SSA definition
* `redef` in the same basic block, without crossing another SSA definition of `v`.
*/
predicate ssaDefReachesUncertainDefWithinBlock(
SourceVariable v, Definition def, UncertainWriteDefinition redef
) {
exists(BasicBlock bb, int rnk, int i |
ssaDefReachesRank(bb, def, rnk, v) and
rnk = ssaRefRank(bb, i, v, SsaDef()) - 1 and
redef.definesAt(v, bb, i)
)
}
/**
* Same as `ssaRefRank()`, but restricted to a particular SSA definition `def`.
*/

View File

@@ -1,7 +1,5 @@
private import ReachableBlock as Reachability
private module ReachabilityGraph = Reachability::Graph;
module Graph {
import Reachability::Graph

View File

@@ -1,7 +1,5 @@
private import ReachableBlock as Reachability
private module ReachabilityGraph = Reachability::Graph;
module Graph {
import Reachability::Graph

View File

@@ -287,20 +287,6 @@ private module SsaDefReaches {
)
}
/**
* Holds if the SSA definition of `v` at `def` reaches uncertain SSA definition
* `redef` in the same basic block, without crossing another SSA definition of `v`.
*/
predicate ssaDefReachesUncertainDefWithinBlock(
SourceVariable v, Definition def, UncertainWriteDefinition redef
) {
exists(BasicBlock bb, int rnk, int i |
ssaDefReachesRank(bb, def, rnk, v) and
rnk = ssaRefRank(bb, i, v, SsaDef()) - 1 and
redef.definesAt(v, bb, i)
)
}
/**
* Same as `ssaRefRank()`, but restricted to a particular SSA definition `def`.
*/

View File

@@ -511,13 +511,6 @@ module FinallySplitting {
predicate isEntryNode() { first(try.getFinally(), this) }
}
/** A control flow element that does not belong to a `finally` block. */
private class NonFinallyControlFlowElement extends ControlFlowElement {
NonFinallyControlFlowElement() {
not this = any(Statements::TryStmtTree t).getAFinallyDescendant()
}
}
/**
* A split for elements belonging to a `finally` block, which determines how to
* continue execution after leaving the `finally` block. For example, in

View File

@@ -287,20 +287,6 @@ private module SsaDefReaches {
)
}
/**
* Holds if the SSA definition of `v` at `def` reaches uncertain SSA definition
* `redef` in the same basic block, without crossing another SSA definition of `v`.
*/
predicate ssaDefReachesUncertainDefWithinBlock(
SourceVariable v, Definition def, UncertainWriteDefinition redef
) {
exists(BasicBlock bb, int rnk, int i |
ssaDefReachesRank(bb, def, rnk, v) and
rnk = ssaRefRank(bb, i, v, SsaDef()) - 1 and
redef.definesAt(v, bb, i)
)
}
/**
* Same as `ssaRefRank()`, but restricted to a particular SSA definition `def`.
*/

View File

@@ -287,20 +287,6 @@ private module SsaDefReaches {
)
}
/**
* Holds if the SSA definition of `v` at `def` reaches uncertain SSA definition
* `redef` in the same basic block, without crossing another SSA definition of `v`.
*/
predicate ssaDefReachesUncertainDefWithinBlock(
SourceVariable v, Definition def, UncertainWriteDefinition redef
) {
exists(BasicBlock bb, int rnk, int i |
ssaDefReachesRank(bb, def, rnk, v) and
rnk = ssaRefRank(bb, i, v, SsaDef()) - 1 and
redef.definesAt(v, bb, i)
)
}
/**
* Same as `ssaRefRank()`, but restricted to a particular SSA definition `def`.
*/

View File

@@ -287,20 +287,6 @@ private module SsaDefReaches {
)
}
/**
* Holds if the SSA definition of `v` at `def` reaches uncertain SSA definition
* `redef` in the same basic block, without crossing another SSA definition of `v`.
*/
predicate ssaDefReachesUncertainDefWithinBlock(
SourceVariable v, Definition def, UncertainWriteDefinition redef
) {
exists(BasicBlock bb, int rnk, int i |
ssaDefReachesRank(bb, def, rnk, v) and
rnk = ssaRefRank(bb, i, v, SsaDef()) - 1 and
redef.definesAt(v, bb, i)
)
}
/**
* Same as `ssaRefRank()`, but restricted to a particular SSA definition `def`.
*/

View File

@@ -24,13 +24,6 @@ private class ServiceClass extends Class {
}
}
/** Top-level Request DTO types */
private class RequestDTO extends Class {
RequestDTO() {
this.getABaseType*().getABaseInterface().hasQualifiedName("ServiceStack", "IReturn")
}
}
/** Flow sources for the ServiceStack framework */
module Sources {
private import semmle.code.csharp.security.dataflow.flowsources.Remote

View File

@@ -11,13 +11,6 @@
import csharp
class ZeroFloatLiteral extends FloatLiteral {
ZeroFloatLiteral() {
this.getValue() = "0" or
this.getValue() = "0.0"
}
}
from EqualityOperation e
where
e.getAnOperand().getType() instanceof FloatingPointType and

View File

@@ -1,7 +1,5 @@
private import ReachableBlock as Reachability
private module ReachabilityGraph = Reachability::Graph;
module Graph {
import Reachability::Graph

View File

@@ -1,7 +1,5 @@
private import ReachableBlock as Reachability
private module ReachabilityGraph = Reachability::Graph;
module Graph {
import Reachability::Graph

View File

@@ -88,15 +88,6 @@ predicate hasAddressType(int byteSize) {
*/
predicate hasFunctionAddressType(int byteSize) { byteSize = getTypeSize(any(NullType type)) }
private int getBaseClassSize(ValueOrRefType type) {
if exists(type.getBaseClass()) then result = getContentSize(type.getBaseClass()) else result = 0
}
private int getContentSize(ValueOrRefType type) {
result =
getBaseClassSize(type) + sum(Field field | not field.isStatic() | getTypeSize(field.getType()))
}
private predicate isOpaqueType(ValueOrRefType type) {
type instanceof Struct or
type instanceof NullableType or

View File

@@ -9,26 +9,6 @@ import EJB
/** A method or constructor that may not be called from an EJB. */
abstract class ForbiddenCallable extends Callable { }
/**
* Specialized version of the `polyCalls(..)` predicate for the use
* case of finding "shortest" call chains from EJBs to forbidden
* methods. This is the same as `polyCalls(..)`, with two exceptions:
*
* - It does not consider calls into an EJB method.
* - It does not consider calls from "forbidden callables".
*/
private predicate ejbPolyCalls(Callable origin, Callable target) {
origin.polyCalls(target) and
not exists(EJB ejb | target = ejb.getACallable()) and
not origin instanceof ForbiddenCallable
}
private predicate ejbPolyCallsPlus(Callable origin, Callable target) {
exists(EJB ejb | origin = ejb.getACallable() | ejbPolyCalls(origin, target))
or
exists(Callable mid | ejbPolyCallsPlus(origin, mid) and ejbPolyCalls(mid, target))
}
/**
* Holds if there exists a call chain from an EJB-`Callable` `origin` to a `ForbiddenCallable` `target`
* that does not contain any intermediate EJB-`Callable` or `ForbiddenCallable`,

View File

@@ -16,13 +16,6 @@
import java
class ReachFromStmt extends Stmt {
ReachFromStmt() {
exists(Method m | m.getBody() = this) or
exists(WhileStmt w | w.getStmt() = this)
}
}
class SleepMethod extends Method {
SleepMethod() {
this.getName() = "sleep" and

View File

@@ -15,11 +15,6 @@ import semmle.code.java.Expr
import semmle.code.java.Statement
import semmle.code.java.JDK
/** A use of `+` that has type `String`. */
class StringCat extends AddExpr {
StringCat() { this.getType() instanceof TypeString }
}
/**
* An assignment of the form
*

View File

@@ -36,16 +36,6 @@ class MessageDigest extends RefType {
MessageDigest() { this.hasQualifiedName("java.security", "MessageDigest") }
}
/** The method call `MessageDigest.getInstance(...)` */
class MDConstructor extends StaticMethodAccess {
MDConstructor() {
exists(Method m | m = this.getMethod() |
m.getDeclaringType() instanceof MessageDigest and
m.hasName("getInstance")
)
}
}
/** The method `digest()` declared in `java.security.MessageDigest`. */
class MDDigestMethod extends Method {
MDDigestMethod() {

View File

@@ -9,15 +9,6 @@
import javascript
import InsecureDownloadCustomizations::InsecureDownload
// Materialize flow labels
private class ConcreteSensitiveInsecureUrl extends Label::SensitiveInsecureUrl {
ConcreteSensitiveInsecureUrl() { this = this }
}
private class ConcreteInsecureUrl extends Label::InsecureUrl {
ConcreteInsecureUrl() { this = this }
}
/**
* A taint tracking configuration for download of sensitive file through insecure connection.
*/

View File

@@ -969,12 +969,6 @@ private module Scopes {
scope = n.getEnclosingModule()
}
private predicate maybe_defined(SsaVariable var) {
exists(var.getDefinition()) and not py_ssa_phi(var, _) and not var.getDefinition().isDelete()
or
exists(SsaVariable input | input = var.getAPhiInput() | maybe_defined(input))
}
private predicate maybe_undefined(SsaVariable var) {
not exists(var.getDefinition()) and not py_ssa_phi(var, _)
or

View File

@@ -900,22 +900,6 @@ private class EssaTaintTracking extends string {
or
result = this.testEvaluates(defn, not_operand(test), use, src).booleanNot()
}
/**
* Holds if `test` is the test in a branch and `use` is that test
* with all the `not` prefixes removed.
*/
private predicate boolean_filter(ControlFlowNode test, ControlFlowNode use) {
any(PyEdgeRefinement ref).getTest() = test and
(
use = test
or
exists(ControlFlowNode notuse |
this.boolean_filter(test, notuse) and
use = not_operand(notuse)
)
)
}
}
private predicate testEvaluatesMaybe(ControlFlowNode test, ControlFlowNode use) {

View File

@@ -21,9 +21,6 @@ private module Invoke {
/** Provides models for the `invoke` module. */
module InvokeModule {
/** Gets a reference to the `invoke.context` module. */
API::Node context() { result = invoke().getMember("context") }
/** Provides models for the `invoke.context` module */
module Context {
/** Provides models for the `invoke.context.Context` class */

View File

@@ -295,17 +295,6 @@ private module RestFramework {
result = API::moduleImport("rest_framework").getMember("response").getMember("Response")
}
/**
* A source of instances of `rest_framework.response.Response`, extend this class to model new instances.
*
* This can include instantiations of the class, return values from function
* calls, or a special parameter that will be set when functions are called by an external
* library.
*
* Use the predicate `Response::instance()` to get references to instances of `rest_framework.response.Response`.
*/
abstract class InstanceSource extends DataFlow::LocalSourceNode { }
/** A direct instantiation of `rest_framework.response.Response`. */
private class ClassInstantiation extends PrivateDjango::DjangoImpl::Http::Response::HttpResponse::InstanceSource,
DataFlow::CallCfgNode {

View File

@@ -185,11 +185,6 @@ predicate function_can_never_return(FunctionObject func) {
func = ModuleObject::named("sys").attr("exit")
}
private newtype TIterationDefinition =
TIterationDefinition_(SsaSourceVariable var, ControlFlowNode def, ControlFlowNode sequence) {
SsaSource::iteration_defined_variable(var, def, sequence)
}
/** Hold if outer contains inner, both are contained within a test and inner is a use is a plain use or an attribute lookup */
pragma[noinline]
predicate contains_interesting_expression_within_test(ControlFlowNode outer, ControlFlowNode inner) {

View File

@@ -40,16 +40,6 @@ private predicate class_statement(Comment c) {
private predicate triple_quote(Comment c) { c.getText().regexpMatch("#.*(\"\"\"|''').*") }
private predicate triple_quoted_string_part(Comment start, Comment end) {
triple_quote(start) and end = start
or
exists(Comment mid |
triple_quoted_string_part(start, mid) and
end = non_empty_following(mid) and
not triple_quote(end)
)
}
private predicate maybe_code(Comment c) {
not non_code(c) and not filler(c) and not endline_comment(c) and not file_or_url(c)
or

View File

@@ -1,9 +1,5 @@
import python
class ImplicitConcat extends StrConst {
ImplicitConcat() { exists(this.getAnImplicitlyConcatenatedPart()) }
}
from StringPart s
select s.getLocation().getStartLine(), s.getText(), s.getLocation().getStartColumn(),
s.getLocation().getEndColumn()

View File

@@ -1,9 +1,5 @@
import python
class ImplicitConcat extends StrConst {
ImplicitConcat() { exists(this.getAnImplicitlyConcatenatedPart()) }
}
from StrConst s, StringPart part, int n
where part = s.getImplicitlyConcatenatedPart(n)
select s.getLocation().getStartLine(), s.getText(), n, part.getText()

View File

@@ -0,0 +1,44 @@
import ql
private import codeql_ql.ast.internal.Module
FileOrModule hasQueryRelation(ClasslessPredicate pred) {
pred.hasAnnotation("query") and
(
result.asModule().getAMember() = pred
or
any(TopLevel top | top.getLocation().getFile() = result.asFile()).getAMember() = pred
)
}
FileOrModule importsQueryRelation(ClasslessPredicate pred) {
result = hasQueryRelation(pred)
or
exists(Import i |
not (i.hasAnnotation("private") and i.getLocation().getFile().getExtension() = "qll") and
importsQueryRelation(pred) = i.getResolvedModule()
|
i = result.asModule().getAMember()
or
i = any(TopLevel top | top.getLocation().getFile() = result.asFile()).getAMember()
)
}
class Query extends File {
Query() { this.getExtension() = "ql" }
predicate isPathProblem() {
exists(QLDoc doc | doc.getLocation().getFile() = this |
doc.getContents().matches("%@kind path-problem%")
)
}
predicate isProblem() {
exists(QLDoc doc | doc.getLocation().getFile() = this |
doc.getContents().matches("%@kind problem%")
)
}
predicate hasEdgesRelation(ClasslessPredicate pred) {
importsQueryRelation(pred).asFile() = this and pred.getName() = "edges"
}
}

View File

@@ -0,0 +1,254 @@
import ql
import codeql_ql.bugs.PathProblemQueryQuery as PathProblemQuery
import codeql_ql.ast.internal.Module
/** Gets something that can be imported by a ".qll" file. */
private AstNode publicApi() {
// base case - the toplevel is always "exported".
result instanceof TopLevel
or
// recursive case. A public class/module/predicate/import that is a child of a public API.
not result.hasAnnotation("private") and
not result.getLocation().getFile().getExtension() = "ql" and // everything in ".ql" files is kinda private, as you can't import it. Query predicates/from-where-select is handled in `queryable`.
result.getParent() = publicApi() and
(
result instanceof Class
or
result instanceof ClasslessPredicate
or
result instanceof Module
or
result instanceof Import
)
or
result = publicApi().(Import).getResolvedModule().asModule()
}
/**
* Gets any AstNode that directly computes a result of a query.
* I.e. a query predicate or the from-where-select.
*/
private AstNode queryPredicate() {
// result = query relation that is "transitively" imported by a .ql file.
PathProblemQuery::importsQueryRelation(result).asFile().getExtension() = "ql"
or
// the from-where-select
result instanceof Select
or
// child of the above.
result = queryPredicate().getAChild()
}
AstNode hackyShouldBeTreatedAsAlive() {
// Stages from the shared DataFlow impl are copy-pasted, so predicates that are dead in one stage are not dead in another.
result = any(Module mod | mod.getName().matches("Stage%")).getAMember().(ClasslessPredicate) and
result.getLocation().getFile().getBaseName().matches("DataFlowImpl%")
or
// Python stuff
result.(Predicate).getName() = "quickEvalMe" // private predicate used for quick-eval
or
result.(Module).getName() = "FutureWork" // holder for later.
or
result = hackyShouldBeTreatedAsAlive().getAChild()
}
/**
* Gets an AST node that is alive.
* That is, an API node that may in some way be part of or affect a query result or a publicly available API.
*/
private AstNode alive() {
//
// The 4 base cases.
//
// 1) everything that can be imported.
result = publicApi()
or
// 2) everything that can be an output when running a query
result = queryPredicate()
or
// 3) A module with an import that imports another file, the import can activate a file.
result.(Module).getAMember().(Import).getResolvedModule().getFile() !=
result.getLocation().getFile()
or
// 4) Things that aren't really alive, but that this query treats as live.
result = hackyShouldBeTreatedAsAlive()
or
result instanceof TopLevel // toplevel is always alive.
or
// recurisve cases
result = aliveStep(alive())
}
private AstNode aliveStep(AstNode prev) {
//
// The recursive cases.
//
result.getEnclosingPredicate() = prev
or
result = prev.(Call).getTarget()
or
prev.(ClassPredicate).overrides(result)
or
result.(ClassPredicate).overrides(prev)
or
result = prev.(PredicateExpr).getResolvedPredicate()
or
// if a sub-class is alive, then the super-class is alive.
result = prev.(Class).getASuperType().getResolvedType().(ClassType).getDeclaration()
or
// if the super class is alive and abstract, then any sub-class is alive.
exists(Class sup | sup = prev and sup.isAbstract() |
sup = result.(Class).getASuperType().getResolvedType().(ClassType).getDeclaration()
)
or
result = prev.(Class).getAChild() and
not result.hasAnnotation("private")
or
result = prev.getAnAnnotation()
or
result = prev.getQLDoc()
or
// any imported module is alive. We don't have to handle the "import a file"-case, those are treated as public APIs.
result = prev.(Import).getResolvedModule().asModule()
or
result = prev.(VarDecl).getType().getDeclaration()
or
result = prev.(FieldDecl).getVarDecl()
or
result = prev.(InlineCast).getType().getDeclaration()
or
// a class overrides some predicate, is the super-predicate is alive.
exists(ClassPredicate pred, ClassPredicate sup |
pred.hasAnnotation("override") and
pred.overrides(sup) and
result = pred.getParent() and
sup.getParent() = prev
)
or
// if a class is alive, so is it's super-class
result =
[prev.(Class).getASuperType(), prev.(Class).getAnInstanceofType()]
.getResolvedType()
.getDeclaration()
or
// if a class is alive and abstract, then any sub-class is alive.
exists(Class clz, Class sup | result = clz |
clz.getASuperType().getResolvedType().getDeclaration() = sup and
sup.isAbstract() and
sup = prev
)
or
// a module containing something live, is also alive.
result.(Module).getAMember() = prev
or
result = prev.(Module).getAlias()
or
result.(NewType).getABranch() = prev
or
result = prev.(TypeExpr).getAChild()
or
result = prev.(FieldAccess).getDeclaration()
or
result = prev.(VarDecl).getTypeExpr()
or
result.(Import).getParent() = prev
or
result = prev.(NewType).getABranch()
or
result = prev.(ModuleExpr).getAChild()
or
result = prev.(ModuleExpr).getResolvedModule().asModule()
or
result = prev.(InstanceOf).getType().getResolvedType().getDeclaration()
or
result = prev.(Annotation).getAChild()
or
result = prev.(Predicate).getReturnType().getDeclaration()
}
private AstNode deprecated() {
result.hasAnnotation("deprecated")
or
result = deprecated().getQLDoc()
or
result = deprecated().getAnAnnotation()
or
result = deprecated().getAChild()
}
// our type-resolution skips these, so ignore.
private AstNode classUnion() {
exists(result.(Class).getUnionMember())
or
exists(result.(Class).getAliasType())
or
result = classUnion().(Class).getUnionMember()
or
result = classUnion().(Class).getAliasType()
or
result = classUnion().getAnAnnotation()
or
result = classUnion().getQLDoc()
or
result = classUnion().(TypeExpr).getAChild()
or
result = classUnion().(ModuleExpr).getAChild()
}
private AstNode benign() {
not result.getLocation().getFile().getExtension() = ["ql", "qll"] or // ignore dbscheme files
result instanceof BlockComment or
not exists(result.toString()) or // <- invalid code
// cached-stages pattern
result.(Module).getAMember().(ClasslessPredicate).getName() = "forceStage" or
result.(ClasslessPredicate).getName() = "forceStage" or
result.getLocation().getFile().getBaseName() = "Caching.qll" or
// sometimes contains dead code - ignore
result.getLocation().getFile().getRelativePath().matches("%/tutorials/%") or
result = classUnion()
}
private predicate isDeadInternal(AstNode node) {
not node = alive() and
not node = deprecated()
}
predicate isDead(AstNode node) {
isDeadInternal(node) and
not isDeadInternal(node.getParent()) and
not node = benign()
}
/**
* Gets an AST node that affects a query.
*/
private AstNode queryable() {
//
// The base cases.
//
// everything that can be an output when running a query
result = queryPredicate()
or
// A module with an import that imports another file, the import can activate a file.
result.(Module).getAMember().(Import).getResolvedModule().getFile() !=
result.getLocation().getFile()
or
result instanceof TopLevel // toplevel is always alive.
or
// recurisve cases
result = aliveStep(queryable())
}
/**
* Gets an AstNode that does not affect any query result.
* Is interresting as an quick-eval target to investigate dead code.
* (It is intentional that this predicate is a result of this predicate).
*/
AstNode unQueryable(string msg) {
not result = queryable() and
not result = deprecated() and
not result = benign() and
not result.getParent() = any(AstNode node | not node = queryable()) and
msg = result.getLocation().getFile().getBaseName() and
result.getLocation().getFile().getAbsolutePath().matches("%/javascript/%")
}

View File

@@ -10,48 +10,7 @@
*/
import ql
import codeql_ql.ast.internal.Module
FileOrModule hasEdgesRelation(ClasslessPredicate pred) {
pred.getName() = "edges" and
pred.hasAnnotation("query") and
(
result.asModule().getAMember() = pred
or
any(TopLevel top | top.getLocation().getFile() = result.asFile()).getAMember() = pred
)
}
FileOrModule importsEdges(ClasslessPredicate pred) {
result = hasEdgesRelation(pred)
or
exists(Import i |
not (i.hasAnnotation("private") and i.getLocation().getFile().getExtension() = "qll") and
importsEdges(pred) = i.getResolvedModule()
|
i = result.asModule().getAMember()
or
i = any(TopLevel top | top.getLocation().getFile() = result.asFile()).getAMember()
)
}
class Query extends File {
Query() { this.getExtension() = "ql" }
predicate isPathProblem() {
exists(QLDoc doc | doc.getLocation().getFile() = this |
doc.getContents().matches("%@kind path-problem%")
)
}
predicate isProblem() {
exists(QLDoc doc | doc.getLocation().getFile() = this |
doc.getContents().matches("%@kind problem%")
)
}
predicate hasEdgesRelation(ClasslessPredicate pred) { importsEdges(pred).asFile() = this }
}
import codeql_ql.bugs.PathProblemQueryQuery
from Query query, string msg, AstNode pred
where

View File

@@ -0,0 +1,15 @@
/**
* @name Dead code
* @description Code that cannot be reached should be deleted.
* @kind problem
* @problem.severity warning
* @id ql/dead-code
* @precision very-high
*/
import ql
import codeql_ql.style.DeadCodeQuery
from AstNode node
where isDead(node)
select node, "Code is dead"

View File

@@ -143,10 +143,6 @@ module DataFlow {
override string toString() { result = p.toString() }
}
newtype TReturnKind =
TNormalReturnKind() or
TParameterOutKind(int i) { any(Parameter p).getIndex() = i }
/** A data flow node that represents the output of a call at the call site. */
abstract class OutNode extends Node {
/** Gets the underlying call. */

View File

@@ -0,0 +1,2 @@
| Foo.qll:2:11:2:38 | ClasslessPredicate dead1 | Code is dead |
| Foo.qll:6:3:6:30 | ClasslessPredicate dead2 | Code is dead |

View File

@@ -0,0 +1 @@
queries/style/DeadCode.ql

View File

@@ -0,0 +1,9 @@
private module Mixed {
private predicate dead1() { none() }
predicate alive1() { none() }
predicate dead2() { none() }
}
predicate usesAlive() { Mixed::alive1() }

View File

@@ -287,20 +287,6 @@ private module SsaDefReaches {
)
}
/**
* Holds if the SSA definition of `v` at `def` reaches uncertain SSA definition
* `redef` in the same basic block, without crossing another SSA definition of `v`.
*/
predicate ssaDefReachesUncertainDefWithinBlock(
SourceVariable v, Definition def, UncertainWriteDefinition redef
) {
exists(BasicBlock bb, int rnk, int i |
ssaDefReachesRank(bb, def, rnk, v) and
rnk = ssaRefRank(bb, i, v, SsaDef()) - 1 and
redef.definesAt(v, bb, i)
)
}
/**
* Same as `ssaRefRank()`, but restricted to a particular SSA definition `def`.
*/

View File

@@ -189,12 +189,6 @@ module IO {
}
}
// "Direct" `IO` instances, i.e. cases where there is no more specific
// subtype such as `File`
private class IOInstanceStrict extends IOInstance {
IOInstanceStrict() { this = ioInstance() }
}
/**
* A `DataFlow::CallNode` that reads data using the `IO` class. For example,
* the `read` and `readline` calls in: