Merge branch 'main' into rust-ti-implementing-type-method

This commit is contained in:
Simon Friis Vindum
2025-05-12 11:35:48 +02:00
323 changed files with 30612 additions and 3092 deletions

View File

@@ -4,7 +4,9 @@ No user-facing changes.
## 0.4.7
No user-facing changes.
### New Features
* CodeQL and Copilot Autofix support for GitHub Actions is now Generally Available.
## 0.4.6

View File

@@ -1,3 +1,5 @@
## 0.4.7
No user-facing changes.
### New Features
* CodeQL and Copilot Autofix support for GitHub Actions is now Generally Available.

View File

@@ -20,6 +20,10 @@
## 0.5.4
### New Features
* CodeQL and Copilot Autofix support for GitHub Actions is now Generally Available.
### Bug Fixes
* Alerts produced by the query `actions/missing-workflow-permissions` now include a minimal set of recommended permissions in the alert message, based on well-known actions seen within the workflow file.

View File

@@ -1,5 +1,9 @@
## 0.5.4
### New Features
* CodeQL and Copilot Autofix support for GitHub Actions is now Generally Available.
### Bug Fixes
* Alerts produced by the query `actions/missing-workflow-permissions` now include a minimal set of recommended permissions in the alert message, based on well-known actions seen within the workflow file.

View File

@@ -1 +1,3 @@
[]
- queries: .
- apply: code-quality-selectors.yml
from: codeql/suite-helpers

View File

@@ -44,6 +44,10 @@ module CastToPointerArithFlowConfig implements DataFlow::StateConfigSig {
) and
getFullyConvertedType(node) = state
}
predicate isBarrierIn(DataFlow::Node node) { isSource(node, _) }
predicate isBarrierOut(DataFlow::Node node) { isSink(node, _) }
}
/**

View File

@@ -8,7 +8,7 @@
* @security-severity 7.8
* @precision high
* @tags security
* external/cwe/cwe-14
* external/cwe/cwe-014
*/
import cpp

View File

@@ -5,7 +5,7 @@
* to it.
* @id cpp/count-untrusted-data-external-api
* @kind table
* @tags security external/cwe/cwe-20
* @tags security external/cwe/cwe-020
*/
import cpp

View File

@@ -5,7 +5,7 @@
* to it.
* @id cpp/count-untrusted-data-external-api-ir
* @kind table
* @tags security external/cwe/cwe-20
* @tags security external/cwe/cwe-020
*/
import cpp

View File

@@ -6,7 +6,7 @@
* @precision low
* @problem.severity error
* @security-severity 7.8
* @tags security external/cwe/cwe-20
* @tags security external/cwe/cwe-020
*/
import cpp

View File

@@ -6,7 +6,7 @@
* @precision low
* @problem.severity error
* @security-severity 7.8
* @tags security external/cwe/cwe-20
* @tags security external/cwe/cwe-020
*/
import cpp

View File

@@ -0,0 +1,9 @@
---
category: queryMetadata
---
* The tag `external/cwe/cwe-14` has been removed from `cpp/memset-may-be-deleted` and the tag `external/cwe/cwe-014` has been added.
* The tag `external/cwe/cwe-20` has been removed from `cpp/count-untrusted-data-external-api` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-20` has been removed from `cpp/count-untrusted-data-external-api-ir` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-20` has been removed from `cpp/untrusted-data-to-external-api-ir` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-20` has been removed from `cpp/untrusted-data-to-external-api` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-20` has been removed from `cpp/late-check-of-function-argument` and the tag `external/cwe/cwe-020` has been added.

View File

@@ -1 +1,3 @@
[]
- queries: .
- apply: code-quality-selectors.yml
from: codeql/suite-helpers

View File

@@ -10,7 +10,7 @@
* @tags correctness
* security
* experimental
* external/cwe/cwe-20
* external/cwe/cwe-020
*/
import cpp

View File

@@ -7,6 +7,7 @@
*/
import internal.CaptureModels
import SummaryModels
from DataFlowSummaryTargetApi api, string flow
where flow = ContentSensitive::captureFlow(api, _)

View File

@@ -7,6 +7,7 @@
*/
import internal.CaptureModels
import SummaryModels
from DataFlowSummaryTargetApi api, string noflow
where noflow = captureNeutral(api)

View File

@@ -7,8 +7,8 @@
*/
import internal.CaptureModels
import Heuristic
import SinkModels
from DataFlowSinkTargetApi api, string sink
where sink = captureSink(api)
where sink = Heuristic::captureSink(api)
select sink order by sink

View File

@@ -7,8 +7,8 @@
*/
import internal.CaptureModels
import Heuristic
import SourceModels
from DataFlowSourceTargetApi api, string source
where source = captureSource(api)
where source = Heuristic::captureSource(api)
select source order by source

View File

@@ -7,6 +7,7 @@
*/
import internal.CaptureModels
import SummaryModels
from DataFlowSummaryTargetApi api, string flow
where flow = captureFlow(api, _)

View File

