Skip to content

Commit cae1892

Browse files
committed
Swift: Update StringLengthConflation to use DataFlow::StateConfigSig
1 parent 3bd6fd0 commit cae1892

File tree

3 files changed

+61
-30
lines changed

3 files changed

+61
-30
lines changed

swift/ql/lib/codeql/swift/security/StringLengthConflationExtensions.qll

Lines changed: 32 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -7,47 +7,63 @@ import swift
77
import codeql.swift.dataflow.DataFlow
88
import codeql.swift.dataflow.ExternalFlow
99

10+
private newtype TStringType =
11+
TString() or
12+
TNsString() or
13+
TStringUtf8() or
14+
TStringUtf16() or
15+
TStringUnicodeScalars()
16+
1017
/**
1118
* A type of Swift string encoding. This class is used as a flow state for
1219
* the string length conflation taint tracking configuration.
1320
*/
14-
class StringType extends string {
21+
class StringType extends TStringType {
22+
string name;
1523
string singular;
16-
string equivClass;
24+
TStringType equivClass;
1725
string csvLabel;
1826

1927
StringType() {
20-
this = "String" and
28+
this = TString() and
29+
name = "String" and
2130
singular = "a String" and
22-
equivClass = "String" and
31+
equivClass = this and
2332
csvLabel = "string-length"
2433
or
25-
this = "NSString" and
34+
this = TNsString() and
35+
name = "NSString" and
2636
singular = "an NSString" and
27-
equivClass = "NSString" and
37+
equivClass = this and
2838
csvLabel = "nsstring-length"
2939
or
30-
this = "String.utf8" and
40+
this = TStringUtf8() and
41+
name = "String.utf8" and
3142
singular = "a String.utf8" and
32-
equivClass = "String.utf8" and
43+
equivClass = this and
3344
csvLabel = "string-utf8-length"
3445
or
35-
this = "String.utf16" and
46+
this = TStringUtf16() and
47+
name = "String.utf16" and
3648
singular = "a String.utf16" and
37-
equivClass = "NSString" and
49+
equivClass = TNsString() and
3850
csvLabel = "string-utf16-length"
3951
or
40-
this = "String.unicodeScalars" and
52+
this = TStringUnicodeScalars() and
53+
name = "String.unicodeScalars" and
4154
singular = "a String.unicodeScalars" and
42-
equivClass = "String.unicodeScalars" and
55+
equivClass = this and
4356
csvLabel = "string-unicodescalars-length"
4457
}
4558

59+
/** Gets a textual representation of this string type. */
60+
string toString() { result = name }
61+
4662
/**
4763
* Gets the equivalence class for this string type. If these are equal,
4864
* they should be treated as equivalent.
4965
*/
50-
string getEquivClass() { result = equivClass }
66+
StringType getEquivClass() { result = equivClass }
5167

5268
/**
5369
* Gets text for the singular form of this string type.
@@ -130,15 +146,15 @@ private class ExtraStringLengthConflationSource extends StringLengthConflationSo
130146
(
131147
// result of a call to `String.utf8.count`
132148
typeName = "String.UTF8View" and
133-
stringType = "String.utf8"
149+
stringType = TStringUtf8()
134150
or
135151
// result of a call to `String.utf16.count`
136152
typeName = "String.UTF16View" and
137-
stringType = "String.utf16"
153+
stringType = TStringUtf16()
138154
or
139155
// result of a call to `String.unicodeScalars.count`
140156
typeName = "String.UnicodeScalarView" and
141-
stringType = "String.unicodeScalars"
157+
stringType = TStringUnicodeScalars()
142158
) and
143159
memberRef.getBase().getType().(NominalType).getName() = typeName and
144160
memberRef.getMember().(VarDecl).getName() = "count" and

swift/ql/lib/codeql/swift/security/StringLengthConflationQuery.qll

Lines changed: 25 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -9,31 +9,46 @@ import codeql.swift.dataflow.TaintTracking
99
import codeql.swift.security.StringLengthConflationExtensions
1010

1111
/**
12-
* A configuration for tracking string lengths originating from source that is
13-
* a `String` or an `NSString` object, to a sink of a different kind that
12+
* A configuration for tracking string lengths originating from a source that
13+
* is a `String` or an `NSString` object, to a sink of a different kind that
1414
* expects an incompatible measure of length.
1515
*/
16-
class StringLengthConflationConfiguration extends TaintTracking::Configuration {
17-
StringLengthConflationConfiguration() { this = "StringLengthConflationConfiguration" }
16+
module StringLengthConflationConfig implements DataFlow::StateConfigSig {
17+
class FlowState = StringType;
1818

19-
override predicate isSource(DataFlow::Node node, string flowstate) {
19+
predicate isSource(DataFlow::Node node, FlowState flowstate) {
2020
flowstate = node.(StringLengthConflationSource).getStringType()
2121
}
2222

23-
override predicate isSink(DataFlow::Node node, string flowstate) {
23+
predicate isSink(DataFlow::Node node, FlowState flowstate) {
2424
// Permit any *incorrect* flowstate, as those are the results the query
2525
// should report.
26-
exists(string correctFlowState |
26+
exists(FlowState correctFlowState |
2727
correctFlowState = node.(StringLengthConflationSink).getCorrectStringType() and
28-
flowstate.(StringType).getEquivClass() != correctFlowState.(StringType).getEquivClass()
28+
flowstate.getEquivClass() != correctFlowState.getEquivClass()
2929
)
3030
}
3131

32-
override predicate isSanitizer(DataFlow::Node sanitizer) {
32+
predicate isBarrier(DataFlow::Node sanitizer) {
3333
sanitizer instanceof StringLengthConflationSanitizer
3434
}
3535

36-
override predicate isAdditionalTaintStep(DataFlow::Node nodeFrom, DataFlow::Node nodeTo) {
36+
predicate isBarrier(DataFlow::Node sanitizer, FlowState flowstate) { none() }
37+
38+
predicate isAdditionalFlowStep(DataFlow::Node nodeFrom, DataFlow::Node nodeTo) {
3739
any(StringLengthConflationAdditionalTaintStep s).step(nodeFrom, nodeTo)
3840
}
41+
42+
predicate isAdditionalFlowStep(
43+
DataFlow::Node nodeFrom, FlowState flowstateFrom, DataFlow::Node nodeTo, FlowState flowStateTo
44+
) {
45+
none()
46+
}
3947
}
48+
49+
/**
50+
* Detect taint flow of string lengths originating from a source that is
51+
* a `String` or an `NSString` object, to a sink of a different kind that
52+
* expects an incompatible measure of length.
53+
*/
54+
module StringLengthConflationFlow = TaintTracking::GlobalWithState<StringLengthConflationConfig>;

swift/ql/src/queries/Security/CWE-135/StringLengthConflation.ql

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,14 @@
1313
import swift
1414
import codeql.swift.dataflow.DataFlow
1515
import codeql.swift.security.StringLengthConflationQuery
16-
import DataFlow::PathGraph
16+
import StringLengthConflationFlow::PathGraph
1717

1818
from
19-
StringLengthConflationConfiguration config, DataFlow::PathNode source, DataFlow::PathNode sink,
19+
StringLengthConflationFlow::PathNode source, StringLengthConflationFlow::PathNode sink,
2020
StringType sourceType, StringType sinkType, string message
2121
where
22-
config.hasFlowPath(source, sink) and
23-
config.isSource(source.getNode(), sourceType) and
22+
StringLengthConflationFlow::flowPath(source, sink) and
23+
StringLengthConflationConfig::isSource(source.getNode(), sourceType) and
2424
sinkType = sink.getNode().(StringLengthConflationSink).getCorrectStringType() and
2525
message =
2626
"This " + sourceType + " length is used in " + sinkType.getSingular() +

0 commit comments

Comments
 (0)