Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit de3ff45

Browse files
committed
Misc updates for OpenSSL modeling to trace algorithm literals to known alg getters, and converting the literal to a TCipherType.
1 parent cce5f24 commit de3ff45

8 files changed

Lines changed: 651 additions & 149 deletions

File tree

cpp/ql/lib/experimental/Quantum/Language.qll

Lines changed: 11 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -49,19 +49,19 @@ module GenericDataSourceUniversalFlowConfig implements DataFlow::ConfigSig {
4949

5050

5151

52-
// TODO: I think this will be inefficient, no?
53-
class ConstantDataSource extends Crypto::GenericConstantOrAllocationSource instanceof Literal {
54-
override DataFlow::Node getOutputNode() {
55-
result.asExpr() = this
56-
}
52+
// // TODO: I think this will be inefficient, no?
53+
// class ConstantDataSource extends Crypto::GenericConstantOrAllocationSource instanceof Literal {
54+
// override DataFlow::Node getOutputNode() {
55+
// result.asExpr() = this
56+
// }
5757

58-
override predicate flowsTo(Crypto::FlowAwareElement other) {
59-
// TODO: separate config to avoid blowing up data-flow analysis
60-
GenericDataSourceUniversalFlow::flow(this.getOutputNode(), other.getInputNode())
61-
}
58+
// override predicate flowsTo(Crypto::FlowAwareElement other) {
59+
// // TODO: separate config to avoid blowing up data-flow analysis
60+
// GenericDataSourceUniversalFlow::flow(this.getOutputNode(), other.getInputNode())
61+
// }
6262

63-
override string getAdditionalDescription() { result = this.toString() }
64-
}
63+
// override string getAdditionalDescription() { result = this.toString() }
64+
// }
6565

6666
/**
6767
* Definitions of various generic data sources

cpp/ql/lib/experimental/Quantum/OpenSSL/CtxFlow.qll

Lines changed: 6 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -8,17 +8,14 @@ class CTXType extends Type {
88
}
99

1010
class CTXPointerExpr extends Expr {
11-
CTXPointerExpr() {
12-
this.getType() instanceof CTXType and
13-
this.getType() instanceof PointerType
11+
CTXPointerExpr() {
12+
this.getType() instanceof CTXType and
13+
this.getType() instanceof PointerType
1414
}
1515
}
1616

1717
class CTXPointerArgument extends CTXPointerExpr {
18-
CTXPointerArgument() {
19-
20-
exists(Call c | c.getAnArgument() = this)
21-
}
18+
CTXPointerArgument() { exists(Call c | c.getAnArgument() = this) }
2219

2320
Call getCall() { result.getAnArgument() = this }
2421
}
@@ -31,14 +28,14 @@ class CTXClearCall extends Call {
3128
}
3229

3330
class CTXCopyOutArgCall extends Call {
34-
CTXCopyOutArgCall() {
31+
CTXCopyOutArgCall() {
3532
this.getTarget().getName().toLowerCase().matches(["%copy%"]) and
3633
this.getAnArgument() instanceof CTXPointerArgument
3734
}
3835
}
3936

4037
class CTXCopyReturnCall extends Call {
41-
CTXCopyReturnCall() {
38+
CTXCopyReturnCall() {
4239
this.getTarget().getName().toLowerCase().matches(["%dup%"]) and
4340
this.getAnArgument() instanceof CTXPointerArgument and
4441
this instanceof CTXPointerExpr
Lines changed: 148 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,148 @@
1+
import cpp
2+
import experimental.Quantum.Language
3+
import EVPCipherConsumers
4+
import OpenSSLAlgorithmGetter
5+
6+
predicate literalToCipherFamilyType(Literal e, Crypto::TCipherType type) {
7+
exists(string name, string algType | algType.toLowerCase().matches("%encryption") |
8+
resolveAlgorithmFromLiteral(e, name, algType) and
9+
(
10+
name.matches("AES%") and type instanceof Crypto::AES
11+
or
12+
name.matches("ARIA") and type instanceof Crypto::ARIA
13+
or
14+
name.matches("BLOWFISH") and type instanceof Crypto::BLOWFISH
15+
or
16+
name.matches("BF") and type instanceof Crypto::BLOWFISH
17+
or
18+
name.matches("CAMELLIA%") and type instanceof Crypto::CAMELLIA
19+
or
20+
name.matches("CHACHA20") and type instanceof Crypto::CHACHA20
21+
or
22+
name.matches("CAST5") and type instanceof Crypto::CAST5
23+
or
24+
name.matches("2DES") and type instanceof Crypto::DOUBLEDES
25+
or
26+
name.matches(["3DES", "TRIPLEDES"]) and type instanceof Crypto::TRIPLEDES
27+
or
28+
name.matches("DES") and type instanceof Crypto::DES
29+
or
30+
name.matches("DESX") and type instanceof Crypto::DESX
31+
or
32+
name.matches("GOST%") and type instanceof Crypto::GOST
33+
or
34+
name.matches("IDEA") and type instanceof Crypto::IDEA
35+
or
36+
name.matches("KUZNYECHIK") and type instanceof Crypto::KUZNYECHIK
37+
or
38+
name.matches("MAGMA") and type instanceof Crypto::MAGMA
39+
or
40+
name.matches("RC2") and type instanceof Crypto::RC2
41+
or
42+
name.matches("RC4") and type instanceof Crypto::RC4
43+
or
44+
name.matches("RC5") and type instanceof Crypto::RC5
45+
or
46+
name.matches("RSA") and type instanceof Crypto::RSA
47+
or
48+
name.matches("SEED") and type instanceof Crypto::SEED
49+
or
50+
name.matches("SM4") and type instanceof Crypto::SM4
51+
)
52+
)
53+
}
54+
55+
class CipherKnownAlgorithmLiteralAlgorithmInstance extends Crypto::CipherAlgorithmInstance instanceof Literal
56+
{
57+
CipherKnownAlgorithmLiteralAlgorithmInstance() {
58+
exists(EVPCipherGetterCall c, DataFlow::Node src, DataFlow::Node sink |
59+
sink = c.getValueArgNode() and
60+
src.asExpr() = this and
61+
KnownAlgorithmLiteralToAlgorithmGetterFlow::flow(src, sink) and
62+
// Not just any known value, but specifically a known cipher operation
63+
exists(string algType |
64+
resolveAlgorithmFromLiteral(src.asExpr(), _, algType) and
65+
algType.toLowerCase().matches("%encryption")
66+
)
67+
)
68+
}
69+
70+
Crypto::AlgorithmConsumer getConsumer() { none() } //result = consumer }
71+
72+
override Crypto::ModeOfOperationAlgorithmInstance getModeOfOperationAlgorithm() {
73+
none() // TODO: provider defaults
74+
}
75+
76+
override Crypto::PaddingAlgorithmInstance getPaddingAlgorithm() { none() }
77+
78+
override string getRawAlgorithmName() { result = this.(Literal).getValue().toString() }
79+
80+
override Crypto::TCipherType getCipherFamily() { literalToCipherFamilyType(this, result) }
81+
}
82+
// override Crypto::TCipherType getCipherFamily() {
83+
// if this.cipherNameMappingKnown(_, super.getAlgorithmName())
84+
// then this.cipherNameMappingKnown(result, super.getAlgorithmName())
85+
// else result instanceof Crypto::OtherCipherType
86+
// }
87+
// bindingset[name]
88+
// private predicate cipherNameMappingKnown(Crypto::TCipherType type, string name) {
89+
// name = "AES" and
90+
// type instanceof Crypto::AES
91+
// or
92+
// name = "DES" and
93+
// type instanceof Crypto::DES
94+
// or
95+
// name = "TripleDES" and
96+
// type instanceof Crypto::TripleDES
97+
// or
98+
// name = "IDEA" and
99+
// type instanceof Crypto::IDEA
100+
// or
101+
// name = "CAST5" and
102+
// type instanceof Crypto::CAST5
103+
// or
104+
// name = "ChaCha20" and
105+
// type instanceof Crypto::ChaCha20
106+
// or
107+
// name = "RC4" and
108+
// type instanceof Crypto::RC4
109+
// or
110+
// name = "RC5" and
111+
// type instanceof Crypto::RC5
112+
// or
113+
// name = "RSA" and
114+
// type instanceof Crypto::RSA
115+
// }
116+
// private predicate modeToNameMappingKnown(Crypto::TBlockCipherModeOperationType type, string name) {
117+
// type instanceof Crypto::ECB and name = "ECB"
118+
// or
119+
// type instanceof Crypto::CBC and name = "CBC"
120+
// or
121+
// type instanceof Crypto::GCM and name = "GCM"
122+
// or
123+
// type instanceof Crypto::CTR and name = "CTR"
124+
// or
125+
// type instanceof Crypto::XTS and name = "XTS"
126+
// or
127+
// type instanceof Crypto::CCM and name = "CCM"
128+
// or
129+
// type instanceof Crypto::SIV and name = "SIV"
130+
// or
131+
// type instanceof Crypto::OCB and name = "OCB"
132+
// }
133+
// override Crypto::TBlockCipherModeOperationType getModeType() {
134+
// if this.modeToNameMappingKnown(_, super.getMode())
135+
// then this.modeToNameMappingKnown(result, super.getMode())
136+
// else result instanceof Crypto::OtherMode
137+
// }
138+
// override string getRawModeAlgorithmName() { result = super.getMode() }
139+
// override string getRawPaddingAlgorithmName() { result = super.getPadding() }
140+
// bindingset[name]
141+
// private predicate paddingToNameMappingKnown(Crypto::TPaddingType type, string name) {
142+
// type instanceof Crypto::NoPadding and name = "NOPADDING"
143+
// or
144+
// type instanceof Crypto::PKCS7 and name = ["PKCS5Padding", "PKCS7Padding"] // TODO: misnomer in the JCA?
145+
// or
146+
// type instanceof Crypto::OAEP and name.matches("OAEP%") // TODO: handle OAEPWith%
147+
// }
148+
// }

cpp/ql/lib/experimental/Quantum/OpenSSL/EVPCipherConsumers.qll

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,14 @@
11
import EVPCipherInitializer
22
import EVPCipherOperation
3-
import AlgorithmSource
3+
import EVPCipherAlgorithmSource
44

55

66
class EVP_Cipher_Initializer_Algorithm_Consumer extends Crypto::AlgorithmConsumer instanceof EVPCipherInitializerAlgorithmArgument
77
{
88
override DataFlow::Node getInputNode() { result.asExpr() = this }
99

1010
override Crypto::AlgorithmElement getAKnownAlgorithmSource() {
11-
result.(CipherLiteralAlgorithmInstance).getConsumer() = this
11+
result.(CipherKnownAlgorithmLiteralAlgorithmInstance).getConsumer() = this
1212
}
1313
}
1414
// //TODO: need a key consumer
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
import cpp
2+
3+
predicate isPossibleOpenSSLFunction(Function f) {
4+
isPossibleOpenSSLLocation(f.getADeclarationLocation())
5+
}
6+
7+
predicate isPossibleOpenSSLLocation(Location l){
8+
l.toString().toLowerCase().matches("%openssl%")
9+
}
10+

0 commit comments

Comments
 (0)