1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164
|
// Copyright 2019 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package wycheproof
import (
"crypto/ecdsa"
"testing"
)
func TestEcdsa(t *testing.T) {
// AsnSignatureTestVector
type AsnSignatureTestVector struct {
// A brief description of the test case
Comment string `json:"comment,omitempty"`
// A list of flags
Flags []string `json:"flags,omitempty"`
// The message to sign
Msg string `json:"msg,omitempty"`
// Test result
Result string `json:"result,omitempty"`
// An ASN encoded signature for msg
Sig string `json:"sig,omitempty"`
// Identifier of the test case
TcId int `json:"tcId,omitempty"`
}
// EcPublicKey
type EcPublicKey struct {
// the EC group used by this public key
Curve interface{} `json:"curve,omitempty"`
// the key size in bits
KeySize int `json:"keySize,omitempty"`
// the key type
Type string `json:"type,omitempty"`
// encoded public key point
Uncompressed string `json:"uncompressed,omitempty"`
// the x-coordinate of the public key point
Wx string `json:"wx,omitempty"`
// the y-coordinate of the public key point
Wy string `json:"wy,omitempty"`
}
// EcUnnamedGroup
type EcUnnamedGroup struct {
// coefficient a of the elliptic curve equation
A string `json:"a,omitempty"`
// coefficient b of the elliptic curve equation
B string `json:"b,omitempty"`
// the x-coordinate of the generator
Gx string `json:"gx,omitempty"`
// the y-coordinate of the generator
Gy string `json:"gy,omitempty"`
// the cofactor
H int `json:"h,omitempty"`
// the order of the generator
N string `json:"n,omitempty"`
// the order of the underlying field
P string `json:"p,omitempty"`
// an unnamed EC group over a prime field in Weierstrass form
Type string `json:"type,omitempty"`
}
// EcdsaTestGroup
type EcdsaTestGroup struct {
// unenocded EC public key
Key *EcPublicKey `json:"key,omitempty"`
// DER encoded public key
KeyDer string `json:"keyDer,omitempty"`
// Pem encoded public key
KeyPem string `json:"keyPem,omitempty"`
// the hash function used for ECDSA
Sha string `json:"sha,omitempty"`
Tests []*AsnSignatureTestVector `json:"tests,omitempty"`
Type interface{} `json:"type,omitempty"`
}
// Notes a description of the labels used in the test vectors
type Notes struct {
}
// Root
type Root struct {
// the primitive tested in the test file
Algorithm string `json:"algorithm,omitempty"`
// the version of the test vectors.
GeneratorVersion string `json:"generatorVersion,omitempty"`
// additional documentation
Header []string `json:"header,omitempty"`
// a description of the labels used in the test vectors
Notes *Notes `json:"notes,omitempty"`
// the number of test vectors in this test
NumberOfTests int `json:"numberOfTests,omitempty"`
Schema interface{} `json:"schema,omitempty"`
TestGroups []*EcdsaTestGroup `json:"testGroups,omitempty"`
}
flagsShouldPass := map[string]bool{
// An encoded ASN.1 integer missing a leading zero is invalid, but accepted by some implementations.
"MissingZero": false,
// A signature using a weaker hash than the EC params is not a security risk, as long as the hash is secure.
// https://www.imperialviolet.org/2014/05/25/strengthmatching.html
"WeakHash": true,
}
// supportedCurves is a map of all elliptic curves supported
// by crypto/elliptic, which can subsequently be parsed and tested.
supportedCurves := map[string]bool{
"secp224r1": true,
"secp256r1": true,
"secp384r1": true,
"secp521r1": true,
}
var root Root
readTestVector(t, "ecdsa_test.json", &root)
for _, tg := range root.TestGroups {
curve := tg.Key.Curve.(string)
if !supportedCurves[curve] {
continue
}
pub := decodePublicKey(tg.KeyDer).(*ecdsa.PublicKey)
h := parseHash(tg.Sha).New()
for _, sig := range tg.Tests {
h.Reset()
h.Write(decodeHex(sig.Msg))
hashed := h.Sum(nil)
got := verifyASN1(pub, hashed, decodeHex(sig.Sig))
if want := shouldPass(sig.Result, sig.Flags, flagsShouldPass); got != want {
t.Errorf("tcid: %d, type: %s, comment: %q, wanted success: %t", sig.TcId, sig.Result, sig.Comment, want)
}
}
}
}
|