Skip to content

Commit 084b02f

Browse files
adecaroyacovm
authored andcommitted
[FAB-3441] Add more input validation tests to BCCSP.
This changeset adds a set of unit-tests to SW part of the default BCCSP. It focuses on passing a few invalid inputs and verifying the correct/expected behavior. Change-Id: I232c5bf77dd264cb93d88394f03dee92f19d40e2 Signed-off-by: Angelo De Caro <[email protected]>
1 parent f367a52 commit 084b02f

File tree

3 files changed

+211
-15
lines changed

3 files changed

+211
-15
lines changed

bccsp/mocks/mocks.go

+48-10
Original file line numberDiff line numberDiff line change
@@ -38,27 +38,27 @@ type MockBCCSP struct {
3838
}
3939

4040
func (*MockBCCSP) KeyGen(opts bccsp.KeyGenOpts) (k bccsp.Key, err error) {
41-
panic("implement me")
41+
panic("Not yet implemented")
4242
}
4343

4444
func (*MockBCCSP) KeyDeriv(k bccsp.Key, opts bccsp.KeyDerivOpts) (dk bccsp.Key, err error) {
45-
panic("implement me")
45+
panic("Not yet implemented")
4646
}
4747

4848
func (*MockBCCSP) KeyImport(raw interface{}, opts bccsp.KeyImportOpts) (k bccsp.Key, err error) {
49-
panic("implement me")
49+
panic("Not yet implemented")
5050
}
5151

5252
func (*MockBCCSP) GetKey(ski []byte) (k bccsp.Key, err error) {
53-
panic("implement me")
53+
panic("Not yet implemented")
5454
}
5555

5656
func (*MockBCCSP) Hash(msg []byte, opts bccsp.HashOpts) (hash []byte, err error) {
57-
panic("implement me")
57+
panic("Not yet implemented")
5858
}
5959

6060
func (*MockBCCSP) GetHash(opts bccsp.HashOpts) (h hash.Hash, err error) {
61-
panic("implement me")
61+
panic("Not yet implemented")
6262
}
6363

