2 // Rfc2898DeriveBytesTest.cs - NUnit Test Cases for Rfc2898DeriveBytes
5 // Sebastien Pouliot <spouliot@ximian.com>
7 // (C) 2003 Motus Technologies Inc. (http://www.motus.com)
8 // Copyright (C) 2004 Novell, Inc (http://www.novell.com)
10 // Permission is hereby granted, free of charge, to any person obtaining
11 // a copy of this software and associated documentation files (the
12 // "Software"), to deal in the Software without restriction, including
13 // without limitation the rights to use, copy, modify, merge, publish,
14 // distribute, sublicense, and/or sell copies of the Software, and to
15 // permit persons to whom the Software is furnished to do so, subject to
16 // the following conditions:
18 // The above copyright notice and this permission notice shall be
19 // included in all copies or substantial portions of the Software.
21 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
22 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
23 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
24 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
25 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
26 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
27 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
32 using NUnit
.Framework
;
35 using System
.Security
.Cryptography
;
37 namespace MonoTests
.System
.Security
.Cryptography
{
40 // a. PKCS#5: Password-Based Cryptography Standard
41 // http://www.rsasecurity.com/rsalabs/pkcs/pkcs-5/index.html
42 // b. RFC 3211 - Password-based Encryption for CMS
43 // http://www.faqs.org/rfcs/rfc3211.html
46 public class Rfc2898DeriveBytesTest
: Assertion
{
48 public void AssertEquals (string msg
, byte[] array1
, byte[] array2
)
50 AllTests
.AssertEquals (msg
, array1
, array2
);
53 static private byte[] salt
= { 0x12, 0x34, 0x56, 0x78, 0x78, 0x56, 0x34, 0x12 }
;
56 public void ConstructorPasswordSalt ()
58 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
);
59 AssertEquals ("IterationCount", 1000, pkcs5
.IterationCount
);
60 AssertEquals ("Salt", salt
, pkcs5
.Salt
);
64 [ExpectedException (typeof (ArgumentNullException
))]
65 public void ConstructorPasswordNullSalt ()
67 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes (null, salt
);
71 [ExpectedException (typeof (ArgumentNullException
))]
72 public void ConstructorPasswordSaltNull ()
74 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", null);
78 public void ConstructorPasswordSaltIterations ()
80 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
, 5);
81 AssertEquals ("IterationCount", 5, pkcs5
.IterationCount
);
82 AssertEquals ("Salt", salt
, pkcs5
.Salt
);
86 [ExpectedException (typeof (ArgumentNullException
))]
87 public void ConstructorPasswordNullSaltIterations ()
89 string password
= null;
90 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes (password
, salt
, 5);
94 [ExpectedException (typeof (ArgumentNullException
))]
95 public void ConstructorPasswordSaltNullIterations ()
97 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", null, 5);
101 [ExpectedException (typeof (ArgumentOutOfRangeException
))]
102 public void ConstructorPasswordSaltIterationsZero ()
104 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
, 0);
108 [ExpectedException (typeof (ArgumentOutOfRangeException
))]
109 public void ConstructorPasswordSaltIterationsNegative ()
111 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
, Int32
.MinValue
);
115 public void ConstructorPasswordSaltLength ()
117 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", 8);
118 AssertEquals ("IterationCount", 1000, pkcs5
.IterationCount
);
119 AssertEquals ("Salt", 8, pkcs5
.Salt
.Length
);
123 [ExpectedException (typeof (ArgumentNullException
))]
124 public void ConstructorPasswordNullSaltLength ()
126 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes (null, 8);
130 [ExpectedException (typeof (ArgumentException
))]
131 public void ConstructorPasswordSaltLengthZero ()
133 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", 0);
137 [ExpectedException (typeof (ArgumentOutOfRangeException
))]
138 public void ConstructorPasswordSaltLengthNegative ()
140 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", Int32
.MinValue
);
144 public void ConstructorPasswordSaltLengthIterations ()
146 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", 8, 5);
147 AssertEquals ("IterationCount", 5, pkcs5
.IterationCount
);
148 AssertEquals ("Salt", 8, pkcs5
.Salt
.Length
);
152 [ExpectedException (typeof (ArgumentNullException
))]
153 public void ConstructorPasswordNullSaltLengthIterations ()
155 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes (null, 8, 5);
159 [ExpectedException (typeof (ArgumentException
))]
160 public void ConstructorPasswordSaltLengthZeroIterations ()
162 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", 0, 5);
166 [ExpectedException (typeof (ArgumentOutOfRangeException
))]
167 public void ConstructorPasswordSaltLengthNegativeIterations ()
169 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", Int32
.MinValue
, 5);
173 [ExpectedException (typeof (ArgumentOutOfRangeException
))]
174 public void ConstructorPasswordSaltLengthIterationsZero ()
176 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", 8, 0);
180 [ExpectedException (typeof (ArgumentOutOfRangeException
))]
181 public void ConstructorPasswordSaltLengthIterationsNegative ()
183 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", 8, Int32
.MinValue
);
187 public void IterationCount ()
189 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
, 5);
190 AssertEquals ("IterationCount", 5, pkcs5
.IterationCount
);
191 pkcs5
.IterationCount
= Int32
.MaxValue
;
192 AssertEquals ("IterationCount", Int32
.MaxValue
, pkcs5
.IterationCount
);
196 public void SaltNew ()
198 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
);
199 AssertEquals ("Salt", salt
, pkcs5
.Salt
);
200 byte[] newSalt
= (byte[]) salt
.Clone ();
202 pkcs5
.Salt
= newSalt
;
203 AssertEquals ("Salt(new)", newSalt
, pkcs5
.Salt
);
207 public void SaltCantModifyInternal ()
209 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
);
210 AssertEquals ("Salt", salt
, pkcs5
.Salt
);
211 byte[] modSalt
= (byte[]) salt
.Clone ();
213 Assert ("Can't modify internal salt", (BitConverter
.ToString(pkcs5
.Salt
) != BitConverter
.ToString(modSalt
)));
217 [ExpectedException (typeof (ArgumentNullException
))]
218 public void SaltNull ()
220 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
);
225 [ExpectedException (typeof (ArgumentException
))]
226 public void SaltTooSmall ()
228 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
);
229 byte[] smallSalt
= { 0x01, 0x02, 0x03, 0x04, 0x05 }
;
230 pkcs5
.Salt
= smallSalt
;
234 [ExpectedException (typeof (ArgumentOutOfRangeException
))]
235 public void GetBytesZero ()
237 byte[] expected
= { 0xd1, 0xda, 0xa7, 0x86, 0x15, 0xf2, 0x87, 0xe6 }
;
238 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
, 5);
239 byte[] key
= pkcs5
.GetBytes (0);
240 AssertEquals ("GetBytesZero", 0, key
.Length
);
244 [ExpectedException (typeof (ArgumentOutOfRangeException
))]
245 public void GetBytesNegative ()
247 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
, 5);
248 byte[] key
= pkcs5
.GetBytes (Int32
.MinValue
);
252 public void RFC3211_TC1 ()
254 byte[] expected
= { 0xd1, 0xda, 0xa7, 0x86, 0x15, 0xf2, 0x87, 0xe6 }
;
255 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("password", salt
, 5);
256 byte[] key
= pkcs5
.GetBytes (8);
257 AssertEquals ("RFC3211_TC1", expected
, key
);
261 public void RFC3211_TC2 ()
263 byte[] expected
= { 0x6A, 0x89, 0x70, 0xBF, 0x68, 0xC9, 0x2C, 0xAE, 0xA8, 0x4A, 0x8D, 0xF2, 0x85, 0x10, 0x85, 0x86 }
;
264 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("All n-entities must communicate with other n-entities via n-1 entiteeheehees", salt
, 500);
265 byte[] key
= pkcs5
.GetBytes (16);
266 AssertEquals ("RFC3211_TC2", expected
, key
);
270 public void RFC3211_TC2_TwoBlocks ()
272 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 }
;
273 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("All n-entities must communicate with other n-entities via n-1 entiteeheehees", salt
, 500);
274 byte[] key
= pkcs5
.GetBytes (32);
275 AssertEquals ("RFC3211_TC2_TwoBlocks", expected
, key
);
279 public void RFC3211_TC2_Splitted_OneBlock ()
281 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("All n-entities must communicate with other n-entities via n-1 entiteeheehees", salt
, 500);
282 byte[] key1
= pkcs5
.GetBytes (8);
283 byte[] expected_part1
= { 0x6A, 0x89, 0x70, 0xBF, 0x68, 0xC9, 0x2C, 0xAE }
;
284 AssertEquals ("RFC3211_TC2_Splitted_OneBlock-1", expected_part1
, key1
);
285 byte[] expected_part2
= { 0xA8, 0x4A, 0x8D, 0xF2, 0x85, 0x10, 0x85, 0x86 }
;
286 byte[] key2
= pkcs5
.GetBytes (8);
287 AssertEquals ("RFC3211_TC2_Splitted_OneBlock-2", expected_part2
, key2
);
291 public void RFC3211_TC2_Splitted_TwoBlocks ()
293 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("All n-entities must communicate with other n-entities via n-1 entiteeheehees", salt
, 500);
294 byte[] key1
= pkcs5
.GetBytes (16);
295 byte[] expected_part1
= { 0x6A, 0x89, 0x70, 0xBF, 0x68, 0xC9, 0x2C, 0xAE, 0xA8, 0x4A, 0x8D, 0xF2, 0x85, 0x10, 0x85, 0x86 }
;
296 AssertEquals ("RFC3211_TC2_Splitted_TwoBlocks-1", expected_part1
, key1
);
297 byte[] expected_part2
= { 0x07, 0x12, 0x63, 0x80, 0xcc, 0x47, 0xab, 0x2d, 0xa6, 0xcc, 0xda, 0xfb, 0x26, 0x83, 0xdf, 0xe8 }
;
298 byte[] key2
= pkcs5
.GetBytes (16);
299 AssertEquals ("RFC3211_TC2_Splitted_TwoBlocks-2", expected_part2
, key2
);
303 public void RFC3211_TC2_Reset ()
305 byte[] expected
= { 0x6A, 0x89, 0x70, 0xBF, 0x68, 0xC9, 0x2C, 0xAE }
;
306 Rfc2898DeriveBytes pkcs5
= new Rfc2898DeriveBytes ("All n-entities must communicate with other n-entities via n-1 entiteeheehees", salt
, 500);
307 byte[] key1
= pkcs5
.GetBytes (8);
308 AssertEquals ("RFC3211_TC2_part1", expected
, key1
);
310 byte[] key2
= pkcs5
.GetBytes (8);
311 AssertEquals ("RFC3211_TC2_part2", expected
, key2
);