Skip to content

Commit 5884c71

Browse files
committed
Added signature input nodes to signature verify operation nodes
1 parent 8a64833 commit 5884c71

File tree

4 files changed

+88
-48
lines changed

4 files changed

+88
-48
lines changed

java/ql/lib/experimental/quantum/BouncyCastle.qll

Lines changed: 1 addition & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -236,8 +236,6 @@ module Signers {
236236
SignatureOperationInstance() { not this.isIntermediate() }
237237

238238
override Crypto::AlgorithmValueConsumer getAnAlgorithmValueConsumer() {
239-
result = this.getParameters().getAnAlgorithmValueConsumer()
240-
or
241239
result = SignerFlow::getNewFromUse(this, _, _)
242240
}
243241

@@ -266,7 +264,7 @@ module Signers {
266264
result.asExpr() = super.getMessageInput()
267265
}
268266

269-
override Crypto::ConsumerInputDataFlowNode getSignatureArtifactConsumer() {
267+
override Crypto::ConsumerInputDataFlowNode getSignatureConsumer() {
270268
result.asExpr() = super.getSignatureInput()
271269
}
272270

@@ -280,16 +278,6 @@ module Signers {
280278
SignerUseCall getAnUpdateCall() {
281279
result = SignerFlow::getAnIntermediateUseFromFinalUse(this, _, _)
282280
}
283-
284-
Crypto::KeyArtifactOutputInstance getKey() { result.flowsTo(this.getInitCall().getKeyArg()) }
285-
286-
Generators::KeyGenerationOperationInstance getKeyGenerationOperationInstance() {
287-
result.getKeyArtifactOutputInstance() = this.getKey()
288-
}
289-
290-
Params::ParametersInstantiation getParameters() {
291-
result = this.getKeyGenerationOperationInstance().getParameters()
292-
}
293281
}
294282
}
295283

java/ql/lib/experimental/quantum/BouncyCastle/AlgorithmInstances.qll

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -150,7 +150,6 @@ abstract class KeyGenerationAlgorithmInstance extends Crypto::KeyOperationAlgori
150150

151151
override Crypto::PaddingAlgorithmInstance getPaddingAlgorithm() { none() }
152152

153-
// TODO: Model flow from the parameter specification to the key generator.
154153
override Crypto::ConsumerInputDataFlowNode getKeySizeConsumer() { none() }
155154

156155
override Crypto::KeyOpAlg::Algorithm getAlgorithmType() {

java/ql/lib/experimental/quantum/BouncyCastle/FlowAnalysis.qll

Lines changed: 35 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -247,10 +247,42 @@ class KeyAdditionalFlowSteps extends MethodCall {
247247
DataFlow::Node getOutputNode() { result.asExpr() = this }
248248
}
249249

250+
/**
251+
* Model data flow from an ECDSA signature to the scalars r and s passed to
252+
* `verifySignature()`. The ECDSA signature is represented as a `BigInteger`
253+
* array, where the first element is the scalar r and the second element is the
254+
* scalar s.
255+
*/
256+
class ECDSASignatureAdditionalFlowSteps extends ArrayAccess {
257+
ECDSASignatureAdditionalFlowSteps() {
258+
this.getArray().getType().getName() = "BigInteger[]" and
259+
// It is reasonable to assume that the indices are integer literals
260+
this.getIndexExpr().(IntegerLiteral).getValue().toInt() = [0, 1]
261+
}
262+
263+
/**
264+
* The input node is the ECDSA signature represented as a `BigInteger` array.
265+
*/
266+
DataFlow::Node getInputNode() {
267+
// TODO: This should be the array node `this.getArray()`
268+
result.asExpr() = this.getArray()
269+
}
270+
271+
/**
272+
* The output node is the `BigInteger` element accessed by this array access.
273+
*/
274+
DataFlow::Node getOutputNode() { result.asExpr() = this }
275+
}
276+
250277
predicate additionalFlowSteps(DataFlow::Node node1, DataFlow::Node node2) {
251-
exists(KeyAdditionalFlowSteps call |
252-
node1 = call.getInputNode() and
253-
node2 = call.getOutputNode()
278+
exists(KeyAdditionalFlowSteps fs |
279+
node1 = fs.getInputNode() and
280+
node2 = fs.getOutputNode()
281+
)
282+
or
283+
exists(ECDSASignatureAdditionalFlowSteps fs |
284+
node1 = fs.getInputNode() and
285+
node2 = fs.getOutputNode()
254286
)
255287
}
256288

shared/quantum/codeql/quantum/experimental/Model.qll

Lines changed: 52 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -424,6 +424,17 @@ module CryptographyBase<LocationSig Location, InputSig<Location> Input> {
424424
final override ConsumerInputDataFlowNode getInputNode() { result = inputNode }
425425
}
426426

427+
final private class SignatureArtifactConsumer extends ArtifactConsumerAndInstance {
428+
ConsumerInputDataFlowNode inputNode;
429+
430+
SignatureArtifactConsumer() {
431+
exists(SignatureOperationInstance op | inputNode = op.getSignatureConsumer()) and
432+
this = Input::dfn_to_element(inputNode)
433+
}
434+
435+
final override ConsumerInputDataFlowNode getInputNode() { result = inputNode }
436+
}
437+
427438
/**
428439
* An artifact that is produced by an operation, representing a concrete artifact instance rather than a synthetic consumer artifact.
429440
*/
@@ -458,6 +469,8 @@ module CryptographyBase<LocationSig Location, InputSig<Location> Input> {
458469
}
459470

460471
override DataFlowNode getOutputNode() { result = creator.getOutputArtifact() }
472+
473+
KeyOperationInstance getCreator() { result = creator }
461474
}
462475

463476
/**
@@ -783,25 +796,14 @@ module CryptographyBase<LocationSig Location, InputSig<Location> Input> {
783796
}
784797

785798
/**
786-
* The output artifact from a signature operation, representing a signature
787-
* that is either generated or verified.
788-
*/
789-
abstract class SignatureArtifactInstance extends KeyOperationOutputArtifactInstance { }
790-
791-
/**
792-
* A key operation instance representing the generation or verification of a
793-
* signature.
799+
* A key operation instance representing a signature being generated or verified.
794800
*/
795801
abstract class SignatureOperationInstance extends KeyOperationInstance {
796802
/**
797-
* Gets the consumer of the signature input for this operation. This is
798-
* typically a signature that is being verified against a message.
803+
* Gets the consumer of the signature that is being verified in case of a
804+
* verification operation.
799805
*/
800-
abstract ConsumerInputDataFlowNode getSignatureArtifactConsumer();
801-
802-
final SignatureArtifactInstance getSignatureOutputArtifact() {
803-
result.getOutputNode() = this.getOutputArtifact()
804-
}
806+
abstract ConsumerInputDataFlowNode getSignatureConsumer();
805807
}
806808

807809
/**
@@ -1286,6 +1288,7 @@ module CryptographyBase<LocationSig Location, InputSig<Location> Input> {
12861288
TNonceInput(NonceArtifactConsumer e) or
12871289
TMessageInput(MessageArtifactConsumer e) or
12881290
TSaltInput(SaltArtifactConsumer e) or
1291+
TSignatureInput(SignatureArtifactConsumer e) or
12891292
TRandomNumberGeneration(RandomNumberGenerationInstance e) { e.flowsTo(_) } or
12901293
// Key Creation Operation union type (e.g., key generation, key load)
12911294
TKeyCreationOperation(KeyCreationOperationInstance e) or
@@ -1295,7 +1298,6 @@ module CryptographyBase<LocationSig Location, InputSig<Location> Input> {
12951298
TKeyOperation(KeyOperationInstance e) or
12961299
TKeyOperationAlgorithm(KeyOperationAlgorithmInstanceOrValueConsumer e) or
12971300
TKeyOperationOutput(KeyOperationOutputArtifactInstance e) or
1298-
TSignature(SignatureOperationInstance e) or
12991301
// Non-Standalone Algorithms (e.g., Mode, Padding)
13001302
// These algorithms are always tied to a key operation algorithm
13011303
TModeOfOperationAlgorithm(ModeOfOperationAlgorithmInstance e) or
@@ -1348,14 +1350,14 @@ module CryptographyBase<LocationSig Location, InputSig<Location> Input> {
13481350
/**
13491351
* Returns the child of this node with the given edge name.
13501352
*
1351-
* This predicate is overriden by derived classes to construct the graph of cryptographic operations.
1353+
* This predicate is overridden by derived classes to construct the graph of cryptographic operations.
13521354
*/
13531355
NodeBase getChild(string edgeName) { none() }
13541356

13551357
/**
13561358
* Defines properties of this node by name and either a value or location or both.
13571359
*
1358-
* This predicate is overriden by derived classes to construct the graph of cryptographic operations.
1360+
* This predicate is overridden by derived classes to construct the graph of cryptographic operations.
13591361
*/
13601362
predicate properties(string key, string value, Location location) { none() }
13611363

@@ -1528,6 +1530,20 @@ module CryptographyBase<LocationSig Location, InputSig<Location> Input> {
15281530
override LocatableElement asElement() { result = instance }
15291531
}
15301532

1533+
/**
1534+
* A signature input. This may represent a signature, or a signature component
1535+
* such as the scalar values r and s in ECDSA.
1536+
*/
1537+
final class SignatureArtifactNode extends ArtifactNode, TSignatureInput {
1538+
SignatureArtifactConsumer instance;
1539+
1540+
SignatureArtifactNode() { this = TSignatureInput(instance) }
1541+
1542+
final override string getInternalType() { result = "SignatureInput" }
1543+
1544+
override LocatableElement asElement() { result = instance }
1545+
}
1546+
15311547
/**
15321548
* A salt input.
15331549
*/
@@ -1551,23 +1567,20 @@ module CryptographyBase<LocationSig Location, InputSig<Location> Input> {
15511567

15521568
KeyOperationOutputNode() { this = TKeyOperationOutput(instance) }
15531569

1554-
final override string getInternalType() { result = "KeyOperationOutput" }
1570+
override string getInternalType() { result = "KeyOperationOutput" }
15551571

15561572
override LocatableElement asElement() { result = instance }
15571573

15581574
override string getSourceNodeRelationship() { none() }
15591575
}
15601576

1561-
class SignatureArtifactNode extends ArtifactNode, TKeyOperationOutput {
1562-
SignatureArtifactInstance instance;
1563-
1564-
SignatureArtifactNode() { this = TKeyOperationOutput(instance) }
1565-
1566-
final override string getInternalType() { result = "Signature" }
1567-
1568-
override LocatableElement asElement() { result = instance }
1577+
class SignOperationOutputNode extends KeyOperationOutputNode {
1578+
SignOperationOutputNode() {
1579+
this.asElement().(KeyOperationOutputArtifactInstance).getCreator().getKeyOperationSubtype() =
1580+
TSignMode()
1581+
}
15691582

1570-
override string getSourceNodeRelationship() { none() }
1583+
override string getInternalType() { result = "SignatureOutput" }
15711584
}
15721585

15731586
/**
@@ -2153,10 +2166,18 @@ module CryptographyBase<LocationSig Location, InputSig<Location> Input> {
21532166

21542167
override string getInternalType() { result = nodeName }
21552168

2156-
SignatureArtifactNode getSignatureArtifact() {
2157-
result.asElement() = instance.getOutputArtifactInstance()
2169+
SignatureArtifactNode getASignatureArtifact() {
2170+
result.asElement() = instance.getSignatureConsumer().getConsumer()
2171+
}
2172+
2173+
override NodeBase getChild(string key) {
2174+
result = super.getChild(key)
21582175
or
2159-
result.asElement() = instance.getSignatureArtifactConsumer().getConsumer()
2176+
// [KNOWN_OR_UNKNOWN]
2177+
key = "Signature" and
2178+
if exists(this.getASignatureArtifact())
2179+
then result = this.getASignatureArtifact()
2180+
else result = this
21602181
}
21612182
}
21622183

0 commit comments

Comments
 (0)