6464
func (b *MockBCCSP) Sign(k bccsp.Key, digest []byte, opts bccsp.SignerOpts) (signature []byte, err error) {
@@ -80,11 +80,11 @@ func (b *MockBCCSP) Verify(k bccsp.Key, signature, digest []byte, opts bccsp.Sig
8080
}
8181

8282
func (*MockBCCSP) Encrypt(k bccsp.Key, plaintext []byte, opts bccsp.EncrypterOpts) (ciphertext []byte, err error) {
83-
panic("implement me")
83+
panic("Not yet implemented")
8484
}
8585

8686
func (*MockBCCSP) Decrypt(k bccsp.Key, ciphertext []byte, opts bccsp.DecrypterOpts) (plaintext []byte, err error) {
87-
panic("implement me")
87+
panic("Not yet implemented")
8888
}
8989

9090
type MockKey struct {
@@ -100,15 +100,15 @@ func (m *MockKey) Bytes() ([]byte, error) {
100100
}
101101

102102
func (*MockKey) SKI() []byte {
103-
panic("implement me")
103+
panic("Not yet implemented")
104104
}
105105

106106
func (m *MockKey) Symmetric() bool {
107107
return m.Symm
108108
}
109109

110110
func (*MockKey) Private() bool {
111-
panic("implement me")
111+
panic("Not yet implemented")
112112
}
113113

114114
func (m *MockKey) PublicKey() (bccsp.Key, error) {
@@ -122,3 +122,41 @@ type SignerOpts struct {
122122
func (o *SignerOpts) HashFunc() crypto.Hash {
123123
return o.HashFuncValue
124124
}
125+
126+
type KeyGenOpts struct{}
127+
128+
func (*KeyGenOpts) Algorithm() string {
129+
return "Mock KeyGenOpts"
130+
}
131+
132+
func (*KeyGenOpts) Ephemeral() bool {
133+
panic("Not yet implemented")
134+
}
135+
136+
type KeyStore struct {
137+
GetKeyValue bccsp.Key
138+
GetKeyErr error
139+
StoreKeyErr error
140+
}
141+
142+
func (*KeyStore) ReadOnly() bool {
143+
panic("Not yet implemented")
144+
}
145+
146+
func (ks *KeyStore) GetKey(ski []byte) (k bccsp.Key, err error) {
147+
return ks.GetKeyValue, ks.GetKeyErr
148+
}
149+
150+
func (ks *KeyStore) StoreKey(k bccsp.Key) (err error) {
151+
return ks.StoreKeyErr
152+
}
153+
154+
type KeyImportOpts struct{}
155+
156+
func (*KeyImportOpts) Algorithm() string {
157+
return "Mock KeyImportOpts"
158+
}
159+
160+
func (*KeyImportOpts) Ephemeral() bool {
161+
panic("Not yet implemented")
162+
}

bccsp/sw/impl.go

+5-5
Original file line numberDiff line numberDiff line change
@@ -580,7 +580,7 @@ func (csp *impl) KeyImport(raw interface{}, opts bccsp.KeyImportOpts) (k bccsp.K
580580
}
581581

582582
default:
583-
return nil, errors.New("Import Key Options not recognized")
583+
return nil, fmt.Errorf("Unsupported 'KeyImportOptions' provided [%v]", opts)
584584
}
585585
}
586586

@@ -665,7 +665,7 @@ func (csp *impl) Sign(k bccsp.Key, digest []byte, opts bccsp.SignerOpts) (signat
665665

666666
return k.(*rsaPrivateKey).privKey.Sign(rand.Reader, digest, opts)
667667
default:
668-
return nil, fmt.Errorf("Key type not recognized [%s]", k)
668+
return nil, fmt.Errorf("Unsupported 'SignKey' provided [%v]", k)
669669
}
670670
}
671671

@@ -717,7 +717,7 @@ func (csp *impl) Verify(k bccsp.Key, signature, digest []byte, opts bccsp.Signer
717717
return false, fmt.Errorf("Opts type not recognized [%s]", opts)
718718
}
719719
default:
720-
return false, fmt.Errorf("Key type not recognized [%s]", k)
720+
return false, fmt.Errorf("Unsupported 'VerifyKey' provided [%v]", k)
721721
}
722722
}
723723

@@ -741,7 +741,7 @@ func (csp *impl) Encrypt(k bccsp.Key, plaintext []byte, opts bccsp.EncrypterOpts
741741
return nil, fmt.Errorf("Mode not recognized [%s]", opts)
742742
}
743743
default:
744-
return nil, fmt.Errorf("Key type not recognized [%s]", k)
744+
return nil, fmt.Errorf("Unsupported 'EncryptKey' provided [%v]", k)
745745
}
746746
}
747747

@@ -765,6 +765,6 @@ func (csp *impl) Decrypt(k bccsp.Key, ciphertext []byte, opts bccsp.DecrypterOpt
765765
return nil, fmt.Errorf("Mode not recognized [%s]", opts)
766766
}
767767
default:
768-
return nil, fmt.Errorf("Key type not recognized [%s]", k)
768+
return nil, fmt.Errorf("Unsupported 'DecryptKey' provided [%v]", k)
769769
}
770770
}

bccsp/sw/sw_test.go

