Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(44)

Side by Side Diff: net/quic/crypto/aes_128_gcm_encrypter_test.cc

Issue 12623017: Add Aes128GcmEncrypter and Aes128GcmDecrypter (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src/
Patch Set: Fix build errors. Add GetKey and GetNoncePrefix. Created 7 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
Property Changes:
Added: svn:eol-style
+ LF
OLDNEW
(Empty)
1 // Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "net/quic/crypto/aes_128_gcm_encrypter.h"
6
7 #include "net/quic/test_tools/quic_test_utils.h"
8
9 using base::StringPiece;
10
11 namespace {
12
13 // The AES GCM test vectors come from the file gcmEncryptExtIV128.rsp
14 // downloaded from http://csrc.nist.gov/groups/STM/cavp/index.html on
15 // 2013-02-01. The test vectors in that file look like this:
16 //
17 // [Keylen = 128]
18 // [IVlen = 96]
19 // [PTlen = 0]
20 // [AADlen = 0]
21 // [Taglen = 128]
22 //
23 // Count = 0
24 // Key = 11754cd72aec309bf52f7687212e8957
25 // IV = 3c819d9a9bed087615030b65
26 // PT =
27 // AAD =
28 // CT =
29 // Tag = 250327c674aaf477aef2675748cf6971
30 //
31 // Count = 1
32 // Key = ca47248ac0b6f8372a97ac43508308ed
33 // IV = ffd2b598feabc9019262d2be
34 // PT =
35 // AAD =
36 // CT =
37 // Tag = 60d20404af527d248d893ae495707d1a
38 //
39 // ...
40 //
41 // The gcmEncryptExtIV128.rsp file is huge (2.8 MB), so I selected just a
42 // few test vectors for this unit test.
43
44 // Describes a group of test vectors that all have a given key length, IV
45 // length, plaintext length, AAD length, and tag length.
46 struct TestGroupInfo {
47 size_t key_len;
48 size_t iv_len;
49 size_t pt_len;
50 size_t aad_len;
51 size_t tag_len;
52 };
53
54 // Each test vector consists of six strings of lowercase hexadecimal digits.
55 // The strings may be empty (zero length). A test vector with a NULL |key|
56 // marks the end of an array of test vectors.
57 struct TestVector {
58 const char* key;
59 const char* iv;
60 const char* pt;
61 const char* aad;
62 const char* ct;
63 const char* tag;
64 };
65
66 const TestGroupInfo test_group_info[] = {
67 { 128, 96, 0, 0, 128 },
68 { 128, 96, 0, 128, 128 },
69 { 128, 96, 128, 0, 128 },
70 { 128, 96, 408, 160, 128 },
71 { 128, 96, 408, 720, 128 },
72 { 128, 96, 104, 0, 128 },
73 };
74
75 const TestVector test_group_0[] = {
76 { "11754cd72aec309bf52f7687212e8957",
77 "3c819d9a9bed087615030b65",
78 "",
79 "",
80 "",
81 "250327c674aaf477aef2675748cf6971"
82 },
83 { "ca47248ac0b6f8372a97ac43508308ed",
84 "ffd2b598feabc9019262d2be",
85 "",
86 "",
87 "",
88 "60d20404af527d248d893ae495707d1a"
89 },
90 { NULL }
91 };
92
93 const TestVector test_group_1[] = {
94 { "77be63708971c4e240d1cb79e8d77feb",
95 "e0e00f19fed7ba0136a797f3",
96 "",
97 "7a43ec1d9c0a5a78a0b16533a6213cab",
98 "",
99 "209fcc8d3675ed938e9c7166709dd946"
100 },
101 { "7680c5d3ca6154758e510f4d25b98820",
102 "f8f105f9c3df4965780321f8",
103 "",
104 "c94c410194c765e3dcc7964379758ed3",
105 "",
106 "94dca8edfcf90bb74b153c8d48a17930"
107 },
108 { NULL }
109 };
110
111 const TestVector test_group_2[] = {
112 { "7fddb57453c241d03efbed3ac44e371c",
113 "ee283a3fc75575e33efd4887",
114 "d5de42b461646c255c87bd2962d3b9a2",
115 "",
116 "2ccda4a5415cb91e135c2a0f78c9b2fd",
117 "b36d1df9b9d5e596f83e8b7f52971cb3"
118 },
119 { "ab72c77b97cb5fe9a382d9fe81ffdbed",
120 "54cc7dc2c37ec006bcc6d1da",
121 "007c5e5b3e59df24a7c355584fc1518d",
122 "",
123 "0e1bde206a07a9c2c1b65300f8c64997",
124 "2b4401346697138c7a4891ee59867d0c"
125 },
126 { NULL }
127 };
128
129 const TestVector test_group_3[] = {
130 { "fe47fcce5fc32665d2ae399e4eec72ba",
131 "5adb9609dbaeb58cbd6e7275",
132 "7c0e88c88899a779228465074797cd4c2e1498d259b54390b85e3eef1c02df60e743f1"
133 "b840382c4bccaf3bafb4ca8429bea063",
134 "88319d6e1d3ffa5f987199166c8a9b56c2aeba5a",
135 "98f4826f05a265e6dd2be82db241c0fbbbf9ffb1c173aa83964b7cf539304373636525"
136 "3ddbc5db8778371495da76d269e5db3e",
137 "291ef1982e4defedaa2249f898556b47"
138 },
139 { "ec0c2ba17aa95cd6afffe949da9cc3a8",
140 "296bce5b50b7d66096d627ef",
141 "b85b3753535b825cbe5f632c0b843c741351f18aa484281aebec2f45bb9eea2d79d987"
142 "b764b9611f6c0f8641843d5d58f3a242",
143 "f8d00f05d22bf68599bcdeb131292ad6e2df5d14",
144 "a7443d31c26bdf2a1c945e29ee4bd344a99cfaf3aa71f8b3f191f83c2adfc7a0716299"
145 "5506fde6309ffc19e716eddf1a828c5a",
146 "890147971946b627c40016da1ecf3e77"
147 },
148 { NULL }
149 };
150
151 const TestVector test_group_4[] = {
152 { "2c1f21cf0f6fb3661943155c3e3d8492",
153 "23cb5ff362e22426984d1907",
154 "42f758836986954db44bf37c6ef5e4ac0adaf38f27252a1b82d02ea949c8a1a2dbc0d6"
155 "8b5615ba7c1220ff6510e259f06655d8",
156 "5d3624879d35e46849953e45a32a624d6a6c536ed9857c613b572b0333e701557a713e"
157 "3f010ecdf9a6bd6c9e3e44b065208645aff4aabee611b391528514170084ccf587177f"
158 "4488f33cfb5e979e42b6e1cfc0a60238982a7aec",
159 "81824f0e0d523db30d3da369fdc0d60894c7a0a20646dd015073ad2732bd989b14a222"
160 "b6ad57af43e1895df9dca2a5344a62cc",
161 "57a3ee28136e94c74838997ae9823f3a"
162 },
163 { "d9f7d2411091f947b4d6f1e2d1f0fb2e",
164 "e1934f5db57cc983e6b180e7",
165 "73ed042327f70fe9c572a61545eda8b2a0c6e1d6c291ef19248e973aee6c312012f490"
166 "c2c6f6166f4a59431e182663fcaea05a",
167 "0a8a18a7150e940c3d87b38e73baee9a5c049ee21795663e264b694a949822b639092d"
168 "0e67015e86363583fcf0ca645af9f43375f05fdb4ce84f411dcbca73c2220dea03a201"
169 "15d2e51398344b16bee1ed7c499b353d6c597af8",
170 "aaadbd5c92e9151ce3db7210b8714126b73e43436d242677afa50384f2149b831f1d57"
171 "3c7891c2a91fbc48db29967ec9542b23",
172 "21b51ca862cb637cdd03b99a0f93b134"
173 },
174 { NULL }
175 };
176
177 const TestVector test_group_5[] = {
178 { "fe9bb47deb3a61e423c2231841cfd1fb",
179 "4d328eb776f500a2f7fb47aa",
180 "f1cc3818e421876bb6b8bbd6c9",
181 "",
182 "b88c5c1977b35b517b0aeae967",
183 "43fd4727fe5cdb4b5b42818dea7ef8c9"
184 },
185 { "6703df3701a7f54911ca72e24dca046a",
186 "12823ab601c350ea4bc2488c",
187 "793cd125b0b84a043e3ac67717",
188 "",
189 "b2051c80014f42f08735a7b0cd",
190 "38e6bcd29962e5f2c13626b85a877101"
191 },
192 { NULL }
193 };
194
195 const TestVector* const test_group_array[] = {
196 test_group_0,
197 test_group_1,
198 test_group_2,
199 test_group_3,
200 test_group_4,
201 test_group_5,
202 };
203
204 // Returns true if |ch| is a lowercase hexadecimal digit.
205 bool IsHexDigit(char ch) {
206 return ('0' <= ch && ch <= '9') || ('a' <= ch && ch <= 'f');
207 }
208
209 // Converts a lowercase hexadecimal digit to its integer value.
210 int HexDigitToInt(char ch) {
211 if ('0' <= ch && ch <= '9') {
212 return ch - '0';
213 }
214 return ch - 'a' + 10;
215 }
216
217 // |in| is a string consisting of lowercase hexadecimal digits, where
218 // every two digits represent one byte. |out| is a buffer of size |max_len|.
219 // Converts |in| to bytes and stores the bytes in the |out| buffer. The
220 // number of bytes converted is returned in |*out_len|. Returns true on
221 // success, false on failure.
222 bool DecodeHexString(const char* in,
223 char* out,
224 size_t* out_len,
225 size_t max_len) {
226 *out_len = 0;
227 while (*in != '\0') {
228 if (!IsHexDigit(*in) || !IsHexDigit(*(in + 1))) {
229 return false;
230 }
231 if (*out_len >= max_len) {
232 return false;
233 }
234 out[*out_len] = HexDigitToInt(*in) * 16 + HexDigitToInt(*(in + 1));
235 (*out_len)++;
236 in += 2;
237 }
238 return true;
239 }
240
241 } // namespace
242
243 namespace net {
244 namespace test {
245
246 class Aes128GcmEncrypterPeer {
247 public:
248 static QuicData* Encrypt(Aes128GcmEncrypter* encrypter,
249 StringPiece nonce,
250 StringPiece associated_data,
251 StringPiece plaintext) {
252 return encrypter->EncryptWithNonce(nonce, associated_data, plaintext);
253 }
254 };
255
256 TEST(Aes128GcmEncrypterTest, Encrypt) {
257 if (!Aes128GcmEncrypter::IsSupported()) {
258 LOG(INFO) << "AES GCM not supported. Test skipped.";
259 return;
260 }
261
262 char key[1024];
263 size_t key_len;
264 char iv[1024];
265 size_t iv_len;
266 char pt[1024];
267 size_t pt_len;
268 char aad[1024];
269 size_t aad_len;
270 char ct[1024];
271 size_t ct_len;
272 char tag[1024];
273 size_t tag_len;
274
275 for (size_t i = 0; i < arraysize(test_group_array); i++) {
276 const TestVector* test_vector = test_group_array[i];
277 const TestGroupInfo& test_info = test_group_info[i];
278 for (size_t j = 0; test_vector[j].key != NULL; j++) {
279 // Decode the test vector.
280 ASSERT_TRUE(DecodeHexString(test_vector[j].key, key, &key_len,
281 sizeof(key)));
282 ASSERT_TRUE(DecodeHexString(test_vector[j].iv, iv, &iv_len,
283 sizeof(iv)));
284 ASSERT_TRUE(DecodeHexString(test_vector[j].pt, pt, &pt_len,
285 sizeof(pt)));
286 ASSERT_TRUE(DecodeHexString(test_vector[j].aad, aad, &aad_len,
287 sizeof(aad)));
288 ASSERT_TRUE(DecodeHexString(test_vector[j].ct, ct, &ct_len,
289 sizeof(ct)));
290 ASSERT_TRUE(DecodeHexString(test_vector[j].tag, tag, &tag_len,
291 sizeof(tag)));
292
293 // The test vector's lengths should look sane. Note that the lengths
294 // in |test_info| are in bits.
295 EXPECT_EQ(test_info.key_len, key_len * 8);
296 EXPECT_EQ(test_info.iv_len, iv_len * 8);
297 EXPECT_EQ(test_info.pt_len, pt_len * 8);
298 EXPECT_EQ(test_info.aad_len, aad_len * 8);
299 EXPECT_EQ(test_info.pt_len, ct_len * 8);
300 EXPECT_EQ(test_info.tag_len, tag_len * 8);
301
302 Aes128GcmEncrypter encrypter;
303 ASSERT_TRUE(encrypter.SetKey(StringPiece(key, key_len)));
304 scoped_ptr<QuicData> encrypted(Aes128GcmEncrypterPeer::Encrypt(
305 &encrypter, StringPiece(iv, iv_len), StringPiece(aad, aad_len),
306 StringPiece(pt, pt_len)));
307 ASSERT_TRUE(encrypted.get());
308 ASSERT_EQ(ct_len + tag_len, encrypted->length());
309 test::CompareCharArraysWithHexError(
310 "ciphertext", encrypted->data(), ct_len,
311 ct, ct_len);
312 test::CompareCharArraysWithHexError(
313 "authentication tag", encrypted->data() + ct_len, tag_len,
314 tag, tag_len);
315 }
316 }
317 }
318
319 TEST(Aes128GcmEncrypterTest, GetMaxPlaintextSize) {
320 Aes128GcmEncrypter encrypter;
321 EXPECT_EQ(1000u, encrypter.GetMaxPlaintextSize(1016));
322 EXPECT_EQ(100u, encrypter.GetMaxPlaintextSize(116));
323 EXPECT_EQ(10u, encrypter.GetMaxPlaintextSize(26));
324 }
325
326 TEST(Aes128GcmEncrypterTest, GetCiphertextSize) {
327 Aes128GcmEncrypter encrypter;
328 EXPECT_EQ(1016u, encrypter.GetCiphertextSize(1000));
329 EXPECT_EQ(116u, encrypter.GetCiphertextSize(100));
330 EXPECT_EQ(26u, encrypter.GetCiphertextSize(10));
331 }
332
333 } // namespace test
334 } // namespace net
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698