2 // Rfc2898DeriveBytesTest.cs - NUnit Test Cases for Rfc2898DeriveBytes
5 // Sebastien Pouliot (spouliot@motus.com)
7 // (C) 2003 Motus Technologies Inc. (http://www.motus.com)
12 using NUnit.Framework;
15 using System.Security.Cryptography;
17 namespace MonoTests.System.Security.Cryptography {
20 // a. PKCS#5: Password-Based Cryptography Standard
21 // http://www.rsasecurity.com/rsalabs/pkcs/pkcs-5/index.html
22 // b. RFC 3211 - Password-based Encryption for CMS
23 // http://www.faqs.org/rfcs/rfc3211.html
26 public class Rfc2898DeriveBytesTest : Assertion {
28 public void AssertEquals (string msg, byte[] array1, byte[] array2)
30 AllTests.AssertEquals (msg, array1, array2);
33 static private byte[] salt = { 0x12, 0x34, 0x56, 0x78, 0x78, 0x56, 0x34, 0x12 };
36 public void ConstructorPasswordSalt ()
38 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt);
39 AssertEquals ("IterationCount", 1000, pkcs5.IterationCount);
40 AssertEquals ("Salt", salt, pkcs5.Salt);
44 [ExpectedException (typeof (ArgumentNullException))]
45 public void ConstructorPasswordNullSalt ()
47 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes (null, salt);
51 [ExpectedException (typeof (ArgumentNullException))]
52 public void ConstructorPasswordSaltNull ()
54 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", null);
58 public void ConstructorPasswordSaltIterations ()
60 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt, 5);
61 AssertEquals ("IterationCount", 5, pkcs5.IterationCount);
62 AssertEquals ("Salt", salt, pkcs5.Salt);
66 [ExpectedException (typeof (ArgumentNullException))]
67 public void ConstructorPasswordNullSaltIterations ()
69 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes (null, salt, 5);
73 [ExpectedException (typeof (ArgumentNullException))]
74 public void ConstructorPasswordSaltNullIterations ()
76 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", null, 5);
80 [ExpectedException (typeof (ArgumentOutOfRangeException))]
81 public void ConstructorPasswordSaltIterationsZero ()
83 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt, 0);
87 [ExpectedException (typeof (ArgumentOutOfRangeException))]
88 public void ConstructorPasswordSaltIterationsNegative ()
90 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt, Int32.MinValue);
94 public void ConstructorPasswordSaltLength ()
96 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", 8);
97 AssertEquals ("IterationCount", 1000, pkcs5.IterationCount);
98 AssertEquals ("Salt", 8, pkcs5.Salt.Length);
102 [ExpectedException (typeof (ArgumentNullException))]
103 public void ConstructorPasswordNullSaltLength ()
105 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes (null, 8);
109 [ExpectedException (typeof (ArgumentException))]
110 public void ConstructorPasswordSaltLengthZero ()
112 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", 0);
116 [ExpectedException (typeof (ArgumentOutOfRangeException))]
117 public void ConstructorPasswordSaltLengthNegative ()
119 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", Int32.MinValue);
123 public void ConstructorPasswordSaltLengthIterations ()
125 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", 8, 5);
126 AssertEquals ("IterationCount", 5, pkcs5.IterationCount);
127 AssertEquals ("Salt", 8, pkcs5.Salt.Length);
131 [ExpectedException (typeof (ArgumentNullException))]
132 public void ConstructorPasswordNullSaltLengthIterations ()
134 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes (null, 8, 5);
138 [ExpectedException (typeof (ArgumentException))]
139 public void ConstructorPasswordSaltLengthZeroIterations ()
141 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", 0, 5);
145 [ExpectedException (typeof (ArgumentOutOfRangeException))]
146 public void ConstructorPasswordSaltLengthNegativeIterations ()
148 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", Int32.MinValue, 5);
152 [ExpectedException (typeof (ArgumentOutOfRangeException))]
153 public void ConstructorPasswordSaltLengthIterationsZero ()
155 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", 8, 0);
159 [ExpectedException (typeof (ArgumentOutOfRangeException))]
160 public void ConstructorPasswordSaltLengthIterationsNegative ()
162 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", 8, Int32.MinValue);
166 public void IterationCount ()
168 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt, 5);
169 AssertEquals ("IterationCount", 5, pkcs5.IterationCount);
170 pkcs5.IterationCount = Int32.MaxValue;
171 AssertEquals ("IterationCount", Int32.MaxValue, pkcs5.IterationCount);
175 public void SaltNew ()
177 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt);
178 AssertEquals ("Salt", salt, pkcs5.Salt);
179 byte[] newSalt = (byte[]) salt.Clone ();
181 pkcs5.Salt = newSalt;
182 AssertEquals ("Salt(new)", newSalt, pkcs5.Salt);
186 public void SaltCantModifyInternal ()
188 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt);
189 AssertEquals ("Salt", salt, pkcs5.Salt);
190 byte[] modSalt = (byte[]) salt.Clone ();
192 Assert ("Can't modify internal salt", (BitConverter.ToString(pkcs5.Salt) != BitConverter.ToString(modSalt)));
196 [ExpectedException (typeof (ArgumentNullException))]
197 public void SaltNull ()
199 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt);
204 [ExpectedException (typeof (ArgumentException))]
205 public void SaltTooSmall ()
207 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt);
208 byte[] smallSalt = { 0x01, 0x02, 0x03, 0x04, 0x05 };
209 pkcs5.Salt = smallSalt;
213 [ExpectedException (typeof (ArgumentOutOfRangeException))]
214 public void GetBytesZero ()
216 byte[] expected = { 0xd1, 0xda, 0xa7, 0x86, 0x15, 0xf2, 0x87, 0xe6 };
217 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt, 5);
218 byte[] key = pkcs5.GetBytes (0);
219 AssertEquals ("GetBytesZero", 0, key.Length);
223 [ExpectedException (typeof (ArgumentOutOfRangeException))]
224 public void GetBytesNegative ()
226 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt, 5);
227 byte[] key = pkcs5.GetBytes (Int32.MinValue);
231 public void RFC3211_TC1 ()
233 byte[] expected = { 0xd1, 0xda, 0xa7, 0x86, 0x15, 0xf2, 0x87, 0xe6 };
234 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("password", salt, 5);
235 byte[] key = pkcs5.GetBytes (8);
236 AssertEquals ("RFC3211_TC1", expected, key);
240 public void RFC3211_TC2 ()
242 byte[] expected = { 0x6A, 0x89, 0x70, 0xBF, 0x68, 0xC9, 0x2C, 0xAE, 0xA8, 0x4A, 0x8D, 0xF2, 0x85, 0x10, 0x85, 0x86 };
243 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("All n-entities must communicate with other n-entities via n-1 entiteeheehees", salt, 500);
244 byte[] key = pkcs5.GetBytes (16);
245 AssertEquals ("RFC3211_TC2", expected, key);
249 public void RFC3211_TC2_TwoBlocks ()
251 byte[] expected = { 0x6A, 0x89, 0x70, 0xBF, 0x68, 0xC9, 0x2C, 0xAE, 0xA8, 0x4A, 0x8D, 0xF2, 0x85, 0x10, 0x85, 0x86, 0x07, 0x12, 0x63, 0x80, 0xcc, 0x47, 0xab, 0x2d, 0xa6, 0xcc, 0xda, 0xfb, 0x26, 0x83, 0xdf, 0xe8 };
252 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("All n-entities must communicate with other n-entities via n-1 entiteeheehees", salt, 500);
253 byte[] key = pkcs5.GetBytes (32);
254 AssertEquals ("RFC3211_TC2_TwoBlocks", expected, key);
258 public void RFC3211_TC2_Splitted_OneBlock ()
260 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("All n-entities must communicate with other n-entities via n-1 entiteeheehees", salt, 500);
261 byte[] key1 = pkcs5.GetBytes (8);
262 byte[] expected_part1 = { 0x6A, 0x89, 0x70, 0xBF, 0x68, 0xC9, 0x2C, 0xAE };
263 AssertEquals ("RFC3211_TC2_Splitted_OneBlock-1", expected_part1, key1);
264 byte[] expected_part2 = { 0xA8, 0x4A, 0x8D, 0xF2, 0x85, 0x10, 0x85, 0x86 };
265 byte[] key2 = pkcs5.GetBytes (8);
266 AssertEquals ("RFC3211_TC2_Splitted_OneBlock-2", expected_part2, key2);
270 public void RFC3211_TC2_Splitted_TwoBlocks ()
272 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("All n-entities must communicate with other n-entities via n-1 entiteeheehees", salt, 500);
273 byte[] key1 = pkcs5.GetBytes (16);
274 byte[] expected_part1 = { 0x6A, 0x89, 0x70, 0xBF, 0x68, 0xC9, 0x2C, 0xAE, 0xA8, 0x4A, 0x8D, 0xF2, 0x85, 0x10, 0x85, 0x86 };
275 AssertEquals ("RFC3211_TC2_Splitted_TwoBlocks-1", expected_part1, key1);
276 byte[] expected_part2 = { 0x07, 0x12, 0x63, 0x80, 0xcc, 0x47, 0xab, 0x2d, 0xa6, 0xcc, 0xda, 0xfb, 0x26, 0x83, 0xdf, 0xe8 };
277 byte[] key2 = pkcs5.GetBytes (16);
278 AssertEquals ("RFC3211_TC2_Splitted_TwoBlocks-2", expected_part2, key2);
282 public void RFC3211_TC2_Reset ()
284 byte[] expected = { 0x6A, 0x89, 0x70, 0xBF, 0x68, 0xC9, 0x2C, 0xAE };
285 Rfc2898DeriveBytes pkcs5 = new Rfc2898DeriveBytes ("All n-entities must communicate with other n-entities via n-1 entiteeheehees", salt, 500);
286 byte[] key1 = pkcs5.GetBytes (8);
287 AssertEquals ("RFC3211_TC2_part1", expected, key1);
289 byte[] key2 = pkcs5.GetBytes (8);
290 AssertEquals ("RFC3211_TC2_part2", expected, key2);