@@ -2,7 +2,7 @@
* Provides predicates related to capturing summary models of the Standard or a 3rd party library.
*/
private import cpp
private import cpp as Cpp
private import semmle.code.cpp.ir.IR
private import semmle.code.cpp.dataflow.ExternalFlow as ExternalFlow
private import semmle.code.cpp.ir.dataflow.internal.DataFlowImplCommon as DataFlowImplCommon
@@ -10,113 +10,67 @@ private import semmle.code.cpp.ir.dataflow.internal.DataFlowImplSpecific
private import semmle.code.cpp.ir.dataflow.internal.DataFlowPrivate as DataFlowPrivate
private import semmle.code.cpp.dataflow.internal.FlowSummaryImpl as FlowSummaryImpl
private import semmle.code.cpp.ir.dataflow.internal.TaintTrackingImplSpecific
private import semmle.code.cpp.dataflow.new.TaintTracking
private import semmle.code.cpp.dataflow.new.TaintTracking as Tt
private import semmle.code.cpp.dataflow.new.DataFlow as Df
private import codeql.mad.modelgenerator.internal.ModelGeneratorImpl
module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFlow> {
/**
* Holds if `f` is a "private" function.
*
* A "private" function does not contribute any models as it is assumed
* to be an implementation detail of some other "public" function for which
* we will generate a summary.
*/
private predicate isPrivateOrProtected(Cpp::Function f) {
f.getNamespace().getParentNamespace*().isAnonymous()
or
exists(Cpp::MemberFunction mf | mf = f |
mf.isPrivate()
or
mf.isProtected()
)
or
f.isStatic()
}
private predicate isUninterestingForModels(Callable api) {
// Note: This also makes all global/static-local variables
// not relevant (which is good!)
not api.(Cpp::Function).hasDefinition()
or
isPrivateOrProtected(api)
or
api instanceof Cpp::Destructor
or
api = any(Cpp::LambdaExpression lambda).getLambdaFunction()
or
api.isFromUninstantiatedTemplate(_)
}
private predicate relevant(Callable api) {
api.fromSource() and
not isUninterestingForModels(api)
}
module ModelGeneratorCommonInput implements ModelGeneratorCommonInputSig<Cpp::Location, CppDataFlow>
{
private module DataFlow = Df::DataFlow;
class Type = DataFlowPrivate::DataFlowType;
// Note: This also includes `this`
class Parameter = DataFlow::ParameterNode;
class Callable = Declaration;
class Callable = Cpp::Declaration;
class NodeExtended extends DataFlow::Node {
Callable getAsExprEnclosingCallable() { result = this.asExpr().getEnclosingDeclaration() }
}
Parameter asParameter(NodeExtended n) { result = n }
Callable getEnclosingCallable(NodeExtended n) {
result = n.getEnclosingCallable().asSourceCallable()
}
Callable getAsExprEnclosingCallable(NodeExtended n) {
result = n.asExpr().getEnclosingDeclaration()
}
/** Gets `api` if it is relevant. */
private Callable liftedImpl(Callable api) { result = api and relevant(api) }
private predicate hasManualSummaryModel(Callable api) {
api = any(FlowSummaryImpl::Public::SummarizedCallable sc | sc.applyManualModel()) or
api = any(FlowSummaryImpl::Public::NeutralSummaryCallable sc | sc.hasManualModel())
}
private predicate hasManualSourceModel(Callable api) {
api = any(FlowSummaryImpl::Public::NeutralSourceCallable sc | sc.hasManualModel())
}
private predicate hasManualSinkModel(Callable api) {
api = any(FlowSummaryImpl::Public::NeutralSinkCallable sc | sc.hasManualModel())
}
/**
* Holds if `f` is a "private" function.
*
* A "private" function does not contribute any models as it is assumed
* to be an implementation detail of some other "public" function for which
* we will generate a summary.
*/
private predicate isPrivateOrProtected(Function f) {
f.getNamespace().getParentNamespace*().isAnonymous()
or
exists(MemberFunction mf | mf = f |
mf.isPrivate()
or
mf.isProtected()
)
or
f.isStatic()
}
private predicate isUninterestingForModels(Callable api) {
// Note: This also makes all global/static-local variables
// not relevant (which is good!)
not api.(Function).hasDefinition()
or
isPrivateOrProtected(api)
or
api instanceof Destructor
or
api = any(LambdaExpression lambda).getLambdaFunction()
or
api.isFromUninstantiatedTemplate(_)
}
private predicate relevant(Callable api) {
api.fromSource() and
not isUninterestingForModels(api)
}
class SummaryTargetApi extends Callable {
private Callable lift;
SummaryTargetApi() {
lift = liftedImpl(this) and
not hasManualSummaryModel(lift)
}
Callable lift() { result = lift }
predicate isRelevant() {
relevant(this) and
not hasManualSummaryModel(this)
}
}
class SourceOrSinkTargetApi extends Callable {
SourceOrSinkTargetApi() { relevant(this) }
}
class SinkTargetApi extends SourceOrSinkTargetApi {
SinkTargetApi() { not hasManualSinkModel(this) }
}
class SourceTargetApi extends SourceOrSinkTargetApi {
SourceTargetApi() { not hasManualSourceModel(this) }
}
class InstanceParameterNode extends DataFlow::ParameterNode {
InstanceParameterNode() {
DataFlowPrivate::nodeHasInstruction(this,
@@ -124,7 +78,7 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFl
}
}
private predicate isFinalMemberFunction(MemberFunction mf) {
private predicate isFinalMemberFunction(Cpp::MemberFunction mf) {
mf.isFinal()
or
mf.getDeclaringType().isFinal()
@@ -146,12 +100,12 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFl
* - An uninstantiated template, or
* - A declaration that is not from a template instantiation.
*/
private string templateParams(Declaration template) {
private string templateParams(Cpp::Declaration template) {
exists(string params |
params =
concat(int i |
|
template.getTemplateArgument(i).(TypeTemplateParameter).getName(), "," order by i
template.getTemplateArgument(i).(Cpp::TypeTemplateParameter).getName(), "," order by i
)
|
if params = "" then result = "" else result = "<" + params + ">"
@@ -166,7 +120,7 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFl
* - An uninstantiated template, or
* - A declaration that is not from a template instantiation.
*/
private string params(Function functionTemplate) {
private string params(Cpp::Function functionTemplate) {
exists(string params |
params =
concat(int i |
@@ -193,7 +147,7 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFl
Callable callable, string namespace, string type, string name, string params
) {
exists(
Function functionTemplate, string typeWithoutTemplateArgs, string nameWithoutTemplateArgs
Cpp::Function functionTemplate, string typeWithoutTemplateArgs, string nameWithoutTemplateArgs
|
functionTemplate = ExternalFlow::getFullyTemplatedFunction(callable) and
functionTemplate.hasQualifiedName(namespace, typeWithoutTemplateArgs, nameWithoutTemplateArgs) and
@@ -201,7 +155,7 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFl
name = nameWithoutTemplateArgs + templateParams(functionTemplate) and
params = params(functionTemplate)
|
exists(Class classTemplate |
exists(Cpp::Class classTemplate |
classTemplate = functionTemplate.getDeclaringType() and
type = typeWithoutTemplateArgs + templateParams(classTemplate)
)
@@ -263,10 +217,10 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFl
/** Holds if this instance access is to an enclosing instance of type `t`. */
pragma[nomagic]
private predicate isEnclosingInstanceAccess(DataFlowPrivate::ReturnNode n, Class t) {
private predicate isEnclosingInstanceAccess(DataFlowPrivate::ReturnNode n, Cpp::Class t) {
n.getKind().isIndirectReturn(-1) and
t = n.getType().stripType() and
t != n.getEnclosingCallable().asSourceCallable().(Function).getDeclaringType()
t != n.getEnclosingCallable().asSourceCallable().(Cpp::Function).getDeclaringType()
}
pragma[nomagic]
@@ -275,26 +229,6 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFl
not isEnclosingInstanceAccess(node, _)
}
predicate sinkModelSanitizer(DataFlow::Node node) { none() }
predicate apiSource(DataFlow::Node source) {
DataFlowPrivate::nodeHasOperand(source, any(DataFlow::FieldAddress fa), 1)
or
source instanceof DataFlow::ParameterNode
}
string getInputArgument(DataFlow::Node source) {
exists(DataFlowPrivate::Position pos, int argumentIndex, int indirectionIndex |
source.(DataFlow::ParameterNode).isParameterOf(_, pos) and
argumentIndex = pos.getArgumentIndex() and
indirectionIndex = pos.getIndirectionIndex() and
result = "Argument[" + DataFlow::repeatStars(indirectionIndex) + argumentIndex + "]"
)
or
DataFlowPrivate::nodeHasOperand(source, any(DataFlow::FieldAddress fa), 1) and
result = qualifierString()
}
DataFlowPrivate::ParameterPosition getReturnKindParamPosition(DataFlowPrivate::ReturnKind k) {
exists(int argumentIndex, int indirectionIndex |
k.isIndirectReturn(argumentIndex) and
@@ -314,18 +248,71 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFl
)
}
predicate irrelevantSourceSinkApi(Callable source, SourceTargetApi api) { none() }
bindingset[kind]
predicate isRelevantSourceKind(string kind) { any() }
bindingset[kind]
predicate isRelevantSinkKind(string kind) { any() }
predicate containerContent(DataFlow::ContentSet cs) { cs instanceof DataFlow::ElementContent }
string partialModelRow(Callable api, int i) {
i = 0 and qualifiedName(api, result, _, _, _) // namespace
or
i = 1 and qualifiedName(api, _, result, _, _) // type
or
i = 2 and result = isExtensible(api) // extensible
or
i = 3 and qualifiedName(api, _, _, result, _) // name
or
i = 4 and qualifiedName(api, _, _, _, result) // parameters
or
i = 5 and result = "" and exists(api) // ext
}
string partialNeutralModelRow(Callable api, int i) {
i = 0 and qualifiedName(api, result, _, _, _) // namespace
or
i = 1 and qualifiedName(api, _, result, _, _) // type
or
i = 2 and qualifiedName(api, _, _, result, _) // name
or
i = 3 and qualifiedName(api, _, _, _, result) // parameters
}
}
private import ModelGeneratorCommonInput
private import MakeModelGeneratorFactory<Cpp::Location, CppDataFlow, CppTaintTracking, ModelGeneratorCommonInput>
private module SummaryModelGeneratorInput implements SummaryModelGeneratorInputSig {
private module DataFlow = Df::DataFlow;
Parameter asParameter(NodeExtended n) { result = n }
Callable getAsExprEnclosingCallable(NodeExtended n) {
result = n.asExpr().getEnclosingDeclaration()
}
private predicate hasManualSummaryModel(Callable api) {
api = any(FlowSummaryImpl::Public::SummarizedCallable sc | sc.applyManualModel()) or
api = any(FlowSummaryImpl::Public::NeutralSummaryCallable sc | sc.hasManualModel())
}
/** Gets `api` if it is relevant. */
private Callable liftedImpl(Callable api) { result = api and relevant(api) }
class SummaryTargetApi extends Callable {
private Callable lift;
SummaryTargetApi() {
lift = liftedImpl(this) and
not hasManualSummaryModel(lift)
}
Callable lift() { result = lift }
predicate isRelevant() {
relevant(this) and
not hasManualSummaryModel(this)
}
}
predicate isAdditionalContentFlowStep(DataFlow::Node node1, DataFlow::Node node2) {
TaintTracking::defaultAdditionalTaintStep(node1, node2, _) and
Tt::TaintTracking::defaultAdditionalTaintStep(node1, node2, _) and
not exists(DataFlow::Content f |
DataFlowPrivate::readStep(node1, f, node2) and containerContent(f)
)
@@ -341,7 +328,7 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFl
predicate isCallback(DataFlow::ContentSet c) { none() }
string getSyntheticName(DataFlow::ContentSet c) {
exists(Field f |
exists(Cpp::Field f |
not f.isPublic() and
f = c.(DataFlow::FieldContent).getField() and
result = f.getName()
@@ -373,40 +360,52 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFl
result = "Element[" + ec.getIndirectionIndex() + "]"
)
}
}
predicate isUninterestingForDataFlowModels(Callable api) { none() }
predicate isUninterestingForHeuristicDataFlowModels(Callable api) {
isUninterestingForDataFlowModels(api)
private module SourceModelGeneratorInput implements SourceModelGeneratorInputSig {
private predicate hasManualSourceModel(Callable api) {
api = any(FlowSummaryImpl::Public::NeutralSourceCallable sc | sc.hasManualModel())
}
string partialModelRow(Callable api, int i) {
i = 0 and qualifiedName(api, result, _, _, _) // namespace
or
i = 1 and qualifiedName(api, _, result, _, _) // type
or
i = 2 and result = isExtensible(api) // extensible
or
i = 3 and qualifiedName(api, _, _, result, _) // name
or
i = 4 and qualifiedName(api, _, _, _, result) // parameters
or
i = 5 and result = "" and exists(api) // ext
}
string partialNeutralModelRow(Callable api, int i) {
i = 0 and qualifiedName(api, result, _, _, _) // namespace
or
i = 1 and qualifiedName(api, _, result, _, _) // type
or
i = 2 and qualifiedName(api, _, _, result, _) // name
or
i = 3 and qualifiedName(api, _, _, _, result) // parameters
class SourceTargetApi extends Callable {
SourceTargetApi() { relevant(this) and not hasManualSourceModel(this) }
}
predicate sourceNode = ExternalFlow::sourceNode/2;
}
private module SinkModelGeneratorInput implements SinkModelGeneratorInputSig {
private module DataFlow = Df::DataFlow;
private predicate hasManualSinkModel(Callable api) {
api = any(FlowSummaryImpl::Public::NeutralSinkCallable sc | sc.hasManualModel())
}
class SinkTargetApi extends Callable {
SinkTargetApi() { relevant(this) and not hasManualSinkModel(this) }
}
predicate apiSource(DataFlow::Node source) {
DataFlowPrivate::nodeHasOperand(source, any(DataFlow::FieldAddress fa), 1)
or
source instanceof DataFlow::ParameterNode
}
string getInputArgument(DataFlow::Node source) {
exists(DataFlowPrivate::Position pos, int argumentIndex, int indirectionIndex |
source.(DataFlow::ParameterNode).isParameterOf(_, pos) and
argumentIndex = pos.getArgumentIndex() and
indirectionIndex = pos.getIndirectionIndex() and
result = "Argument[" + DataFlow::repeatStars(indirectionIndex) + argumentIndex + "]"
)
or
DataFlowPrivate::nodeHasOperand(source, any(DataFlow::FieldAddress fa), 1) and
result = qualifierString()
}
predicate sinkNode = ExternalFlow::sinkNode/2;
}
import MakeModelGenerator<Location, CppDataFlow, CppTaintTracking, ModelGeneratorInput>
import MakeSummaryModelGenerator<SummaryModelGeneratorInput> as SummaryModels
import MakeSourceModelGenerator<SourceModelGeneratorInput> as SourceModels
import MakeSinkModelGenerator<SinkModelGeneratorInput> as SinkModels

View File

@@ -1,6 +1,6 @@
private import cpp as Cpp
private import codeql.mad.modelgenerator.internal.ModelPrinting
private import CaptureModels::ModelGeneratorInput as ModelGeneratorInput
private import CaptureModels::ModelGeneratorCommonInput as ModelGeneratorInput
private module ModelPrintingLang implements ModelPrintingLangSig {
class Callable = Cpp::Declaration;

View File

@@ -1,5 +1,6 @@
import cpp
import utils.modelgenerator.internal.CaptureModels
import SummaryModels
import InlineModelsAsDataTest
module InlineMadTestConfig implements InlineMadTestConfigSig {

View File

@@ -1,5 +1,6 @@
import cpp
import utils.modelgenerator.internal.CaptureModels
import SummaryModels
import InlineModelsAsDataTest
module InlineMadTestConfig implements InlineMadTestConfigSig {

View File

@@ -3,22 +3,13 @@ edges
| test.cpp:30:34:30:34 | b | test.cpp:31:2:31:2 | b | provenance | |
| test.cpp:34:31:34:31 | b | test.cpp:35:2:35:2 | b | provenance | |
| test.cpp:57:19:57:19 | d | test.cpp:26:29:26:29 | b | provenance | |
| test.cpp:57:19:57:19 | d | test.cpp:58:25:58:25 | d | provenance | |
| test.cpp:57:19:57:19 | d | test.cpp:59:21:59:21 | d | provenance | |
| test.cpp:58:25:58:25 | d | test.cpp:30:34:30:34 | b | provenance | |
| test.cpp:58:25:58:25 | d | test.cpp:59:21:59:21 | d | provenance | |
| test.cpp:59:21:59:21 | d | test.cpp:34:31:34:31 | b | provenance | |
| test.cpp:74:19:74:21 | dss | test.cpp:26:29:26:29 | b | provenance | |
| test.cpp:74:19:74:21 | dss | test.cpp:75:25:75:27 | dss | provenance | |
| test.cpp:74:19:74:21 | dss | test.cpp:76:21:76:23 | dss | provenance | |
| test.cpp:75:25:75:27 | dss | test.cpp:30:34:30:34 | b | provenance | |
| test.cpp:75:25:75:27 | dss | test.cpp:76:21:76:23 | dss | provenance | |
| test.cpp:76:21:76:23 | dss | test.cpp:34:31:34:31 | b | provenance | |
| test.cpp:86:19:86:20 | d2 | test.cpp:26:29:26:29 | b | provenance | |
| test.cpp:86:19:86:20 | d2 | test.cpp:87:25:87:26 | d2 | provenance | |
| test.cpp:86:19:86:20 | d2 | test.cpp:88:21:88:22 | d2 | provenance | |
| test.cpp:87:25:87:26 | d2 | test.cpp:30:34:30:34 | b | provenance | |
| test.cpp:87:25:87:26 | d2 | test.cpp:88:21:88:22 | d2 | provenance | |
| test.cpp:88:21:88:22 | d2 | test.cpp:34:31:34:31 | b | provenance | |
nodes
| test.cpp:26:29:26:29 | b | semmle.label | b |
@@ -41,18 +32,9 @@ subpaths
| test.cpp:27:2:27:2 | b | test.cpp:57:19:57:19 | d | test.cpp:27:2:27:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:57:19:57:19 | d | this cast |
| test.cpp:27:2:27:2 | b | test.cpp:74:19:74:21 | dss | test.cpp:27:2:27:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:74:19:74:21 | dss | this cast |
| test.cpp:27:2:27:2 | b | test.cpp:86:19:86:20 | d2 | test.cpp:27:2:27:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:86:19:86:20 | d2 | this cast |
| test.cpp:31:2:31:2 | b | test.cpp:57:19:57:19 | d | test.cpp:31:2:31:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:57:19:57:19 | d | this cast |
| test.cpp:31:2:31:2 | b | test.cpp:58:25:58:25 | d | test.cpp:31:2:31:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:58:25:58:25 | d | this cast |
| test.cpp:31:2:31:2 | b | test.cpp:74:19:74:21 | dss | test.cpp:31:2:31:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:74:19:74:21 | dss | this cast |
| test.cpp:31:2:31:2 | b | test.cpp:75:25:75:27 | dss | test.cpp:31:2:31:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:75:25:75:27 | dss | this cast |
| test.cpp:31:2:31:2 | b | test.cpp:86:19:86:20 | d2 | test.cpp:31:2:31:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:86:19:86:20 | d2 | this cast |
| test.cpp:31:2:31:2 | b | test.cpp:87:25:87:26 | d2 | test.cpp:31:2:31:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:87:25:87:26 | d2 | this cast |
| test.cpp:35:2:35:2 | b | test.cpp:57:19:57:19 | d | test.cpp:35:2:35:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:57:19:57:19 | d | this cast |
| test.cpp:35:2:35:2 | b | test.cpp:58:25:58:25 | d | test.cpp:35:2:35:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:58:25:58:25 | d | this cast |
| test.cpp:35:2:35:2 | b | test.cpp:59:21:59:21 | d | test.cpp:35:2:35:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:59:21:59:21 | d | this cast |
| test.cpp:35:2:35:2 | b | test.cpp:74:19:74:21 | dss | test.cpp:35:2:35:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:74:19:74:21 | dss | this cast |
| test.cpp:35:2:35:2 | b | test.cpp:75:25:75:27 | dss | test.cpp:35:2:35:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:75:25:75:27 | dss | this cast |
| test.cpp:35:2:35:2 | b | test.cpp:76:21:76:23 | dss | test.cpp:35:2:35:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:76:21:76:23 | dss | this cast |
| test.cpp:35:2:35:2 | b | test.cpp:86:19:86:20 | d2 | test.cpp:35:2:35:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:86:19:86:20 | d2 | this cast |
| test.cpp:35:2:35:2 | b | test.cpp:87:25:87:26 | d2 | test.cpp:35:2:35:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:87:25:87:26 | d2 | this cast |
| test.cpp:35:2:35:2 | b | test.cpp:88:21:88:22 | d2 | test.cpp:35:2:35:2 | b | This pointer arithmetic may be done with the wrong type because of $@. | test.cpp:88:21:88:22 | d2 | this cast |

View File

@@ -8,6 +8,7 @@
* @id cs/invalid-string-formatting
* @tags reliability
* maintainability
* quality
*/
import csharp

View File

@@ -8,6 +8,7 @@
* @id cs/local-not-disposed
* @tags efficiency
* maintainability
* quality
* external/cwe/cwe-404
* external/cwe/cwe-459
* external/cwe/cwe-460

View File

@@ -9,6 +9,7 @@
* @id cs/constant-condition
* @tags maintainability
* readability
* quality
* external/cwe/cwe-835
*/

View File

@@ -7,7 +7,7 @@
* @precision medium
* @id cs/password-in-configuration
* @tags security
* external/cwe/cwe-13
* external/cwe/cwe-013
* external/cwe/cwe-256
* external/cwe/cwe-313
*/

View File

@@ -6,6 +6,7 @@
* @problem.severity warning
* @id cs/useless-assignment-to-local
* @tags maintainability
* quality
* external/cwe/cwe-563
* @precision very-high
*/

View File

@@ -9,6 +9,7 @@
* @tags reliability
* correctness
* logic
* quality
* external/cwe/cwe-193
*/

View File

@@ -8,6 +8,7 @@
* @tags reliability
* correctness
* logic
* quality
*/
import csharp

View File

@@ -9,6 +9,7 @@
* @tags reliability
* correctness
* logic
* quality
* external/cwe/cwe-480
* external/cwe/cwe-691
*/

View File

@@ -9,6 +9,7 @@
* @id cs/equality-on-floats
* @tags reliability
* correctness
* quality
*/
import csharp

View File

@@ -7,6 +7,7 @@
* @id cs/reference-equality-on-valuetypes
* @tags reliability
* correctness
* quality
* external/cwe/cwe-595
*/

View File

@@ -8,6 +8,7 @@
* @tags reliability
* correctness
* logic
* quality
*/
import csharp

View File

@@ -7,6 +7,7 @@
* @id cs/unchecked-cast-in-equals
* @tags reliability
* maintainability
* quality
*/
import csharp

View File

@@ -6,7 +6,9 @@
* @problem.severity recommendation
* @precision high
* @id cs/inefficient-containskey
* @tags maintainability efficiency
* @tags maintainability
* efficiency
* quality
*/
import csharp

View File

@@ -10,7 +10,7 @@
* @tags security
* maintainability
* frameworks/asp.net
* external/cwe/cwe-11
* external/cwe/cwe-011
* external/cwe/cwe-532
*/

View File

@@ -8,7 +8,7 @@
* @id cs/web/large-max-request-length
* @tags security
* frameworks/asp.net
* external/cwe/cwe-16
* external/cwe/cwe-016
*/
import csharp

View File

@@ -8,7 +8,7 @@
* @id cs/web/request-validation-disabled
* @tags security
* frameworks/asp.net
* external/cwe/cwe-16
* external/cwe/cwe-016
*/
import csharp

View File

@@ -5,7 +5,7 @@
* to it.
* @id cs/count-untrusted-data-external-api
* @kind table
* @tags security external/cwe/cwe-20
* @tags security external/cwe/cwe-020
*/
import csharp

View File

@@ -7,7 +7,7 @@
* @security-severity 7.8
* @precision medium
* @tags security
* external/cwe/cwe-20
* external/cwe/cwe-020
*/
import semmle.code.csharp.serialization.Serialization

View File

@@ -6,7 +6,7 @@
* @precision low
* @problem.severity error
* @security-severity 7.8
* @tags security external/cwe/cwe-20
* @tags security external/cwe/cwe-020
*/
import csharp

View File

@@ -8,7 +8,7 @@
* @precision high
* @id cs/web/missing-global-error-handler
* @tags security
* external/cwe/cwe-12
* external/cwe/cwe-012
* external/cwe/cwe-248
*/

View File

@@ -8,6 +8,7 @@
* @id cs/call-to-object-tostring
* @tags reliability
* maintainability
* quality
*/
import DefaultToStringQuery

View File

@@ -8,6 +8,7 @@
* @id cs/useless-gethashcode-call
* @tags readability
* useless-code
* quality
*/
import csharp

View File

@@ -0,0 +1,12 @@
---
category: queryMetadata
---
* The tag `external/cwe/cwe-13` has been removed from `cs/password-in-configuration` and the tag `external/cwe/cwe-013` has been added.
* The tag `external/cwe/cwe-11` has been removed from `cs/web/debug-binary` and the tag `external/cwe/cwe-011` has been added.
* The tag `external/cwe/cwe-16` has been removed from `cs/web/large-max-request-length` and the tag `external/cwe/cwe-016` has been added.
* The tag `external/cwe/cwe-16` has been removed from `cs/web/request-validation-disabled` and the tag `external/cwe/cwe-016` has been added.
* The tag `external/cwe/cwe-20` has been removed from `cs/count-untrusted-data-external-api` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-20` has been removed from `cs/serialization-check-bypass` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-20` has been removed from `cs/untrusted-data-to-external-api` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-12` has been removed from `cs/web/missing-global-error-handler` and the tag `external/cwe/cwe-012` has been added.

View File

@@ -1,17 +1,3 @@
- queries: .
- include:
id:
- cs/index-out-of-bounds
- cs/test-for-negative-container-size
- cs/unchecked-cast-in-equals
- cs/reference-equality-on-valuetypes
- cs/self-assignment
- cs/inefficient-containskey
- cs/call-to-object-tostring
- cs/local-not-disposed
- cs/constant-condition
- cs/useless-gethashcode-call
- cs/non-short-circuit
- cs/useless-assignment-to-local
- cs/invalid-string-formatting
- cs/equality-on-floats
- apply: code-quality-selectors.yml
from: codeql/suite-helpers

View File

@@ -7,6 +7,7 @@
*/
import internal.CaptureModels
import SummaryModels
from DataFlowSummaryTargetApi api, string flow
where flow = ContentSensitive::captureFlow(api, _)

View File

@@ -7,6 +7,7 @@
*/
import internal.CaptureModels
import SummaryModels
from DataFlowSummaryTargetApi api, string noflow
where noflow = captureNeutral(api)

View File

@@ -7,6 +7,7 @@
*/
import internal.CaptureModels
import SinkModels
from DataFlowSinkTargetApi api, string sink
where sink = Heuristic::captureSink(api)

View File

@@ -7,6 +7,7 @@
*/
import internal.CaptureModels
import SourceModels
from DataFlowSourceTargetApi api, string source
where source = Heuristic::captureSource(api)

View File

@@ -7,6 +7,7 @@
*/
import internal.CaptureModels
import SummaryModels
from DataFlowSummaryTargetApi api, string flow
where flow = captureFlow(api, _)

View File

@@ -10,6 +10,7 @@
import csharp
import utils.modelgenerator.internal.CaptureModels
import SummaryModels
import PartialFlow::PartialPathGraph
int explorationLimit() { result = 3 }

View File

@@ -10,6 +10,7 @@
import csharp
import utils.modelgenerator.internal.CaptureModels
import SummaryModels
import Heuristic
import PropagateFlow::PathGraph

View File

@@ -15,7 +15,41 @@ private import semmle.code.csharp.frameworks.System
private import semmle.code.csharp.Location
private import codeql.mad.modelgenerator.internal.ModelGeneratorImpl
module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CsharpDataFlow> {
private predicate irrelevantAccessor(CS::Accessor a) {
a.getDeclaration().(CS::Property).isReadWrite()
}
private predicate isUninterestingForModels(Callable api) {
api.getDeclaringType().getNamespace().getFullName() = ""
or
api instanceof CS::ConversionOperator
or
api instanceof Util::MainMethod
or
api instanceof CS::Destructor
or
api instanceof CS::AnonymousFunctionExpr
or
api.(CS::Constructor).isParameterless()
or
exists(Type decl | decl = api.getDeclaringType() |
decl instanceof SystemObjectClass or
decl instanceof SystemValueTypeClass
)
or
// Disregard properties that have both a get and a set accessor,
// which implicitly means auto implemented properties.
irrelevantAccessor(api)
}
private predicate relevant(Callable api) {
[api.(CS::Modifiable), api.(CS::Accessor).getDeclaration()].isEffectivelyPublic() and
api.fromSource() and
api.isUnboundDeclaration() and
not isUninterestingForModels(api)
}
module ModelGeneratorCommonInput implements ModelGeneratorCommonInputSig<Location, CsharpDataFlow> {
class Type = CS::Type;
class Parameter = CS::Parameter;
@@ -24,127 +58,8 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CsharpDat
class NodeExtended = CS::DataFlow::Node;
Callable getAsExprEnclosingCallable(NodeExtended node) {
result = node.asExpr().getEnclosingCallable()
}
Callable getEnclosingCallable(NodeExtended node) { result = node.getEnclosingCallable() }
Parameter asParameter(NodeExtended node) { result = node.asParameter() }
/**
* Holds if any of the parameters of `api` are `System.Func<>`.
*/
private predicate isHigherOrder(Callable api) {
exists(Type t | t = api.getAParameter().getType().getUnboundDeclaration() |
t instanceof SystemLinqExpressions::DelegateExtType
)
}
private predicate irrelevantAccessor(CS::Accessor a) {
a.getDeclaration().(CS::Property).isReadWrite()
}
private predicate isUninterestingForModels(Callable api) {
api.getDeclaringType().getNamespace().getFullName() = ""
or
api instanceof CS::ConversionOperator
or
api instanceof Util::MainMethod
or
api instanceof CS::Destructor
or
api instanceof CS::AnonymousFunctionExpr
or
api.(CS::Constructor).isParameterless()
or
exists(Type decl | decl = api.getDeclaringType() |
decl instanceof SystemObjectClass or
decl instanceof SystemValueTypeClass
)
or
// Disregard properties that have both a get and a set accessor,
// which implicitly means auto implemented properties.
irrelevantAccessor(api)
}
private predicate relevant(Callable api) {
[api.(CS::Modifiable), api.(CS::Accessor).getDeclaration()].isEffectivelyPublic() and
api.fromSource() and
api.isUnboundDeclaration() and
not isUninterestingForModels(api)
}
private Callable getARelevantOverrideeOrImplementee(Overridable m) {
m.overridesOrImplements(result) and relevant(result)
}
/**
* Gets the super implementation of `api` if it is relevant.
* If such a super implementation does not exist, returns `api` if it is relevant.
*/
private Callable liftedImpl(Callable api) {
(
result = getARelevantOverrideeOrImplementee(api)
or
result = api and relevant(api)
) and
not exists(getARelevantOverrideeOrImplementee(result))
}
private predicate hasManualSummaryModel(Callable api) {
api = any(FlowSummaryImpl::Public::SummarizedCallable sc | sc.applyManualModel()) or
api = any(FlowSummaryImpl::Public::NeutralSummaryCallable sc | sc.hasManualModel())
}
private predicate hasManualSourceModel(Callable api) {
api = any(ExternalFlow::SourceCallable sc | sc.hasManualModel()) or
api = any(FlowSummaryImpl::Public::NeutralSourceCallable sc | sc.hasManualModel())
}
private predicate hasManualSinkModel(Callable api) {
api = any(ExternalFlow::SinkCallable sc | sc.hasManualModel()) or
api = any(FlowSummaryImpl::Public::NeutralSinkCallable sc | sc.hasManualModel())
}
predicate isUninterestingForDataFlowModels(Callable api) { none() }
predicate isUninterestingForHeuristicDataFlowModels(Callable api) { isHigherOrder(api) }
class SourceOrSinkTargetApi extends Callable {
SourceOrSinkTargetApi() { relevant(this) }
}
class SinkTargetApi extends SourceOrSinkTargetApi {
SinkTargetApi() { not hasManualSinkModel(this) }
}
class SourceTargetApi extends SourceOrSinkTargetApi {
SourceTargetApi() {
not hasManualSourceModel(this) and
// Do not generate source models for overridable callables
// as virtual dispatch implies that too many methods
// will be considered sources.
not this.(Overridable).overridesOrImplements(_)
}
}
class SummaryTargetApi extends Callable {
private Callable lift;
SummaryTargetApi() {
lift = liftedImpl(this) and
not hasManualSummaryModel(lift)
}
Callable lift() { result = lift }
predicate isRelevant() {
relevant(this) and
not hasManualSummaryModel(this)
}
}
/**
* Holds if `t` is a type that is generally used for bulk data in collection types.
* Eg. char[] is roughly equivalent to string and thus a highly
@@ -205,6 +120,8 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CsharpDat
)
}
class InstanceParameterNode = DataFlowPrivate::InstanceParameterNode;
string qualifierString() { result = "Argument[this]" }
string parameterAccess(CS::Parameter p) {
@@ -215,8 +132,6 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CsharpDat
string parameterContentAccess(CS::Parameter p) { result = "Argument[" + p.getPosition() + "]" }
class InstanceParameterNode = DataFlowPrivate::InstanceParameterNode;
private signature string parameterAccessSig(Parameter p);
private module ParamReturnNodeAsOutput<parameterAccessSig/1 getParamAccess> {
@@ -251,63 +166,92 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CsharpDat
node.asExpr() instanceof CS::ThisAccess
}
private predicate isRelevantMemberAccess(DataFlow::Node node) {
exists(CS::MemberAccess access | access = node.asExpr() |
access.hasThisQualifier() and
access.getTarget().isEffectivelyPublic() and
(
access instanceof CS::FieldAccess
or
access.getTarget().(CS::Property).getSetter().isPublic()
)
)
}
predicate sinkModelSanitizer(DataFlow::Node node) { none() }
predicate apiSource(DataFlow::Node source) {
isRelevantMemberAccess(source) or source instanceof DataFlow::ParameterNode
}
private predicate uniquelyCalls(DataFlowCallable dc1, DataFlowCallable dc2) {
exists(DataFlowCall call |
dc1 = call.getEnclosingCallable() and
dc2 = unique(DataFlowCallable dc0 | dc0 = viableCallable(call) | dc0)
)
}
bindingset[dc1, dc2]
private predicate uniquelyCallsPlus(DataFlowCallable dc1, DataFlowCallable dc2) =
fastTC(uniquelyCalls/2)(dc1, dc2)
bindingset[sourceEnclosing, api]
predicate irrelevantSourceSinkApi(Callable sourceEnclosing, SourceTargetApi api) {
not exists(DataFlowCallable dc1, DataFlowCallable dc2 |
uniquelyCallsPlus(dc1, dc2) or dc1 = dc2
|
dc1.getUnderlyingCallable() = api and
dc2.getUnderlyingCallable() = sourceEnclosing
)
}
string getInputArgument(DataFlow::Node source) {
exists(int pos |
pos = source.(DataFlow::ParameterNode).getParameter().getPosition() and
result = "Argument[" + pos + "]"
)
or
source.asExpr() instanceof DataFlowPrivate::FieldOrPropertyAccess and
result = qualifierString()
}
bindingset[kind]
predicate isRelevantSinkKind(string kind) { any() }
bindingset[kind]
predicate isRelevantSourceKind(string kind) { any() }
predicate containerContent(DataFlow::ContentSet c) { c.isElement() }
string partialModelRow(Callable api, int i) {
i = 0 and ExternalFlow::partialModel(api, result, _, _, _, _) // package
or
i = 1 and ExternalFlow::partialModel(api, _, result, _, _, _) // type
or
i = 2 and ExternalFlow::partialModel(api, _, _, result, _, _) // extensible
or
i = 3 and ExternalFlow::partialModel(api, _, _, _, result, _) // name
or
i = 4 and ExternalFlow::partialModel(api, _, _, _, _, result) // parameters
or
i = 5 and result = "" and exists(api) // ext
}
string partialNeutralModelRow(Callable api, int i) {
i = 0 and result = partialModelRow(api, 0) // package
or
i = 1 and result = partialModelRow(api, 1) // type
or
i = 2 and result = partialModelRow(api, 3) // name
or
i = 3 and result = partialModelRow(api, 4) // parameters
}
}
private import ModelGeneratorCommonInput
private import MakeModelGeneratorFactory<Location, CsharpDataFlow, CsharpTaintTracking, ModelGeneratorCommonInput>
module SummaryModelGeneratorInput implements SummaryModelGeneratorInputSig {
Callable getAsExprEnclosingCallable(NodeExtended node) {
result = node.asExpr().getEnclosingCallable()
}
Parameter asParameter(NodeExtended node) { result = node.asParameter() }
/**
* Holds if any of the parameters of `api` are `System.Func<>`.
*/
private predicate isHigherOrder(Callable api) {
exists(Type t | t = api.getAParameter().getType().getUnboundDeclaration() |
t instanceof SystemLinqExpressions::DelegateExtType
)
}
private Callable getARelevantOverrideeOrImplementee(Overridable m) {
m.overridesOrImplements(result) and relevant(result)
}
/**
* Gets the super implementation of `api` if it is relevant.
* If such a super implementation does not exist, returns `api` if it is relevant.
*/
private Callable liftedImpl(Callable api) {
(
result = getARelevantOverrideeOrImplementee(api)
or
result = api and relevant(api)
) and
not exists(getARelevantOverrideeOrImplementee(result))
}
private predicate hasManualSummaryModel(Callable api) {
api = any(FlowSummaryImpl::Public::SummarizedCallable sc | sc.applyManualModel()) or
api = any(FlowSummaryImpl::Public::NeutralSummaryCallable sc | sc.hasManualModel())
}
predicate isUninterestingForHeuristicDataFlowModels(Callable api) { isHigherOrder(api) }
class SummaryTargetApi extends Callable {
private Callable lift;
SummaryTargetApi() {
lift = liftedImpl(this) and
not hasManualSummaryModel(lift)
}
Callable lift() { result = lift }
predicate isRelevant() {
relevant(this) and
not hasManualSummaryModel(this)
}
}
predicate isAdditionalContentFlowStep(DataFlow::Node nodeFrom, DataFlow::Node nodeTo) {
TaintTrackingPrivate::defaultAdditionalTaintStep(nodeFrom, nodeTo, _) and
not nodeTo.asExpr() instanceof CS::ElementAccess and
@@ -370,34 +314,88 @@ module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CsharpDat
or
c.isDelegateCallReturn() and result = "ReturnValue"
}
}
string partialModelRow(Callable api, int i) {
i = 0 and ExternalFlow::partialModel(api, result, _, _, _, _) // package
or
i = 1 and ExternalFlow::partialModel(api, _, result, _, _, _) // type
or
i = 2 and ExternalFlow::partialModel(api, _, _, result, _, _) // extensible
or
i = 3 and ExternalFlow::partialModel(api, _, _, _, result, _) // name
or
i = 4 and ExternalFlow::partialModel(api, _, _, _, _, result) // parameters
or
i = 5 and result = "" and exists(api) // ext
private module SourceModelGeneratorInput implements SourceModelGeneratorInputSig {
private predicate hasManualSourceModel(Callable api) {
api = any(ExternalFlow::SourceCallable sc | sc.hasManualModel()) or
api = any(FlowSummaryImpl::Public::NeutralSourceCallable sc | sc.hasManualModel())
}
string partialNeutralModelRow(Callable api, int i) {
i = 0 and result = partialModelRow(api, 0) // package
or
i = 1 and result = partialModelRow(api, 1) // type
or
i = 2 and result = partialModelRow(api, 3) // name
or
i = 3 and result = partialModelRow(api, 4) // parameters
class SourceTargetApi extends Callable {
SourceTargetApi() {
relevant(this) and
not hasManualSourceModel(this) and
// Do not generate source models for overridable callables
// as virtual dispatch implies that too many methods
// will be considered sources.
not this.(Overridable).overridesOrImplements(_)
}
}
private predicate uniquelyCalls(DataFlowCallable dc1, DataFlowCallable dc2) {
exists(DataFlowCall call |
dc1 = call.getEnclosingCallable() and
dc2 = unique(DataFlowCallable dc0 | dc0 = viableCallable(call) | dc0)
)
}
bindingset[dc1, dc2]
private predicate uniquelyCallsPlus(DataFlowCallable dc1, DataFlowCallable dc2) =
fastTC(uniquelyCalls/2)(dc1, dc2)
bindingset[sourceEnclosing, api]
predicate irrelevantSourceSinkApi(Callable sourceEnclosing, SourceTargetApi api) {
not exists(DataFlowCallable dc1, DataFlowCallable dc2 |
uniquelyCallsPlus(dc1, dc2) or dc1 = dc2
|
dc1.getUnderlyingCallable() = api and
dc2.getUnderlyingCallable() = sourceEnclosing
)
}
predicate sourceNode = ExternalFlow::sourceNode/2;
}
private module SinkModelGeneratorInput implements SinkModelGeneratorInputSig {
private predicate hasManualSinkModel(Callable api) {
api = any(ExternalFlow::SinkCallable sc | sc.hasManualModel()) or
api = any(FlowSummaryImpl::Public::NeutralSinkCallable sc | sc.hasManualModel())
}
class SinkTargetApi extends Callable {
SinkTargetApi() { relevant(this) and not hasManualSinkModel(this) }
}
private predicate isRelevantMemberAccess(DataFlow::Node node) {
exists(CS::MemberAccess access | access = node.asExpr() |
access.hasThisQualifier() and
access.getTarget().isEffectivelyPublic() and
(
access instanceof CS::FieldAccess
or
access.getTarget().(CS::Property).getSetter().isPublic()
)
)
}
predicate apiSource(DataFlow::Node source) {
isRelevantMemberAccess(source) or source instanceof DataFlow::ParameterNode
}
string getInputArgument(DataFlow::Node source) {
exists(int pos |
pos = source.(DataFlow::ParameterNode).getParameter().getPosition() and
result = "Argument[" + pos + "]"
)
or
source.asExpr() instanceof DataFlowPrivate::FieldOrPropertyAccess and
result = qualifierString()
}
predicate sinkNode = ExternalFlow::sinkNode/2;
}
import MakeModelGenerator<Location, CsharpDataFlow, CsharpTaintTracking, ModelGeneratorInput>
import MakeSummaryModelGenerator<SummaryModelGeneratorInput> as SummaryModels
import MakeSourceModelGenerator<SourceModelGeneratorInput> as SourceModels
import MakeSinkModelGenerator<SinkModelGeneratorInput> as SinkModels

View File

@@ -1,6 +1,6 @@
private import csharp as CS
private import codeql.mad.modelgenerator.internal.ModelPrinting
private import CaptureModels::ModelGeneratorInput as ModelGeneratorInput
private import CaptureModels::ModelGeneratorCommonInput as ModelGeneratorInput
private module ModelPrintingLang implements ModelPrintingLangSig {
class Callable = CS::Callable;

View File

@@ -2,7 +2,8 @@ private import csharp
private import semmle.code.csharp.frameworks.system.collections.Generic as GenericCollections
private import semmle.code.csharp.dataflow.internal.DataFlowPrivate
private import semmle.code.csharp.frameworks.system.linq.Expressions
private import CaptureModels::ModelGeneratorInput as ModelGeneratorInput
private import CaptureModels::ModelGeneratorCommonInput as ModelGeneratorInput
private import CaptureModels::SummaryModelGeneratorInput as SummaryModelGeneratorInput
private import CaptureModelsPrinting
/**
@@ -177,21 +178,19 @@ private predicate output(Callable callable, TypeParameter tp, string output) {
delegateSink(callable, tp, output)
}
private module ModelPrintingInput implements ModelPrintingSig {
private module ModelPrintingInput implements ModelPrintingSummarySig {
class SummaryApi = TypeBasedFlowTargetApi;
class SourceOrSinkApi = TypeBasedFlowTargetApi;
string getProvenance() { result = "tb-generated" }
}
private module Printing = ModelPrinting<ModelPrintingInput>;
private module Printing = ModelPrintingSummary<ModelPrintingInput>;
/**
* A class of callables that are relevant generating summaries for based
* on the Theorems for Free approach.
*/
class TypeBasedFlowTargetApi extends ModelGeneratorInput::SummaryTargetApi {
class TypeBasedFlowTargetApi extends SummaryModelGeneratorInput::SummaryTargetApi {
/**
* Gets the string representation of all type based summaries for `this`
* inspired by the Theorems for Free approach.

View File

@@ -1,5 +1,6 @@
import csharp
import utils.modelgenerator.internal.CaptureModels
import SummaryModels
import utils.test.InlineMadTest
module InlineMadTestConfig implements InlineMadTestConfigSig {

View File

@@ -1,5 +1,6 @@
import csharp
import utils.modelgenerator.internal.CaptureModels
import SummaryModels
import utils.test.InlineMadTest
module InlineMadTestConfig implements InlineMadTestConfigSig {

View File

@@ -1,5 +1,6 @@
import csharp
import utils.modelgenerator.internal.CaptureModels
import SummaryModels
import utils.test.InlineMadTest
module InlineMadTestConfig implements InlineMadTestConfigSig {

View File

@@ -1,5 +1,6 @@
import csharp
import utils.modelgenerator.internal.CaptureModels
import SinkModels
import utils.test.InlineMadTest
module InlineMadTestConfig implements InlineMadTestConfigSig {

View File

@@ -1,5 +1,6 @@
import csharp
import utils.modelgenerator.internal.CaptureModels
import SourceModels
import utils.test.InlineMadTest
module InlineMadTestConfig implements InlineMadTestConfigSig {

View File

@@ -37,6 +37,14 @@ Bug Fixes
Query Packs
-----------
New Features
~~~~~~~~~~~~
GitHub Actions
""""""""""""""
* CodeQL and Copilot Autofix support for GitHub Actions is now Generally Available.
Bug Fixes
~~~~~~~~~
@@ -123,6 +131,11 @@ Ruby
New Features
~~~~~~~~~~~~
GitHub Actions
""""""""""""""
* CodeQL and Copilot Autofix support for GitHub Actions is now Generally Available.
C/C++
"""""

View File

@@ -254,6 +254,7 @@ and the CodeQL library pack ``codeql/python-all`` (`changelog <https://github.co
cassandra-driver, Database
clickhouse-driver, Database
cx_Oracle, Database
hdbcli, Database
mysql-connector, Database
mysql-connector-python, Database
MySQL-python, Database

View File

@@ -1582,18 +1582,10 @@ func isAlias(tp types.Type) bool {
return ok
}
// If the given type is a type alias, this function resolves it to its underlying type.
func resolveTypeAlias(tp types.Type) types.Type {
if isAlias(tp) {
return types.Unalias(tp) // tp.Underlying()
}
return tp
}
// extractType extracts type information for `tp` and returns its associated label;
// types are only extracted once, so the second time `extractType` is invoked it simply returns the label
func extractType(tw *trap.Writer, tp types.Type) trap.Label {
tp = resolveTypeAlias(tp)
tp = types.Unalias(tp)
lbl, exists := getTypeLabel(tw, tp)
if !exists {
var kind int
@@ -1771,7 +1763,7 @@ func extractType(tw *trap.Writer, tp types.Type) trap.Label {
// is constructed from their globally unique ID. This prevents cyclic type keys
// since type recursion in Go always goes through defined types.
func getTypeLabel(tw *trap.Writer, tp types.Type) (trap.Label, bool) {
tp = resolveTypeAlias(tp)
tp = types.Unalias(tp)
lbl, exists := tw.Labeler.TypeLabels[tp]
if !exists {
switch tp := tp.(type) {

View File

@@ -10,7 +10,7 @@ toolchain go1.24.0
// bazel mod tidy
require (
golang.org/x/mod v0.24.0
golang.org/x/tools v0.32.0
golang.org/x/tools v0.33.0
)
require golang.org/x/sync v0.13.0 // indirect
require golang.org/x/sync v0.14.0 // indirect

View File

@@ -2,7 +2,7 @@ github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI=
github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
golang.org/x/mod v0.24.0 h1:ZfthKaKaT4NrhGVZHO1/WDTwGES4De8KtWO0SIbNJMU=
golang.org/x/mod v0.24.0/go.mod h1:IXM97Txy2VM4PJ3gI61r1YEk/gAj6zAHN3AdZt6S9Ww=
golang.org/x/sync v0.13.0 h1:AauUjRAJ9OSnvULf/ARrrVywoJDy0YS2AwQ98I37610=
golang.org/x/sync v0.13.0/go.mod h1:1dzgHSNfp02xaA81J2MS99Qcpr2w7fw1gpm99rleRqA=
golang.org/x/tools v0.32.0 h1:Q7N1vhpkQv7ybVzLFtTjvQya2ewbwNDZzUgfXGqtMWU=
golang.org/x/tools v0.32.0/go.mod h1:ZxrU41P/wAbZD8EDa6dDCa6XfpkhJ7HFMjHJXfBDu8s=
golang.org/x/sync v0.14.0 h1:woo0S4Yywslg6hp4eUFjTVOyKt0RookbpAHG4c1HmhQ=
golang.org/x/sync v0.14.0/go.mod h1:1dzgHSNfp02xaA81J2MS99Qcpr2w7fw1gpm99rleRqA=
golang.org/x/tools v0.33.0 h1:4qz2S3zmRxbGIhDIAgjxvFutSvH5EfnsYrRBj0UI0bc=
golang.org/x/tools v0.33.0/go.mod h1:CIJMaWEY88juyUfo7UbgPqbC8rU2OqfAV1h2Qp0oMYI=

View File

@@ -169,11 +169,12 @@ func (l *Labeler) ScopedObjectID(object types.Object, getTypeLabel func() Label)
// findMethodWithGivenReceiver finds a method with `object` as its receiver, if one exists
func findMethodWithGivenReceiver(object types.Object) *types.Func {
meth := findMethodOnTypeWithGivenReceiver(object.Type(), object)
unaliasedType := types.Unalias(object.Type())
meth := findMethodOnTypeWithGivenReceiver(unaliasedType, object)
if meth != nil {
return meth
}
if pointerType, ok := object.Type().(*types.Pointer); ok {
if pointerType, ok := unaliasedType.(*types.Pointer); ok {
meth = findMethodOnTypeWithGivenReceiver(pointerType.Elem(), object)
}
return meth

View File

@@ -8,6 +8,7 @@
* @tags reliability
* correctness
* logic
* quality
* external/cwe/cwe-193
* @precision high
*/

View File

@@ -8,6 +8,7 @@
* @tags reliability
* correctness
* logic
* quality
* @precision high
*/

View File

@@ -11,6 +11,7 @@
* correctness
* call
* defer
* quality
*/
import go

View File

@@ -7,6 +7,7 @@
* @tags reliability
* correctness
* logic
* quality
* @precision high
*/

View File

@@ -9,6 +9,7 @@
* @precision very-high
* @id go/negative-length-check
* @tags correctness
* quality
*/
import go

View File

@@ -8,6 +8,7 @@
* @id go/redundant-recover
* @tags maintainability
* correctness
* quality
* @precision high
*/

View File

@@ -5,7 +5,7 @@
* to it.
* @id go/count-untrusted-data-external-api
* @kind table
* @tags security external/cwe/cwe-20
* @tags security external/cwe/cwe-020
*/
import go

View File

@@ -9,7 +9,7 @@
* @id go/incomplete-hostname-regexp
* @tags correctness
* security
* external/cwe/cwe-20
* external/cwe/cwe-020
*/
import go

View File

@@ -8,7 +8,7 @@
* @id go/regex/missing-regexp-anchor
* @tags correctness
* security
* external/cwe/cwe-20
* external/cwe/cwe-020
*/
import go

View File

@@ -8,7 +8,7 @@
* @id go/suspicious-character-in-regex
* @tags correctness
* security
* external/cwe/cwe-20
* external/cwe/cwe-020
*/
import go

View File

@@ -6,7 +6,7 @@
* @precision low
* @problem.severity error
* @security-severity 7.8
* @tags security external/cwe/cwe-20
* @tags security external/cwe/cwe-020
*/
import go

View File

@@ -6,7 +6,7 @@
* @precision low
* @problem.severity error
* @security-severity 7.8
* @tags security external/cwe/cwe-20
* @tags security external/cwe/cwe-020
*/
import go

View File

@@ -0,0 +1,14 @@
---
category: queryMetadata
---
* The tag `external/cwe/cwe-20` has been removed from `go/count-untrusted-data-external-api` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-20` has been removed from `go/incomplete-hostname-regexp` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-20` has been removed from `go/regex/missing-regexp-anchor` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-20` has been removed from `go/suspicious-character-in-regex` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-20` has been removed from `go/untrusted-data-to-external-api` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-20` has been removed from `go/untrusted-data-to-unknown-external-api` and the tag `external/cwe/cwe-020` has been added.
* The tag `external/cwe/cwe-90` has been removed from `go/ldap-injection` and the tag `external/cwe/cwe-090` has been added.
* The tag `external/cwe/cwe-74` has been removed from `go/dsn-injection` and the tag `external/cwe/cwe-074` has been added.
* The tag `external/cwe/cwe-74` has been removed from `go/dsn-injection-local` and the tag `external/cwe/cwe-074` has been added.
* The tag `external/cwe/cwe-79` has been removed from `go/html-template-escaping-passthrough` and the tag `external/cwe/cwe-079` has been added.

View File

@@ -1,9 +1,3 @@
- queries: .
- include:
id:
- go/unhandled-writable-file-close
- go/unexpected-nil-value
- go/negative-length-check
- go/redundant-recover
- go/missing-error-check
- go/index-out-of-bounds
- apply: code-quality-selectors.yml
from: codeql/suite-helpers

View File

@@ -7,7 +7,7 @@
* @id go/ldap-injection
* @tags security
* experimental
* external/cwe/cwe-90
* external/cwe/cwe-090
*/
import go

View File

@@ -6,7 +6,7 @@
* @id go/dsn-injection
* @tags security
* experimental
* external/cwe/cwe-74
* external/cwe/cwe-074
*/
import go

View File

@@ -6,7 +6,7 @@
* @id go/dsn-injection-local
* @tags security
* experimental
* external/cwe/cwe-74
* external/cwe/cwe-074
*/
import go

View File

@@ -7,7 +7,7 @@
* @id go/html-template-escaping-passthrough
* @tags security
* experimental
* external/cwe/cwe-79
* external/cwe/cwe-079
*/
import go

View File

@@ -1,4 +1,3 @@
ql/java/ql/src/Language Abuse/TypeVariableHidesType.ql
ql/java/ql/src/Likely Bugs/Arithmetic/IntMultToLong.ql
ql/java/ql/src/Likely Bugs/Collections/WriteOnlyContainer.ql
ql/java/ql/src/Likely Bugs/Comparison/IncomparableEquals.ql

View File

@@ -9,6 +9,7 @@
* @tags reliability
* readability
* types
* quality
*/
import java

View File

@@ -9,6 +9,7 @@
* @tags reliability
* correctness
* types
* quality
* external/cwe/cwe-190
* external/cwe/cwe-192
* external/cwe/cwe-197

View File

@@ -7,6 +7,7 @@
* @id java/unused-container
* @tags maintainability
* useless-code
* quality
* external/cwe/cwe-561
*/

View File

@@ -8,6 +8,7 @@
* @id java/equals-on-unrelated-types
* @tags reliability
* correctness
* quality
*/
import java

View File

@@ -8,6 +8,7 @@
* @id java/inconsistent-equals-and-hashcode
* @tags reliability
* correctness
* quality
* external/cwe/cwe-581
*/

View File

@@ -8,6 +8,7 @@
* @id java/unchecked-cast-in-equals
* @tags reliability
* correctness
* quality
*/
import java

View File

@@ -8,6 +8,7 @@
* @id java/reference-equality-of-boxed-types
* @tags reliability
* correctness
* quality
* external/cwe/cwe-595
*/

View File

@@ -9,6 +9,7 @@
* @id java/contradictory-type-checks
* @tags correctness
* logic
* quality
*/
import java

View File

@@ -6,6 +6,7 @@
* @precision high
* @id java/suspicious-date-format
* @tags correctness
* quality
*/
import java

View File

@@ -9,6 +9,7 @@
* @tags efficiency
* correctness
* resources
* quality
* external/cwe/cwe-404
* external/cwe/cwe-772
*/

View File

@@ -9,6 +9,7 @@
* @tags efficiency
* correctness
* resources
* quality
* external/cwe/cwe-404
* external/cwe/cwe-772
*/

View File

@@ -5,7 +5,7 @@
* to it.
* @id java/count-untrusted-data-external-api
* @kind table
* @tags security external/cwe/cwe-20
* @tags security external/cwe/cwe-020
*/
import java

Some files were not shown because too many files have changed in this diff Show More