1
2
3
4
5 package wycheproof
6
7 import (
8 "crypto/aes"
9 "crypto/cipher"
10 "encoding/hex"
11 "fmt"
12 "testing"
13 )
14
15 func TestAesCbc(t *testing.T) {
16
17 type IndCpaTestVector struct {
18
19
20 Comment string `json:"comment,omitempty"`
21
22
23 Ct string `json:"ct,omitempty"`
24
25
26 Flags []string `json:"flags,omitempty"`
27
28
29 Iv string `json:"iv,omitempty"`
30
31
32 Key string `json:"key,omitempty"`
33
34
35 Msg string `json:"msg,omitempty"`
36
37
38 Result string `json:"result,omitempty"`
39
40
41 TcId int `json:"tcId,omitempty"`
42 }
43
44
45 type Notes struct {
46 }
47
48
49 type IndCpaTestGroup struct {
50
51
52 IvSize int `json:"ivSize,omitempty"`
53
54
55 KeySize int `json:"keySize,omitempty"`
56
57
58 TagSize int `json:"tagSize,omitempty"`
59 Tests []*IndCpaTestVector `json:"tests,omitempty"`
60 Type interface{} `json:"type,omitempty"`
61 }
62
63
64 type Root struct {
65
66
67 Algorithm string `json:"algorithm,omitempty"`
68
69
70 GeneratorVersion string `json:"generatorVersion,omitempty"`
71
72
73 Header []string `json:"header,omitempty"`
74
75
76 Notes *Notes `json:"notes,omitempty"`
77
78
79 NumberOfTests int `json:"numberOfTests,omitempty"`
80 Schema interface{} `json:"schema,omitempty"`
81 TestGroups []*IndCpaTestGroup `json:"testGroups,omitempty"`
82 }
83
84 var root Root
85 readTestVector(t, "aes_cbc_pkcs5_test.json", &root)
86 for _, tg := range root.TestGroups {
87 tests:
88 for _, tv := range tg.Tests {
89 block, err := aes.NewCipher(decodeHex(tv.Key))
90 if err != nil {
91 t.Fatalf("#%d: %v", tv.TcId, err)
92 }
93 mode := cipher.NewCBCDecrypter(block, decodeHex(tv.Iv))
94 ct := decodeHex(tv.Ct)
95 if len(ct)%aes.BlockSize != 0 {
96 panic(fmt.Sprintf("#%d: ciphertext is not a multiple of the block size", tv.TcId))
97 }
98 mode.CryptBlocks(ct, ct)
99
100
101
102
103 for _, flag := range tv.Flags {
104 if flag == "BadPadding" {
105 continue tests
106 }
107 }
108 if !shouldPass(tv.Result, tv.Flags, nil) {
109 panic(fmt.Sprintf("#%d: found an invalid test that is broken for some reason other than bad padding", tv.TcId))
110 }
111
112
113 padding := ct[len(ct)-1]
114 paddingNum := int(padding)
115 for i := paddingNum; i > 0; i-- {
116 if ct[len(ct)-i] != padding {
117 panic(fmt.Sprintf("#%d: bad padding at index=%d of %v", tv.TcId, i, ct))
118 }
119 }
120 ct = ct[:len(ct)-paddingNum]
121
122 if got, want := hex.EncodeToString(ct), tv.Msg; got != want {
123 t.Errorf("#%d, type: %s, comment: %q, decoded ciphertext not equal: %s, want %s", tv.TcId, tv.Result, tv.Comment, got, want)
124 }
125 }
126 }
127 }
128
View as plain text