+158
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,158 @@
1+
/*
2+
Copyright IBM Corp. 2017 All Rights Reserved.
3+
4+
Licensed under the Apache License, Version 2.0 (the "License");
5+
you may not use this file except in compliance with the License.
6+
You may obtain a copy of the License at
7+
8+
http://www.apache.org/licenses/LICENSE-2.0
9+
10+
Unless required by applicable law or agreed to in writing, software
11+
distributed under the License is distributed on an "AS IS" BASIS,
12+
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
See the License for the specific language governing permissions and
14+
limitations under the License.
15+
*/
16+
17+
package sw
18+
19+
import (
20+
"errors"
21+
"strings"
22+
"testing"
23+
24+
"github.com/hyperledger/fabric/bccsp"
25+
"github.com/hyperledger/fabric/bccsp/mocks"
26+
"github.com/stretchr/testify/assert"
27+
)
28+
29+
func TestKeyGenInvalidInputs(t *testing.T) {
30+
// Init a BCCSP instance with a key store that returns an error on store
31+
csp, err := New(256, "SHA2", &mocks.KeyStore{StoreKeyErr: errors.New("cannot store key")})
32+
assert.NoError(t, err)
33+
34+
_, err = csp.KeyGen(nil)
35+
assert.Error(t, err)
36+
assert.True(t, strings.Contains(err.Error(), "Invalid Opts parameter. It must not be nil."))
37+
38+
_, err = csp.KeyGen(&mocks.KeyGenOpts{})
39+
assert.Error(t, err)
40+
assert.True(t, strings.Contains(err.Error(), "Unrecognized KeyGenOpts provided ["))
41+
42+
_, err = csp.KeyGen(&bccsp.ECDSAP256KeyGenOpts{})
43+
assert.Error(t, err, "Generation of a non-ephemeral key must fail. KeyStore is programmed to fail.")
44+
assert.True(t, strings.Contains(err.Error(), "cannot store key"), "Failure must be due to the KeyStore")
45+
}
46+
47+
func TestKeyDerivInvalidInputs(t *testing.T) {
48+
csp, err := New(256, "SHA2", &mocks.KeyStore{})
49+
assert.NoError(t, err)
50+
51+
_, err = csp.KeyDeriv(nil, &bccsp.ECDSAReRandKeyOpts{})
52+
assert.Error(t, err)
53+
assert.True(t, strings.Contains(err.Error(), "Invalid Key. It must not be nil."))
54+
55+
_, err = csp.KeyDeriv(&mocks.MockKey{}, &bccsp.ECDSAReRandKeyOpts{})
56+
assert.Error(t, err)
57+
assert.True(t, strings.Contains(err.Error(), "Key type not recognized ["))
58+
}
59+
60+
func TestKeyImportInvalidInputs(t *testing.T) {
61+
csp, err := New(256, "SHA2", &mocks.KeyStore{})
62+
assert.NoError(t, err)
63+
64+
_, err = csp.KeyImport(nil, &bccsp.AES256ImportKeyOpts{})
65+
assert.Error(t, err)
66+
assert.True(t, strings.Contains(err.Error(), "Invalid raw. Cannot be nil"))
67+
68+
_, err = csp.KeyImport([]byte{0, 1, 2, 3, 4}, nil)
69+
assert.Error(t, err)
70+
assert.True(t, strings.Contains(err.Error(), "Invalid Opts parameter. It must not be nil."))
71+
72+
_, err = csp.KeyImport([]byte{0, 1, 2, 3, 4}, &mocks.KeyImportOpts{})
73+
assert.Error(t, err)
74+
assert.True(t, strings.Contains(err.Error(), "Unsupported 'KeyImportOptions' provided ["))
75+
}
76+
77+
func TestGetKeyInvalidInputs(t *testing.T) {
78+
// Init a BCCSP instance with a key store that returns an error on get
79+
csp, err := New(256, "SHA2", &mocks.KeyStore{GetKeyErr: errors.New("cannot get key")})
80+
assert.NoError(t, err)
81+
82+
_, err = csp.GetKey(nil)
83+
assert.Error(t, err)
84+
assert.True(t, strings.Contains(err.Error(), "cannot get key"))
85+
86+
// Init a BCCSP instance with a key store that returns a given key
87+
k := &mocks.MockKey{}
88+
csp, err = New(256, "SHA2", &mocks.KeyStore{GetKeyValue: k})
89+
assert.NoError(t, err)
90+
// No SKI is needed here
91+
k2, err := csp.GetKey(nil)
92+
assert.NoError(t, err)
93+
assert.Equal(t, k, k2, "Keys must be the same.")
94+
}
95+
96+
func TestSignInvalidInputs(t *testing.T) {
97+
csp, err := New(256, "SHA2", &mocks.KeyStore{})
98+
assert.NoError(t, err)
99+
100+
_, err = csp.Sign(nil, []byte{1, 2, 3, 5}, nil)
101+
assert.Error(t, err)
102+
assert.True(t, strings.Contains(err.Error(), "Invalid Key. It must not be nil."))
103+
104+
_, err = csp.Sign(&mocks.MockKey{}, nil, nil)
105+
assert.Error(t, err)
106+
assert.True(t, strings.Contains(err.Error(), "Invalid digest. Cannot be empty."))
107+
108+
_, err = csp.Sign(&mocks.MockKey{}, []byte{1, 2, 3, 5}, nil)
109+
assert.Error(t, err)
110+
assert.True(t, strings.Contains(err.Error(), "Unsupported 'SignKey' provided ["))
111+
}
112+
113+
func TestVerifyInvalidInputs(t *testing.T) {
114+
csp, err := New(256, "SHA2", &mocks.KeyStore{})
115+
assert.NoError(t, err)
116+
117+
_, err = csp.Verify(nil, []byte{1, 2, 3, 5}, []byte{1, 2, 3, 5}, nil)
118+
assert.Error(t, err)
119+
assert.True(t, strings.Contains(err.Error(), "Invalid Key. It must not be nil."))
120+
121+
_, err = csp.Verify(&mocks.MockKey{}, nil, []byte{1, 2, 3, 5}, nil)
122+
assert.Error(t, err)
123+
assert.True(t, strings.Contains(err.Error(), "Invalid signature. Cannot be empty."))
124+
125+
_, err = csp.Verify(&mocks.MockKey{}, []byte{1, 2, 3, 5}, nil, nil)
126+
assert.Error(t, err)
127+
assert.True(t, strings.Contains(err.Error(), "Invalid digest. Cannot be empty."))
128+
129+
_, err = csp.Verify(&mocks.MockKey{}, []byte{1, 2, 3, 5}, []byte{1, 2, 3, 5}, nil)
130+
assert.Error(t, err)
131+
assert.True(t, strings.Contains(err.Error(), "Unsupported 'VerifyKey' provided ["))
132+
}
133+
134+
func TestEncryptInvalidInputs(t *testing.T) {
135+
csp, err := New(256, "SHA2", &mocks.KeyStore{})
136+
assert.NoError(t, err)
137+
138+
_, err = csp.Encrypt(nil, []byte{1, 2, 3, 4}, &bccsp.AESCBCPKCS7ModeOpts{})
139+
assert.Error(t, err)
140+
assert.True(t, strings.Contains(err.Error(), "Invalid Key. It must not be nil."))
141+
142+
_, err = csp.Encrypt(&mocks.MockKey{}, []byte{1, 2, 3, 4}, &bccsp.AESCBCPKCS7ModeOpts{})
143+
assert.Error(t, err)
144+
assert.True(t, strings.Contains(err.Error(), "Unsupported 'EncryptKey' provided ["))
145+
}
146+
147+
func TestDecryptInvalidInputs(t *testing.T) {
148+
csp, err := New(256, "SHA2", &mocks.KeyStore{})
149+
assert.NoError(t, err)
150+
151+
_, err = csp.Decrypt(nil, []byte{1, 2, 3, 4}, &bccsp.AESCBCPKCS7ModeOpts{})
152+
assert.Error(t, err)
153+
assert.True(t, strings.Contains(err.Error(), "Invalid Key. It must not be nil."))
154+
155+
_, err = csp.Decrypt(&mocks.MockKey{}, []byte{1, 2, 3, 4}, &bccsp.AESCBCPKCS7ModeOpts{})
156+
assert.Error(t, err)
157+
assert.True(t, strings.Contains(err.Error(), "Unsupported 'DecryptKey' provided ["))
158+
}

0 commit comments

Comments
 (0)