1 //
2 // RegistryKeyTest.cs - NUnit Test Cases for Microsoft.Win32.RegistryKey
3 //
4 // Authors:
5 //	mei (mei@work.email.ne.jp)
6 //	Robert Jordan (robertj@gmx.net)
7 //	Gert Driesen (drieseng@users.sourceforge.net)
8 //
9 // (C) 2005 mei
10 // (C) 2004, 2005 Novell (http://www.novell.com)
11 //
12 
13 using System;
14 using System.IO;
15 using System.Runtime.InteropServices;
16 
17 using Microsoft.Win32;
18 using Microsoft.Win32.SafeHandles;
19 
20 using NUnit.Framework;
21 
22 namespace MonoTests.Microsoft.Win32
23 {
24 	[TestFixture]
25 	public class RegistryKeyTest
26 	{
27 		private const string mimeroot = @"MIME\Database\Content Type";
28 
29 		[Test]
30 		[Category ("NotWorking")] // this will not work on Linux ever
TestGetValue()31 		public void TestGetValue ()
32 		{
33 			RegistryKey root = Registry.ClassesRoot;
34 			RegistryKey key;
35 
36 			key = root.OpenSubKey (mimeroot + @"\audio/wav");
37 			Assert.AreEqual (".wav", key.GetValue ("Extension"), "GetValue #1");
38 			key = root.OpenSubKey (mimeroot + @"\text/x-scriptlet");
39 			Assert.AreEqual (null, key.GetValue ("Extension"), "GetValue #2");
40 		}
41 
42 		[Test] // bug #77212
TestHandle()43 		public void TestHandle ()
44 		{
45 			// this test is for Windows only
46 			if (RunningOnUnix)
47 				Assert.Ignore ("Running on Unix.");
48 
49 			// this regpath always exists under windows
50 			RegistryKey k = Registry.CurrentUser
51 				.OpenSubKey ("Software", false)
52 				.OpenSubKey ("Microsoft", false)
53 				.OpenSubKey ("Windows", false);
54 
55 			Assert.IsNotNull (k, "#01");
56 		}
57 
58 		[Test]
OpenSubKey()59 		public void OpenSubKey ()
60 		{
61 			RegistryKey key = Registry.LocalMachine;
62 
63 			// HKEY_LOCAL_MACHINE\software should always exist on Windows
64 			// and is automatically created on Linux
65 			Assert.IsNotNull (key.OpenSubKey ("Software"), "#A1");
66 			Assert.IsNotNull (key.OpenSubKey ("soFtware"), "#A2");
67 
68 			key = Registry.CurrentUser;
69 
70 			// HKEY_CURRENT_USER\software should always exist on Windows
71 			// and is automatically created on Linux
72 			Assert.IsNotNull (key.OpenSubKey ("Software"), "#B1");
73 			Assert.IsNotNull (key.OpenSubKey ("soFtware"), "#B2");
74 
75 			key = Registry.Users;
76 
77 			// HKEY_USERS\software should not exist on Windows, and should not
78 			// be created automatically on Linux
79 			Assert.IsNull (key.OpenSubKey ("Software"), "#C1");
80 			Assert.IsNull (key.OpenSubKey ("soFtware"), "#C2");
81 		}
82 
83 		[Test]
OpenSubKey_Key_DoesNotExist()84 		public void OpenSubKey_Key_DoesNotExist ()
85 		{
86 			string subKeyName = Guid.NewGuid ().ToString ();
87 			Assert.IsNull (Registry.CurrentUser.OpenSubKey (subKeyName), "#1"); // read-only
88 			Assert.IsNull (Registry.CurrentUser.OpenSubKey (subKeyName, true), "#2"); // writable
89 		}
90 
91 		[Test]
OpenSubKey_Key_Removed()92 		public void OpenSubKey_Key_Removed ()
93 		{
94 			string subKeyName = Guid.NewGuid ().ToString ();
95 
96 			try {
97 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
98 					// check if key was successfully created
99 					Assert.IsNotNull (createdKey, "#1");
100 					RegistryKey subKey = createdKey.CreateSubKey ("monotemp");
101 					subKey.Close ();
102 				}
103 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName, true)) {
104 					Assert.IsNotNull (createdKey, "#2");
105 					using (RegistryKey subKey = createdKey.OpenSubKey ("monotemp")) {
106 						Assert.IsNotNull (createdKey, "#3");
107 					}
108 					Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
109 
110 					// read-only
111 					Assert.IsNull (Registry.CurrentUser.OpenSubKey (subKeyName), "#4");
112 					Assert.IsNull (createdKey.OpenSubKey ("monotemp"), "#5"); // read-only
113 					// writable
114 					Assert.IsNull (Registry.CurrentUser.OpenSubKey (subKeyName, true), "#6");
115 					Assert.IsNull (createdKey.OpenSubKey ("monotemp", true), "#7");
116 				}
117 			} finally {
118 				try {
119 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
120 					if (createdKey != null) {
121 						createdKey.Close ();
122 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
123 					}
124 				} catch {
125 				}
126 			}
127 		}
128 
129 		[Test]
130 		[Category ("NotWorking")] // MS should not allow this
OpenSubKey_Name_Empty()131 		public void OpenSubKey_Name_Empty ()
132 		{
133 			// read-only
134 			using (RegistryKey emptyKey = Registry.CurrentUser.OpenSubKey (string.Empty)) {
135 				Assert.IsNotNull (emptyKey, "#1");
136 			}
137 			// writable
138 			using (RegistryKey emptyKey = Registry.CurrentUser.OpenSubKey (string.Empty, true)) {
139 				Assert.IsNotNull (emptyKey, "#1");
140 			}
141 		}
142 
143 		[Test]
OpenSubKey_Name_MaxLength()144 		public void OpenSubKey_Name_MaxLength ()
145 		{
146 			string name = new string ('a', 254);
147 
148 			Assert.IsNull (Registry.CurrentUser.OpenSubKey (name), "#A1");
149 
150 			name = new string ('a', 255);
151 
152 			Assert.IsNull (Registry.CurrentUser.OpenSubKey (name), "#B1");
153 
154 			name = new string ('a', 256);
155 
156 			try {
157 				Registry.CurrentUser.OpenSubKey (name);
158 				Assert.Fail ("#C1");
159 			} catch (ArgumentException ex) {
160 				// 1.x: Registry subkeys should not be
161 				// greater than or equal to 255 characters
162 				//
163 				// 2.x: Registry subkeys should not be
164 				// greater than 255 characters
165 				Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#C2");
166 				Assert.IsNull (ex.InnerException, "#C3");
167 				Assert.IsNotNull (ex.Message, "#c4");
168 				Assert.IsTrue (ex.Message.IndexOf ("255") != -1, "#C5");
169 				Assert.IsNull (ex.ParamName, "#C6");
170 			}
171 		}
172 
173 		[Test]
OpenSubKey_Name_Null()174 		public void OpenSubKey_Name_Null ()
175 		{
176 			try {
177 				Registry.CurrentUser.OpenSubKey (null);
178 				Assert.Fail ("#A1");
179 			} catch (ArgumentNullException ex) {
180 				Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#A2");
181 				Assert.IsNull (ex.InnerException, "#A3");
182 				Assert.IsNotNull (ex.Message, "#A4");
183 				Assert.AreEqual ("name", ex.ParamName, "#A5");
184 			}
185 
186 			try {
187 				Registry.CurrentUser.OpenSubKey (null, true);
188 				Assert.Fail ("#B1");
189 			} catch (ArgumentNullException ex) {
190 				Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#B2");
191 				Assert.IsNull (ex.InnerException, "#B3");
192 				Assert.IsNotNull (ex.Message, "#B4");
193 				Assert.AreEqual ("name", ex.ParamName, "#B5");
194 			}
195 		}
196 
197 		[Test]
Close_Local_Hive()198 		public void Close_Local_Hive ()
199 		{
200 			RegistryKey hive = Registry.CurrentUser;
201 			hive.Close ();
202 
203 			Assert.IsNotNull (hive.GetSubKeyNames (), "#1");
204 			Assert.IsNull (hive.GetValue ("doesnotexist"), "#2");
205 			Assert.IsNotNull (hive.GetValueNames (), "#3");
206 			Assert.IsNull (hive.OpenSubKey ("doesnotexist"), "#4");
207 			Assert.IsNotNull (hive.SubKeyCount, "#5");
208 			Assert.IsNotNull (hive.ToString (), "#6");
209 
210 			// closing key again does not have any effect
211 			hive.Close ();
212 		}
213 
214 		[Test]
Close_Local_Key()215 		public void Close_Local_Key ()
216 		{
217 			RegistryKey key = Registry.CurrentUser.OpenSubKey ("SOFTWARE");
218 			key.Close ();
219 
220 			// closing a key twice does not have any effect
221 			key.Close ();
222 
223 			try {
224 				key.CreateSubKey ("a");
225 				Assert.Fail ("#1");
226 			} catch (ObjectDisposedException) {
227 			}
228 
229 			try {
230 				key.DeleteSubKey ("doesnotexist");
231 				Assert.Fail ("#2");
232 			} catch (ObjectDisposedException) {
233 			}
234 
235 			try {
236 				key.DeleteSubKeyTree ("doesnotexist");
237 				Assert.Fail ("#3");
238 			} catch (ObjectDisposedException) {
239 			}
240 
241 			try {
242 				key.DeleteValue ("doesnotexist");
243 				Assert.Fail ("#4");
244 			} catch (ObjectDisposedException) {
245 			}
246 
247 			// flushing a closed key does not have any effect
248 			key.Flush ();
249 
250 			try {
251 				key.GetSubKeyNames ();
252 				Assert.Fail ("#5");
253 			} catch (ObjectDisposedException) {
254 			}
255 
256 			try {
257 				key.GetValue ("doesnotexist");
258 				Assert.Fail ("#6");
259 			} catch (ObjectDisposedException) {
260 			}
261 
262 			try {
263 				key.GetValueNames ();
264 				Assert.Fail ("#7");
265 			} catch (ObjectDisposedException) {
266 			}
267 
268 			try {
269 				key.OpenSubKey ("doesnotexist");
270 				Assert.Fail ("#8");
271 			} catch (ObjectDisposedException) {
272 			}
273 
274 			try {
275 				key.SetValue ("doesnotexist", "something");
276 				Assert.Fail ("#9");
277 			} catch (ObjectDisposedException) {
278 			}
279 
280 			try {
281 				int x = key.SubKeyCount;
282 				Assert.Fail ("#10:" + x);
283 			} catch (ObjectDisposedException) {
284 			}
285 
286 			try {
287 				key.ToString ();
288 				Assert.Fail ("#11");
289 			} catch (ObjectDisposedException) {
290 			}
291 
292 			try {
293 				int x = key.ValueCount;
294 				Assert.Fail ("#12:" + x);
295 			} catch (ObjectDisposedException) {
296 			}
297 		}
298 
299 		[Test]
Close_Remote_Hive()300 		public void Close_Remote_Hive ()
301 		{
302 			// access to registry of remote machines is not implemented on unix
303 			if (RunningOnUnix)
304 				Assert.Ignore ("Running on Unix.");
305 
306 			RegistryKey hive = RegistryKey.OpenRemoteBaseKey (
307 				RegistryHive.CurrentUser, Environment.MachineName);
308 			hive.Close ();
309 
310 			// closing a remote hive twice does not have any effect
311 			hive.Close ();
312 
313 			try {
314 				hive.CreateSubKey ("a");
315 				Assert.Fail ("#1");
316 			} catch (ObjectDisposedException) {
317 			}
318 
319 			try {
320 				hive.DeleteSubKey ("doesnotexist");
321 				Assert.Fail ("#2");
322 			} catch (ObjectDisposedException) {
323 			}
324 
325 			try {
326 				hive.DeleteSubKeyTree ("doesnotexist");
327 				Assert.Fail ("#3");
328 			} catch (ObjectDisposedException) {
329 			}
330 
331 			try {
332 				hive.DeleteValue ("doesnotexist");
333 				Assert.Fail ("#4");
334 			} catch (ObjectDisposedException) {
335 			}
336 
337 			// flushing a closed hive does not have any effect
338 			hive.Flush ();
339 
340 			try {
341 				hive.GetSubKeyNames ();
342 				Assert.Fail ("#5");
343 			} catch (ObjectDisposedException) {
344 			}
345 
346 			try {
347 				hive.GetValue ("doesnotexist");
348 				Assert.Fail ("#6");
349 			} catch (ObjectDisposedException) {
350 			}
351 
352 			try {
353 				hive.GetValueNames ();
354 				Assert.Fail ("#7");
355 			} catch (ObjectDisposedException) {
356 			}
357 
358 			try {
359 				hive.OpenSubKey ("doesnotexist");
360 				Assert.Fail ("#8");
361 			} catch (ObjectDisposedException) {
362 			}
363 
364 			try {
365 				hive.SetValue ("doesnotexist", "something");
366 				Assert.Fail ("#9");
367 			} catch (ObjectDisposedException) {
368 			}
369 
370 			try {
371 				int x = hive.SubKeyCount;
372 				Assert.Fail ("#10:" + x);
373 			} catch (ObjectDisposedException) {
374 			}
375 
376 			try {
377 				hive.ToString ();
378 				Assert.Fail ("#11");
379 			} catch (ObjectDisposedException) {
380 			}
381 
382 			try {
383 				int x = hive.ValueCount;
384 				Assert.Fail ("#12:" + x);
385 			} catch (ObjectDisposedException) {
386 			}
387 		}
388 
389 		[Test]
Close_Remote_Key()390 		public void Close_Remote_Key ()
391 		{
392 			// access to registry of remote machines is not implemented on unix
393 			if (RunningOnUnix)
394 				Assert.Ignore ("Running on Unix.");
395 
396 			RegistryKey hive = RegistryKey.OpenRemoteBaseKey (
397 				RegistryHive.CurrentUser, Environment.MachineName);
398 			RegistryKey key = hive.OpenSubKey ("SOFTWARE");
399 			key.Close ();
400 
401 			// closing a remote key twice does not have any effect
402 			key.Close ();
403 
404 			try {
405 				key.CreateSubKey ("a");
406 				Assert.Fail ("#1");
407 			} catch (ObjectDisposedException) {
408 			}
409 
410 			try {
411 				key.DeleteSubKey ("doesnotexist");
412 				Assert.Fail ("#2");
413 			} catch (ObjectDisposedException) {
414 			}
415 
416 			try {
417 				key.DeleteSubKeyTree ("doesnotexist");
418 				Assert.Fail ("#3");
419 			} catch (ObjectDisposedException) {
420 			}
421 
422 			try {
423 				key.DeleteValue ("doesnotexist");
424 				Assert.Fail ("#4");
425 			} catch (ObjectDisposedException) {
426 			}
427 
428 			// flushing a closed key does not have any effect
429 			key.Flush ();
430 
431 			try {
432 				key.GetSubKeyNames ();
433 				Assert.Fail ("#5");
434 			} catch (ObjectDisposedException) {
435 			}
436 
437 			try {
438 				key.GetValue ("doesnotexist");
439 				Assert.Fail ("#6");
440 			} catch (ObjectDisposedException) {
441 			}
442 
443 			try {
444 				key.GetValueNames ();
445 				Assert.Fail ("#7");
446 			} catch (ObjectDisposedException) {
447 			}
448 
449 			try {
450 				key.OpenSubKey ("doesnotexist");
451 				Assert.Fail ("#8");
452 			} catch (ObjectDisposedException) {
453 			}
454 
455 			try {
456 				key.SetValue ("doesnotexist", "something");
457 				Assert.Fail ("#9");
458 			} catch (ObjectDisposedException) {
459 			}
460 
461 			try {
462 				int x = key.SubKeyCount;
463 				Assert.Fail ("#10:" + x);
464 			} catch (ObjectDisposedException) {
465 			}
466 
467 			try {
468 				key.ToString ();
469 				Assert.Fail ("#11");
470 			} catch (ObjectDisposedException) {
471 			}
472 
473 			try {
474 				int x = key.ValueCount;
475 				Assert.Fail ("#12:" + x);
476 			} catch (ObjectDisposedException) {
477 			}
478 
479 			hive.Close ();
480 		}
481 
482 		[Test]
CreateSubKey()483 		public void CreateSubKey ()
484 		{
485 			string subKeyName = Guid.NewGuid ().ToString ();
486 
487 			try {
488 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
489 					// check if key was successfully created
490 					Assert.IsNotNull (createdKey, "#A1");
491 					// software subkey should not be created automatically
492 					Assert.IsNull (createdKey.OpenSubKey ("software"), "#A2");
493 				}
494 
495 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
496 					// check if key was successfully created
497 					Assert.IsNotNull (createdKey, "#B1");
498 					// software subkey should not be created automatically
499 					Assert.IsNull (createdKey.OpenSubKey ("software"), "#B2");
500 				}
501 			} finally {
502 				// clean-up
503 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
504 			}
505 
506 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
507 				try {
508 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
509 						// check if key was successfully created
510 						Assert.IsNotNull (createdKey, "#C1");
511 						// software subkey should not be created automatically
512 						Assert.IsNull (softwareKey.OpenSubKey ("software"), "#C2");
513 					}
514 
515 					using (RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName)) {
516 						// check if key was successfully created
517 						Assert.IsNotNull (createdKey, "#D1");
518 						// software subkey should not be created automatically
519 						Assert.IsNull (softwareKey.OpenSubKey ("software"), "#D2");
520 					}
521 				} finally {
522 					// clean-up
523 					softwareKey.DeleteSubKeyTree (subKeyName);
524 				}
525 			}
526 		}
527 
528 		[Test]
CreateSubKey_Key_ReadOnly()529 		public void CreateSubKey_Key_ReadOnly ()
530 		{
531 			string subKeyName = Guid.NewGuid ().ToString ();
532 
533 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software")) {
534 				RegistryKey createdKey = null;
535 				try {
536 					try {
537 						createdKey = softwareKey.CreateSubKey (subKeyName);
538 						Assert.Fail ("#1");
539 					} catch (UnauthorizedAccessException ex) {
540 						// Cannot write to the registry key
541 						Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#2");
542 						Assert.IsNotNull (ex.Message, "#3");
543 						Assert.IsNull (ex.InnerException, "#4");
544 					}
545 				} finally {
546 					if (createdKey != null)
547 						createdKey.Close ();
548 				}
549 			}
550 		}
551 
552 		[Test]
CreateSubKey_Key_Removed()553 		public void CreateSubKey_Key_Removed ()
554 		{
555 			string subKeyName = Guid.NewGuid ().ToString ();
556 
557 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
558 				try {
559 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
560 						softwareKey.DeleteSubKeyTree (subKeyName);
561 						Assert.IsNull (softwareKey.OpenSubKey (subKeyName), "#1");
562 						try {
563 							createdKey.CreateSubKey ("test");
564 							Assert.Fail ("#2");
565 						} catch (IOException ex) {
566 							// Illegal operation attempted on a registry key that
567 							// has been marked for deletion
568 							Assert.AreEqual (typeof (IOException), ex.GetType (), "#3");
569 							Assert.IsNotNull (ex.Message, "#4");
570 							Assert.IsNull (ex.InnerException, "#5");
571 						}
572 					}
573 				} finally {
574 					try {
575 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
576 						if (createdKey != null) {
577 							createdKey.Close ();
578 							softwareKey.DeleteSubKeyTree (subKeyName);
579 						}
580 					} catch {
581 					}
582 				}
583 			}
584 		}
585 
586 		[Test]
587 		[Category ("NotWorking")] // MS should not allow this
CreateSubKey_Name_Empty()588 		public void CreateSubKey_Name_Empty ()
589 		{
590 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
591 				using (RegistryKey emptyKey = softwareKey.CreateSubKey (string.Empty)) {
592 					Assert.IsNotNull (emptyKey, "#1");
593 					emptyKey.SetValue ("name1", "value1");
594 				}
595 			}
596 		}
597 
598 		[Test]
CreateSubKey_Name_MaxLength()599 		public void CreateSubKey_Name_MaxLength ()
600 		{
601 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
602 				string subKeyName = new string ('a', 254);
603 
604 				try {
605 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
606 						Assert.IsNotNull (createdKey, "#A1");
607 						Assert.IsNotNull (softwareKey.OpenSubKey (subKeyName), "#A2");
608 					}
609 				} finally {
610 					softwareKey.DeleteSubKeyTree (subKeyName);
611 				}
612 
613 				subKeyName = new string ('a', 255);
614 
615 				try {
616 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
617 						Assert.IsNotNull (createdKey, "#B1");
618 						Assert.IsNotNull (softwareKey.OpenSubKey (subKeyName), "#B2");
619 					}
620 				} finally {
621 					softwareKey.DeleteSubKey (subKeyName);
622 				}
623 
624 				subKeyName = new string ('a', 256);
625 
626 				try {
627 					softwareKey.CreateSubKey (subKeyName);
628 					Assert.Fail ("#C1");
629 				} catch (ArgumentException ex) {
630 					// 1.x: Registry subkeys should not be
631 					// greater than or equal to 255 characters
632 					//
633 					// 2.x: Registry subkeys should not be
634 					// greater than 255 characters
635 					Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#C2");
636 					Assert.IsNull (ex.InnerException, "#C3");
637 					Assert.IsNotNull (ex.Message, "#C4");
638 					Assert.IsTrue (ex.Message.IndexOf ("255") != -1, "#C5");
639 					Assert.IsNull (ex.ParamName, "#C6");
640 				}
641 			}
642 		}
643 
644 		[Test]
CreateSubKey_Name_Null()645 		public void CreateSubKey_Name_Null ()
646 		{
647 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
648 				try {
649 					softwareKey.CreateSubKey (null);
650 					Assert.Fail ("#1");
651 				} catch (ArgumentNullException ex) {
652 					Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
653 					Assert.IsNull (ex.InnerException, "#3");
654 					Assert.IsNotNull (ex.Message, "#4");
655 					Assert.AreEqual ("name", ex.ParamName, "#5");
656 				}
657 			}
658 		}
659 
660 		// Unfortunately we can't test that the scenario where a volatile
661 		// key is not alive after a reboot, but we can test other bits.
662 		[Test]
CreateSubKey_Volatile()663 		public void CreateSubKey_Volatile ()
664 		{
665 			RegistryKey key = null;
666 			RegistryKey subkey = null;
667 			string subKeyName = "VolatileKey";
668 
669 			try {
670 				key = Registry.CurrentUser.CreateSubKey (subKeyName, RegistryKeyPermissionCheck.Default, RegistryOptions.Volatile);
671 				subkey = key.CreateSubKey ("Child", RegistryKeyPermissionCheck.Default, RegistryOptions.Volatile);
672 				key.Close ();
673 
674 				key = Registry.CurrentUser.OpenSubKey (subKeyName);
675 				subkey = key.OpenSubKey ("Child");
676 				Assert.AreEqual (true, subkey != null, "#A1");
677 			} finally {
678 				if (subkey != null)
679 					subkey.Close ();
680 				if (key != null)
681 					key.Close ();
682 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName, false);
683 			}
684 		}
685 
686 		[Test]
CreateSubKey_Volatile_Child()687 		public void CreateSubKey_Volatile_Child ()
688 		{
689 			RegistryKey key = null;
690 			RegistryKey subkey = null;
691 			string subKeyName = "VolatileKey";
692 
693 			try {
694 				key = Registry.CurrentUser.CreateSubKey (subKeyName, RegistryKeyPermissionCheck.Default, RegistryOptions.Volatile);
695 				subkey = key.CreateSubKey ("Child"); // Non volatile child
696 				Assert.Fail ("#Exc");
697 			} catch (IOException) {
698 			} finally {
699 				if (subkey != null)
700 					subkey.Close ();
701 				if (key != null)
702 					key.Close ();
703 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName, false);
704 			}
705 		}
706 
707 		[Test]
CreateSubKey_Volatile_Conflict()708 		public void CreateSubKey_Volatile_Conflict ()
709 		{
710 			RegistryKey key = null;
711 			RegistryKey key2 = null;
712 			RegistryKey subkey = null;
713 			string subKeyNameVolatile = "VolatileKey";
714 			string subKeyNameNonVolatile = "NonVolatileKey";
715 
716 			try {
717 				//
718 				// Create a volatile key and try to open it as a normal one
719 				//
720 				key = Registry.CurrentUser.CreateSubKey (subKeyNameVolatile, RegistryKeyPermissionCheck.Default, RegistryOptions.Volatile);
721 				key2 = Registry.CurrentUser.CreateSubKey (subKeyNameVolatile, RegistryKeyPermissionCheck.Default, RegistryOptions.None);
722 				Assert.AreEqual (key.Name, key2.Name, "A0");
723 
724 				subkey = key2.CreateSubKey ("Child", RegistryKeyPermissionCheck.Default, RegistryOptions.Volatile);
725 				Assert.AreEqual (true, key.OpenSubKey ("Child") != null, "#A1");
726 				Assert.AreEqual (true, key2.OpenSubKey ("Child") != null, "#A2");
727 
728 				subkey.Close ();
729 				key.Close ();
730 				key2.Close ();
731 
732 				//
733 				// Create a non-volatile key and try to open it as a volatile one
734 				//
735 				key2 = Registry.CurrentUser.CreateSubKey (subKeyNameNonVolatile, RegistryKeyPermissionCheck.Default, RegistryOptions.None);
736 				key2.SetValue ("Name", "Mono");
737 				key = Registry.CurrentUser.CreateSubKey (subKeyNameNonVolatile, RegistryKeyPermissionCheck.Default, RegistryOptions.Volatile);
738 				Assert.AreEqual (key.Name, key2.Name, "B0");
739 				Assert.AreEqual ("Mono", key.GetValue ("Name"), "#B1");
740 				Assert.AreEqual ("Mono", key2.GetValue ("Name"), "#B2");
741 
742 				key.CreateSubKey ("Child");
743 				Assert.AreEqual (true, key.OpenSubKey ("Child") != null, "#B3");
744 				Assert.AreEqual (true, key2.OpenSubKey ("Child") != null, "#B4");
745 
746 				//
747 				// Close the non-volatile key and try to re-open it as a volatile one
748 				//
749 				key.Close ();
750 				key2.Close ();
751 				key = Registry.CurrentUser.CreateSubKey (subKeyNameNonVolatile, RegistryKeyPermissionCheck.Default, RegistryOptions.Volatile);
752 				Assert.AreEqual ("Mono", key.GetValue ("Name"), "#C0");
753 				Assert.AreEqual (true, key.OpenSubKey ("Child") != null, "#C1");
754 			} finally {
755 				if (subkey != null)
756 					subkey.Close ();
757 				if (key != null)
758 					key.Close ();
759 				if (key2 != null)
760 					key2.Close ();
761 				Registry.CurrentUser.DeleteSubKeyTree (subKeyNameVolatile, false);
762 				Registry.CurrentUser.DeleteSubKeyTree (subKeyNameNonVolatile, false);
763 			}
764 		}
765 
766 		[Test]
DeleteSubKey_Volatile()767 		public void DeleteSubKey_Volatile ()
768 		{
769 			RegistryKey key = null;
770 			RegistryKey subkey = null;
771 			string subKeyName = "VolatileKey";
772 
773 			try {
774 				key = Registry.CurrentUser.CreateSubKey (subKeyName, RegistryKeyPermissionCheck.Default, RegistryOptions.Volatile);
775 				key.CreateSubKey ("VolatileKeyChild", RegistryKeyPermissionCheck.Default, RegistryOptions.Volatile);
776 				key.SetValue ("Name", "Mono");
777 				key.Close ();
778 
779 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
780 
781 				key = Registry.CurrentUser.OpenSubKey (subKeyName);
782 				Assert.AreEqual (null, key, "#A0");
783 			} finally {
784 				if (subkey != null)
785 					subkey.Close ();
786 				if (key != null)
787 					key.Close ();
788 			}
789 		}
790 
791 		// Define a normal key, and create a normal and a volatile key under it, and retrieve their names.
792 		[Test]
GetSubKeyNames_Volatile()793 		public void GetSubKeyNames_Volatile ()
794 		{
795 			RegistryKey key = null;
796 			RegistryKey subkey = null;
797 			string subKeyName = Guid.NewGuid ().ToString ();
798 			string volChildKeyName = "volatilechildkey";
799 			string childKeyName = "childkey";
800 
801 			try {
802 				key = Registry.CurrentUser.CreateSubKey (subKeyName);
803 				key.CreateSubKey (volChildKeyName, RegistryKeyPermissionCheck.Default, RegistryOptions.Volatile);
804 				key.CreateSubKey (childKeyName, RegistryKeyPermissionCheck.Default, RegistryOptions.None);
805 				key.Close ();
806 
807 				key = Registry.CurrentUser.OpenSubKey (subKeyName);
808 				string [] keyNames = key.GetSubKeyNames ();
809 
810 				// we can guarantee the order of the child keys, so we sort the two of them
811 				Array.Sort (keyNames);
812 
813 				Assert.AreEqual (2, keyNames.Length, "#A0");
814 				Assert.AreEqual (childKeyName, keyNames [0], "#A1");
815 				Assert.AreEqual (volChildKeyName, keyNames [1], "#A2");
816 			} finally {
817 				if (subkey != null)
818 					subkey.Close ();
819 				if (key != null)
820 					key.Close ();
821 			}
822 
823 		}
824 
825 		[Test]
DeleteSubKey()826 		public void DeleteSubKey ()
827 		{
828 			string subKeyName = Guid.NewGuid ().ToString ();
829 
830 			try {
831 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
832 					// check if key was successfully created
833 					Assert.IsNotNull (createdKey, "#1");
834 				}
835 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
836 					Assert.IsNotNull (createdKey, "#2");
837 					Registry.CurrentUser.DeleteSubKey (subKeyName);
838 				}
839 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
840 					Assert.IsNull (createdKey, "#3");
841 				}
842 			} finally {
843 				try {
844 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
845 					if (createdKey != null) {
846 						createdKey.Close ();
847 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
848 					}
849 				} catch {
850 				}
851 			}
852 		}
853 
854 		[Test]
DeleteSubKey_Key_HasChildKeys()855 		public void DeleteSubKey_Key_HasChildKeys ()
856 		{
857 			string subKeyName = Guid.NewGuid ().ToString ();
858 
859 			try {
860 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
861 					// check if key was successfully created
862 					Assert.IsNotNull (createdKey, "#1");
863 					RegistryKey subKey = createdKey.CreateSubKey ("monotemp");
864 					subKey.Close ();
865 				}
866 				try {
867 					Registry.CurrentUser.DeleteSubKey (subKeyName);
868 					Assert.Fail ("#2");
869 				} catch (InvalidOperationException ex) {
870 					// Registry key has subkeys and recursive removes are not
871 					// supported by this method
872 					Assert.AreEqual (typeof (InvalidOperationException), ex.GetType (), "#3");
873 					Assert.IsNotNull (ex.Message, "#4");
874 					Assert.IsNull (ex.InnerException, "#5");
875 				}
876 			} finally {
877 				try {
878 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
879 					if (createdKey != null) {
880 						createdKey.Close ();
881 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
882 					}
883 				} catch {
884 				}
885 			}
886 		}
887 
888 		[Test]
DeleteSubKey_Key_ReadOnly()889 		public void DeleteSubKey_Key_ReadOnly ()
890 		{
891 			string subKeyName = Guid.NewGuid ().ToString ();
892 
893 			try {
894 				using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
895 					RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName);
896 					createdKey.Close ();
897 				}
898 
899 				using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software")) {
900 					try {
901 						softwareKey.DeleteSubKey (subKeyName);
902 						Assert.Fail ("#1");
903 					} catch (UnauthorizedAccessException ex) {
904 						// Cannot write to the registry key
905 						Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#2");
906 						Assert.IsNotNull (ex.Message, "#3");
907 						Assert.IsNull (ex.InnerException, "#4");
908 					}
909 				}
910 			} finally {
911 				try {
912 					using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
913 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
914 						if (createdKey != null) {
915 							createdKey.Close ();
916 							softwareKey.DeleteSubKeyTree (subKeyName);
917 						}
918 					}
919 				} catch {
920 				}
921 			}
922 		}
923 
924 		[Test]
DeleteSubKey_Key_DoesNotExist()925 		public void DeleteSubKey_Key_DoesNotExist ()
926 		{
927 			string subKeyName = Guid.NewGuid ().ToString ();
928 
929 			try {
930 				Registry.CurrentUser.DeleteSubKey (subKeyName);
931 				Assert.Fail ("#A1");
932 			} catch (ArgumentException ex) {
933 				// Cannot delete a subkey tree because the subkey does not exist
934 				Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#A2");
935 				Assert.IsNull (ex.InnerException, "#A3");
936 				Assert.IsNotNull (ex.Message, "#A4");
937 				Assert.IsNull (ex.ParamName, "#A5");
938 			}
939 
940 			try {
941 				Registry.CurrentUser.DeleteSubKey (subKeyName, true);
942 				Assert.Fail ("#B1");
943 			} catch (ArgumentException ex) {
944 				// Cannot delete a subkey tree because the subkey does not exist
945 				Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#B2");
946 				Assert.IsNull (ex.InnerException, "#B3");
947 				Assert.IsNotNull (ex.Message, "#B4");
948 				Assert.IsNull (ex.ParamName, "#B5");
949 			}
950 
951 			Registry.CurrentUser.DeleteSubKey (subKeyName, false);
952 		}
953 
954 		[Test]
DeleteSubKey_Key_Removed()955 		public void DeleteSubKey_Key_Removed ()
956 		{
957 			string subKeyName = Guid.NewGuid ().ToString ();
958 
959 			try {
960 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
961 					// check if key was successfully created
962 					Assert.IsNotNull (createdKey, "#1");
963 					RegistryKey subKey = createdKey.CreateSubKey ("monotemp");
964 					subKey.Close ();
965 				}
966 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName, true)) {
967 					Assert.IsNotNull (createdKey, "#2");
968 					using (RegistryKey subKey = createdKey.OpenSubKey ("monotemp")) {
969 						Assert.IsNotNull (createdKey, "#3");
970 					}
971 					Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
972 					Assert.IsNull (Registry.CurrentUser.OpenSubKey (subKeyName), "#4");
973 					try {
974 						createdKey.DeleteSubKey ("monotemp");
975 						Assert.Fail ("#5");
976 					} catch (ArgumentException ex) {
977 						// Cannot delete a subkey tree because the subkey does
978 						// not exist
979 						Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#6");
980 						Assert.IsNull (ex.InnerException, "#7");
981 						Assert.IsNotNull (ex.Message, "#8");
982 						Assert.IsNull (ex.ParamName, "#9");
983 					}
984 				}
985 			} finally {
986 				try {
987 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
988 					if (createdKey != null) {
989 						createdKey.Close ();
990 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
991 					}
992 				} catch {
993 				}
994 			}
995 		}
996 
997 		[Test]
998 		[Category ("NotWorking")] // MS should not allow this
DeleteSubKey_Name_Empty()999 		public void DeleteSubKey_Name_Empty ()
1000 		{
1001 			string subKeyName = Guid.NewGuid ().ToString ();
1002 
1003 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
1004 				try {
1005 					RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName);
1006 					createdKey.DeleteSubKey (string.Empty);
1007 					createdKey.Close ();
1008 
1009 					createdKey = softwareKey.OpenSubKey (subKeyName);
1010 					Assert.IsNull (createdKey, "#1");
1011 				} finally {
1012 					try {
1013 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
1014 						if (createdKey != null)
1015 							createdKey.Close ();
1016 						softwareKey.DeleteSubKeyTree (subKeyName);
1017 					} catch {
1018 					}
1019 				}
1020 			}
1021 		}
1022 
1023 		[Test]
DeleteSubKey_Name_MaxLength()1024 		public void DeleteSubKey_Name_MaxLength ()
1025 		{
1026 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
1027 				string subKeyName = new string ('a', 254);
1028 
1029 				using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
1030 					createdKey.Close ();
1031 				}
1032 				using (RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName, false)) {
1033 					Assert.IsNotNull (createdKey, "#A1");
1034 				}
1035 				softwareKey.DeleteSubKey (subKeyName);
1036 				using (RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName, false)) {
1037 					Assert.IsNull (createdKey, "#A2");
1038 				}
1039 
1040 				subKeyName = new string ('a', 256);
1041 
1042 				try {
1043 					softwareKey.DeleteSubKey (subKeyName);
1044 					Assert.Fail ("#B1");
1045 				} catch (ArgumentException ex) {
1046 					// 1.x: Registry subkeys should not be
1047 					// greater than or equal to 255 characters
1048 					//
1049 					// 2.x: Registry subkeys should not be
1050 					// greater than 255 characters
1051 					Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#B2");
1052 					Assert.IsNull (ex.InnerException, "#B3");
1053 					Assert.IsNotNull (ex.Message, "#B4");
1054 					Assert.IsTrue (ex.Message.IndexOf ("255") != -1, "#B5");
1055 					Assert.IsNull (ex.ParamName, "#B6");
1056 				}
1057 			}
1058 		}
1059 
1060 		[Test]
DeleteSubKey_Name_Null()1061 		public void DeleteSubKey_Name_Null ()
1062 		{
1063 			string subKeyName = Guid.NewGuid ().ToString ();
1064 
1065 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
1066 				try {
1067 					RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName);
1068 					try {
1069 						createdKey.DeleteSubKey (null);
1070 						Assert.Fail ("#1");
1071 					} catch (ArgumentNullException ex) {
1072 						Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
1073 						Assert.IsNull (ex.InnerException, "#3");
1074 						Assert.IsNotNull (ex.Message, "#4");
1075 						Assert.AreEqual ("name", ex.ParamName, "#5");
1076 					}
1077 				} finally {
1078 					try {
1079 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
1080 						if (createdKey != null)
1081 							createdKey.Close ();
1082 						softwareKey.DeleteSubKeyTree (subKeyName);
1083 					} catch {
1084 					}
1085 				}
1086 			}
1087 		}
1088 
1089 		[Test]
DeleteSubKeyTree()1090 		public void DeleteSubKeyTree ()
1091 		{
1092 			// TODO:
1093 			// - remove key with subkeys
1094 			// - remove key of which some subkeys are marked for deletion
1095 			// - remove key with values
1096 		}
1097 
1098 		[Test]
DeleteSubKeyTree_Key_DoesNotExist()1099 		public void DeleteSubKeyTree_Key_DoesNotExist ()
1100 		{
1101 			// Cannot delete a subkey tree because the subkey does not exist
1102 			string subKeyName = Guid.NewGuid ().ToString ();
1103 			try {
1104 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1105 				Assert.Fail ("#1");
1106 			} catch (ArgumentException ex) {
1107 				Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#2");
1108 				Assert.IsNull (ex.InnerException, "#3");
1109 				Assert.IsNotNull (ex.Message, "#4");
1110 				Assert.IsNull (ex.ParamName, "#5");
1111 			}
1112 		}
1113 
1114 		[Test]
DeleteSubKeyTree_Key_DoesNotExist_Overload()1115 		public void DeleteSubKeyTree_Key_DoesNotExist_Overload ()
1116 		{
1117 			// Cannot delete a subkey tree because the subkey does not exist
1118 			string subKeyName = Guid.NewGuid ().ToString ();
1119 			try {
1120 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName, true);
1121 				Assert.Fail ("#1");
1122 			} catch (ArgumentException ex) {
1123 				Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#2");
1124 				Assert.IsNull (ex.InnerException, "#3");
1125 				Assert.IsNotNull (ex.Message, "#4");
1126 				Assert.IsNull (ex.ParamName, "#5");
1127 			}
1128 
1129 			// It's enough to know this line is not throwing an exception.
1130 			Registry.CurrentUser.DeleteSubKey (subKeyName, false);
1131 		}
1132 
1133 		[Test]
DeleteSubKeyTree_Key_ReadOnly()1134 		public void DeleteSubKeyTree_Key_ReadOnly ()
1135 		{
1136 			string subKeyName = Guid.NewGuid ().ToString ();
1137 
1138 			try {
1139 				using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
1140 					RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName);
1141 					createdKey.Close ();
1142 				}
1143 
1144 				using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software")) {
1145 					try {
1146 						softwareKey.DeleteSubKeyTree (subKeyName);
1147 						Assert.Fail ("#1");
1148 					} catch (UnauthorizedAccessException ex) {
1149 						// Cannot write to the registry key
1150 						Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#2");
1151 						Assert.IsNotNull (ex.Message, "#3");
1152 						Assert.IsNull (ex.InnerException, "#4");
1153 					}
1154 				}
1155 			} finally {
1156 				try {
1157 					using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
1158 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
1159 						if (createdKey != null)
1160 							createdKey.Close ();
1161 						softwareKey.DeleteSubKeyTree (subKeyName);
1162 					}
1163 				} catch {
1164 				}
1165 			}
1166 		}
1167 
1168 		[Test]
DeleteSubKeyTree_Key_Removed()1169 		public void DeleteSubKeyTree_Key_Removed ()
1170 		{
1171 			string subKeyName = Guid.NewGuid ().ToString ();
1172 
1173 			try {
1174 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1175 					// check if key was successfully created
1176 					Assert.IsNotNull (createdKey, "#1");
1177 					RegistryKey subKey = createdKey.CreateSubKey ("monotemp");
1178 					subKey.Close ();
1179 				}
1180 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName, true)) {
1181 					Assert.IsNotNull (createdKey, "#2");
1182 					using (RegistryKey subKey = createdKey.OpenSubKey ("monotemp")) {
1183 						Assert.IsNotNull (createdKey, "#3");
1184 					}
1185 					Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1186 					Assert.IsNull (Registry.CurrentUser.OpenSubKey (subKeyName), "#4");
1187 					try {
1188 						createdKey.DeleteSubKeyTree ("monotemp");
1189 						Assert.Fail ("#5");
1190 					} catch (ArgumentException ex) {
1191 						// Cannot delete a subkey tree because the subkey does
1192 						// not exist
1193 						Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#6");
1194 						Assert.IsNull (ex.InnerException, "#7");
1195 						Assert.IsNotNull (ex.Message, "#8");
1196 						Assert.IsNull (ex.ParamName, "#9");
1197 					}
1198 				}
1199 			} finally {
1200 				try {
1201 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1202 					if (createdKey != null) {
1203 						createdKey.Close ();
1204 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1205 					}
1206 				} catch {
1207 				}
1208 			}
1209 		}
1210 
1211 		[Test]
1212 		[Category ("NotWorking")] // MS should not allow this
DeleteSubKeyTree_Name_Empty()1213 		public void DeleteSubKeyTree_Name_Empty ()
1214 		{
1215 			string subKeyName = Guid.NewGuid ().ToString ();
1216 
1217 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
1218 				try {
1219 					RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName);
1220 					createdKey.DeleteSubKeyTree (string.Empty);
1221 					createdKey.Close ();
1222 
1223 					createdKey = softwareKey.OpenSubKey (subKeyName);
1224 					Assert.IsNull (createdKey, "#1");
1225 				} finally {
1226 					try {
1227 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
1228 						if (createdKey != null)
1229 							createdKey.Close ();
1230 						softwareKey.DeleteSubKeyTree (subKeyName);
1231 					} catch {
1232 					}
1233 				}
1234 			}
1235 		}
1236 
1237 		[Test]
DeleteSubKeyTree_Name_MaxLength()1238 		public void DeleteSubKeyTree_Name_MaxLength ()
1239 		{
1240 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
1241 				string subKeyName = new string ('a', 254);
1242 
1243 				using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
1244 					createdKey.Close ();
1245 				}
1246 				using (RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName, false)) {
1247 					Assert.IsNotNull (createdKey, "#A1");
1248 				}
1249 				softwareKey.DeleteSubKeyTree (subKeyName);
1250 				using (RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName, false)) {
1251 					Assert.IsNull (createdKey, "#A2");
1252 				}
1253 
1254 				subKeyName = new string ('a', 256);
1255 
1256 				try {
1257 					softwareKey.DeleteSubKeyTree (subKeyName);
1258 					Assert.Fail ("#B1");
1259 				} catch (ArgumentException ex) {
1260 					// 1.x: Registry subkeys should not be
1261 					// greater than or equal to 255 characters
1262 					//
1263 					// 2.x: Registry subkeys should not be
1264 					// greater than 255 characters
1265 					Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#B2");
1266 					Assert.IsNull (ex.InnerException, "#B3");
1267 					Assert.IsNotNull (ex.Message, "#B4");
1268 					Assert.IsTrue (ex.Message.IndexOf ("255") != -1, "#B5");
1269 					Assert.IsNull (ex.ParamName, "#B6");
1270 				}
1271 			}
1272 		}
1273 
1274 		[Test]
DeleteSubKeyTree_Name_Null()1275 		public void DeleteSubKeyTree_Name_Null ()
1276 		{
1277 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
1278 				try {
1279 					softwareKey.DeleteSubKeyTree (null);
1280 					Assert.Fail ("#1");
1281 				} catch (ArgumentNullException ex) {
1282 					Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
1283 					Assert.IsNull (ex.InnerException, "#3");
1284 					Assert.IsNotNull (ex.Message, "#4");
1285 					Assert.AreEqual ("name", ex.ParamName, "#5");
1286 				}
1287 			}
1288 		}
1289 
1290 		[Test]
DeleteValue()1291 		public void DeleteValue ()
1292 		{
1293 			string subKeyName = Guid.NewGuid ().ToString ();
1294 
1295 			try {
1296 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1297 					// check if key was successfully created
1298 					Assert.IsNotNull (createdKey, "#A1");
1299 					createdKey.SetValue ("name1", "value1");
1300 					createdKey.SetValue ("name2", "value2");
1301 					string [] names = createdKey.GetValueNames ();
1302 					Assert.IsNotNull (names, "#A2");
1303 					Assert.AreEqual (2, names.Length, "#A3");
1304 					Assert.IsNotNull (names [0], "#A4");
1305 					Assert.AreEqual ("name1", names [0], "#A5");
1306 					Assert.IsNotNull (createdKey.GetValue ("name1"), "#A6");
1307 					Assert.AreEqual ("value1", createdKey.GetValue ("name1"), "#A7");
1308 					Assert.AreEqual ("name2", names [1], "#A8");
1309 					Assert.IsNotNull (createdKey.GetValue ("name2"), "#A9");
1310 					Assert.AreEqual ("value2", createdKey.GetValue ("name2"), "#A10");
1311 				}
1312 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName, true)) {
1313 					Assert.IsNotNull (createdKey, "#B1");
1314 					createdKey.DeleteValue ("name1");
1315 					string [] names = createdKey.GetValueNames ();
1316 					Assert.IsNotNull (names, "#B2");
1317 					Assert.AreEqual (1, names.Length, "#B3");
1318 					Assert.IsNotNull (names [0], "#B4");
1319 					Assert.AreEqual ("name2", names [0], "#B5");
1320 					Assert.IsNotNull (createdKey.GetValue ("name2"), "#B6");
1321 					Assert.AreEqual ("value2", createdKey.GetValue ("name2"), "#B7");
1322 					createdKey.DeleteValue (new string ('a', 400), false);
1323 				}
1324 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
1325 					string [] names = createdKey.GetValueNames ();
1326 					Assert.IsNotNull (names, "#C1");
1327 					Assert.AreEqual (1, names.Length, "#C2");
1328 					Assert.IsNotNull (names [0], "#C3");
1329 					Assert.AreEqual ("name2", names [0], "#C4");
1330 					Assert.IsNotNull (createdKey.GetValue ("name2"), "#C5");
1331 					Assert.AreEqual ("value2", createdKey.GetValue ("name2"), "#C6");
1332 				}
1333 			} finally {
1334 				try {
1335 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1336 					if (createdKey != null) {
1337 						createdKey.Close ();
1338 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1339 					}
1340 				} catch {
1341 				}
1342 			}
1343 		}
1344 
1345 		[Test]
DeleteValue_Key_ReadOnly()1346 		public void DeleteValue_Key_ReadOnly ()
1347 		{
1348 			string subKeyName = Guid.NewGuid ().ToString ();
1349 
1350 			try {
1351 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1352 					createdKey.SetValue ("name1", "value1");
1353 				}
1354 
1355 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
1356 					try {
1357 						// deleting value that exists
1358 						createdKey.DeleteValue ("name1");
1359 						Assert.Fail ("#A1");
1360 					} catch (UnauthorizedAccessException ex) {
1361 						// Cannot write to the registry key
1362 						Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#A2");
1363 						Assert.IsNotNull (ex.Message, "#A3");
1364 						Assert.IsNull (ex.InnerException, "#A4");
1365 					}
1366 
1367 					try {
1368 						// deleting value that exists
1369 						createdKey.DeleteValue ("name1", true);
1370 						Assert.Fail ("#B1");
1371 					} catch (UnauthorizedAccessException ex) {
1372 						// Cannot write to the registry key
1373 						Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#B2");
1374 						Assert.IsNotNull (ex.Message, "#B3");
1375 						Assert.IsNull (ex.InnerException, "#B4");
1376 					}
1377 
1378 					try {
1379 						// deleting value that exists
1380 						createdKey.DeleteValue ("name1", false);
1381 						Assert.Fail ("#C1");
1382 					} catch (UnauthorizedAccessException ex) {
1383 						// Cannot write to the registry key
1384 						Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#C2");
1385 						Assert.IsNotNull (ex.Message, "#C3");
1386 						Assert.IsNull (ex.InnerException, "#C4");
1387 					}
1388 
1389 					try {
1390 						// deleting value that does not exist
1391 						createdKey.DeleteValue ("name2");
1392 						Assert.Fail ("#D1");
1393 					} catch (UnauthorizedAccessException ex) {
1394 						// Cannot write to the registry key
1395 						Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#D2");
1396 						Assert.IsNotNull (ex.Message, "#D3");
1397 						Assert.IsNull (ex.InnerException, "#D4");
1398 					}
1399 
1400 					try {
1401 						// deleting value that does not exist
1402 						createdKey.DeleteValue ("name2", true);
1403 						Assert.Fail ("#E1");
1404 					} catch (UnauthorizedAccessException ex) {
1405 						// Cannot write to the registry key
1406 						Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#E2");
1407 						Assert.IsNotNull (ex.Message, "#E3");
1408 						Assert.IsNull (ex.InnerException, "#E4");
1409 					}
1410 
1411 					try {
1412 						// deleting value that does not exist
1413 						createdKey.DeleteValue ("name2", false);
1414 						Assert.Fail ("#F1");
1415 					} catch (UnauthorizedAccessException ex) {
1416 						// Cannot write to the registry key
1417 						Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#F2");
1418 						Assert.IsNotNull (ex.Message, "#F3");
1419 						Assert.IsNull (ex.InnerException, "#F4");
1420 					}
1421 				}
1422 			} finally {
1423 				try {
1424 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1425 					if (createdKey != null) {
1426 						createdKey.Close ();
1427 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1428 					}
1429 				} catch {
1430 				}
1431 			}
1432 		}
1433 
1434 		[Test]
DeleteValue_Key_Removed()1435 		public void DeleteValue_Key_Removed ()
1436 		{
1437 			string subKeyName = Guid.NewGuid ().ToString ();
1438 
1439 			try {
1440 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1441 					// check if key was successfully created
1442 					Assert.IsNotNull (createdKey, "#1");
1443 					createdKey.SetValue ("name1", "value1");
1444 				}
1445 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName, true)) {
1446 					Assert.IsNotNull (createdKey, "#2");
1447 					Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1448 					Assert.IsNull (Registry.CurrentUser.OpenSubKey (subKeyName), "#3");
1449 
1450 					createdKey.DeleteValue ("name1");
1451 					createdKey.DeleteValue ("name1", true);
1452 					createdKey.DeleteValue ("name1", false);
1453 				}
1454 			} finally {
1455 				try {
1456 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1457 					if (createdKey != null) {
1458 						createdKey.Close ();
1459 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1460 					}
1461 				} catch {
1462 				}
1463 			}
1464 		}
1465 
1466 		[Test]
DeleteValue_Value_DoesNotExist()1467 		public void DeleteValue_Value_DoesNotExist ()
1468 		{
1469 			string subKeyName = Guid.NewGuid ().ToString ();
1470 
1471 			try {
1472 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1473 					// check if key was successfully created
1474 					Assert.IsNotNull (createdKey, "#A1");
1475 					createdKey.SetValue ("name1", "value1");
1476 
1477 					try {
1478 						createdKey.DeleteValue ("name2");
1479 						Assert.Fail ("#B1");
1480 					} catch (ArgumentException ex) {
1481 						// No value exists with that name
1482 						Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#B2");
1483 						Assert.IsNull (ex.InnerException, "#B3");
1484 						Assert.IsNotNull (ex.Message, "#B4");
1485 						Assert.IsNull (ex.ParamName, "#B5");
1486 					}
1487 
1488 					try {
1489 						createdKey.DeleteValue ("name2", true);
1490 						Assert.Fail ("#C1");
1491 					} catch (ArgumentException ex) {
1492 						// No value exists with that name
1493 						Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#C2");
1494 						Assert.IsNull (ex.InnerException, "#C3");
1495 						Assert.IsNotNull (ex.Message, "#C4");
1496 						Assert.IsNull (ex.ParamName, "#C5");
1497 					}
1498 
1499 					createdKey.DeleteValue ("name2", false);
1500 				}
1501 			} finally {
1502 				try {
1503 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1504 					if (createdKey != null) {
1505 						createdKey.Close ();
1506 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1507 					}
1508 				} catch {
1509 				}
1510 			}
1511 		}
1512 
1513 		[Test]
DeleteValue_Name_Empty()1514 		public void DeleteValue_Name_Empty ()
1515 		{
1516 			string subKeyName = Guid.NewGuid ().ToString ();
1517 
1518 			try {
1519 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1520 					createdKey.SetValue ("name1", "value1");
1521 					createdKey.SetValue (string.Empty, "value2");
1522 
1523 					string [] names = createdKey.GetValueNames ();
1524 					Assert.IsNotNull (names, "#A1");
1525 					Assert.AreEqual (2, names.Length, "#A2");
1526 					Assert.IsNotNull (names [0], "#A3");
1527 					/*
1528 					Assert.AreEqual ("name1", names [0], "#A4");
1529 					*/
1530 					Assert.IsNotNull (createdKey.GetValue ("name1"), "#A5");
1531 					Assert.AreEqual ("value1", createdKey.GetValue ("name1"), "#A6");
1532 					Assert.IsNotNull (names [1], "#A7");
1533 					/*
1534 					Assert.AreEqual (string.Empty, names [1], "#A8");
1535 					*/
1536 					Assert.IsNotNull (createdKey.GetValue (string.Empty), "#A9");
1537 					Assert.AreEqual ("value2", createdKey.GetValue (string.Empty), "#A10");
1538 
1539 					createdKey.DeleteValue (string.Empty);
1540 
1541 					names = createdKey.GetValueNames ();
1542 					Assert.IsNotNull (names, "#B1");
1543 					Assert.AreEqual (1, names.Length, "#B2");
1544 					Assert.IsNotNull (names [0], "#B3");
1545 					Assert.AreEqual ("name1", names [0], "#B4");
1546 					Assert.IsNotNull (createdKey.GetValue ("name1"), "#B5");
1547 					Assert.AreEqual ("value1", createdKey.GetValue ("name1"), "#B6");
1548 
1549 					try {
1550 						createdKey.DeleteValue (string.Empty);
1551 						Assert.Fail ("#C1");
1552 					} catch (ArgumentException ex) {
1553 						// No value exists with that name
1554 						Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#C2");
1555 						Assert.IsNull (ex.InnerException, "#C3");
1556 						Assert.IsNotNull (ex.Message, "#C4");
1557 						Assert.IsNull (ex.ParamName, "#C5");
1558 					}
1559 
1560 					try {
1561 						createdKey.DeleteValue (string.Empty, true);
1562 						Assert.Fail ("#D1");
1563 					} catch (ArgumentException ex) {
1564 						// No value exists with that name
1565 						Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#D2");
1566 						Assert.IsNull (ex.InnerException, "#D3");
1567 						Assert.IsNotNull (ex.Message, "#D4");
1568 						Assert.IsNull (ex.ParamName, "#D5");
1569 					}
1570 
1571 					createdKey.DeleteValue (string.Empty, false);
1572 
1573 					names = createdKey.GetValueNames ();
1574 					Assert.IsNotNull (names, "#E1");
1575 					Assert.AreEqual (1, names.Length, "#E2");
1576 					Assert.IsNotNull (names [0], "#E3");
1577 					Assert.AreEqual ("name1", names [0], "#E4");
1578 					Assert.IsNotNull (createdKey.GetValue ("name1"), "#E5");
1579 					Assert.AreEqual ("value1", createdKey.GetValue ("name1"), "#E6");
1580 				}
1581 			} finally {
1582 				try {
1583 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1584 					if (createdKey != null) {
1585 						createdKey.Close ();
1586 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1587 					}
1588 				} catch {
1589 				}
1590 			}
1591 		}
1592 
1593 		[Test]
DeleteValue_Name_Null()1594 		public void DeleteValue_Name_Null ()
1595 		{
1596 			string subKeyName = Guid.NewGuid ().ToString ();
1597 
1598 			try {
1599 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1600 					createdKey.SetValue ("name1", "value1");
1601 					createdKey.SetValue (null, "value2");
1602 
1603 					string [] names = createdKey.GetValueNames ();
1604 					Assert.IsNotNull (names, "#A1");
1605 					Assert.AreEqual (2, names.Length, "#A2");
1606 					Assert.IsNotNull (names [0], "#A3");
1607 					/*
1608 					Assert.AreEqual ("name1", names [0], "#A4");
1609 					*/
1610 					Assert.IsNotNull (createdKey.GetValue ("name1"), "#A5");
1611 					Assert.AreEqual ("value1", createdKey.GetValue ("name1"), "#A6");
1612 					Assert.IsNotNull (names [1], "#A7");
1613 					/*
1614 					Assert.AreEqual (string.Empty, names [1], "#A8");
1615 					*/
1616 					Assert.IsNotNull (createdKey.GetValue (null), "#A9");
1617 					Assert.AreEqual ("value2", createdKey.GetValue (null), "#A10");
1618 
1619 					try {
1620 						createdKey.DeleteValue (null);
1621 						Assert.Fail ("#B1");
1622 					} catch (ArgumentNullException ex) {
1623 						Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#B2");
1624 						Assert.IsNull (ex.InnerException, "#B3");
1625 						Assert.IsNotNull (ex.Message, "#B4");
1626 						Assert.AreEqual ("name", ex.ParamName, "#B5");
1627 					}
1628 
1629 					try {
1630 						createdKey.DeleteValue (null, true);
1631 						Assert.Fail ("#C1");
1632 					} catch (ArgumentNullException ex) {
1633 						Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#C2");
1634 						Assert.IsNull (ex.InnerException, "#C3");
1635 						Assert.IsNotNull (ex.Message, "#C4");
1636 						Assert.AreEqual ("name", ex.ParamName, "#C5");
1637 					}
1638 
1639 					try {
1640 						createdKey.DeleteValue (null, false);
1641 						Assert.Fail ("#D1");
1642 					} catch (ArgumentNullException ex) {
1643 						Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#D2");
1644 						Assert.IsNull (ex.InnerException, "#D3");
1645 						Assert.IsNotNull (ex.Message, "#D4");
1646 						Assert.AreEqual ("name", ex.ParamName, "#D5");
1647 					}
1648 				}
1649 			} finally {
1650 				try {
1651 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1652 					if (createdKey != null) {
1653 						createdKey.Close ();
1654 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1655 					}
1656 				} catch {
1657 				}
1658 			}
1659 		}
1660 
1661 		[DllImport ("advapi32.dll", CharSet = CharSet.Unicode)]
RegOpenKeyEx(IntPtr keyBase, string keyName, IntPtr reserved, int access, out IntPtr keyHandle)1662 		static extern int RegOpenKeyEx (IntPtr keyBase, string keyName, IntPtr reserved, int access, out IntPtr keyHandle);
1663 
1664 		const int RegCurrentUserHive = -2147483647;
1665 		const int RegAccessRead = 0x00020019;
1666 
1667 		// FromHandle is specially designed to retrieve a RegistryKey instance based on a IntPtr
1668 		// retrieved using any unmanaged registry function, so we use directly RegOpenKeyEx to load
1669 		// our handle and then pass it to the new 4.0 method.
1670 		[Test]
FromHandle()1671 		public void FromHandle ()
1672 		{
1673 			// Not supported on Unix
1674 			if (RunningOnUnix)
1675 				Assert.Ignore ("Running on Unix.");
1676 
1677 			string subKeyName = Guid.NewGuid ().ToString ();
1678 			try {
1679 				using (RegistryKey key = Registry.CurrentUser.CreateSubKey (subKeyName))
1680 					key.SetValue ("Name", "Mono001");
1681 
1682 				IntPtr handle;
1683 				int res = RegOpenKeyEx (new IntPtr (RegCurrentUserHive), subKeyName, IntPtr.Zero, RegAccessRead, out handle);
1684 
1685 				using (RegistryKey key = RegistryKey.FromHandle (new SafeRegistryHandle (handle, true))) {
1686 					Assert.AreEqual (String.Empty, key.Name, "#A0");
1687 					Assert.AreEqual ("Mono001", key.GetValue ("Name"), "#A1");
1688 				}
1689 			} finally {
1690 				RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1691 				if (createdKey != null) {
1692 					createdKey.Close ();
1693 					Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1694 				}
1695 			}
1696 		}
1697 
1698 		[Test]
FromHandle_InvalidHandle()1699 		public void FromHandle_InvalidHandle ()
1700 		{
1701 			// Not supported on Unix
1702 			if (RunningOnUnix)
1703 				Assert.Ignore ("Running on Unix.");
1704 
1705 			string subKeyName = Guid.NewGuid ().ToString ();
1706 			try {
1707 				using (RegistryKey key = RegistryKey.FromHandle (new SafeRegistryHandle (IntPtr.Zero, true))) {
1708 					Assert.AreEqual (String.Empty, key.Name, "#A0");
1709 
1710 					// Any operation should throw a IOException, since even if we have a RegistryKey instance,
1711 					// the handle is not valid.
1712 					key.CreateSubKey ("ChildSubKey");
1713 					Assert.Fail ("#Exc0");
1714 				}
1715 			} catch (IOException) {
1716 			} finally {
1717 				RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1718 				if (createdKey != null) {
1719 					createdKey.Close ();
1720 					Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1721 				}
1722 			}
1723 		}
1724 
1725 		[Test]
Handle()1726 		public void Handle ()
1727 		{
1728 			if (RunningOnUnix)
1729 				Assert.Ignore ("Running on Unix.");
1730 
1731 			string subKeyName = Guid.NewGuid ().ToString ();
1732 			RegistryKey subkey = null;
1733 			try {
1734 				subkey = Registry.CurrentUser.CreateSubKey (subKeyName);
1735 				Assert.AreEqual (true, subkey.Handle != null, "#A0");
1736 				Assert.AreEqual (false, subkey.Handle.IsClosed, "#A1");
1737 				Assert.AreEqual (false, subkey.Handle.IsInvalid, "#A2");
1738 
1739 				subkey.Close ();
1740 				try {
1741 					if (subkey.Handle != null)
1742 						Console.WriteLine (); // Avoids a warning at compile time
1743 					Assert.Fail ("#Disposed");
1744 				} catch (ObjectDisposedException) {
1745 				}
1746 
1747 			} finally {
1748 				if (subkey != null) {
1749 					subkey.Close ();
1750 					Registry.CurrentUser.DeleteSubKeyTree (subKeyName, false);
1751 				}
1752 			}
1753 		}
1754 
1755 		[Test]
GetValue()1756 		public void GetValue ()
1757 		{
1758 			string subKeyName = Guid.NewGuid ().ToString ();
1759 
1760 			try {
1761 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1762 					createdKey.SetValue ("name1", "value1");
1763 					createdKey.SetValue ("name2", "value2");
1764 				}
1765 
1766 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
1767 					Assert.IsNotNull (createdKey.GetValue ("name1"), "#1");
1768 					Assert.AreEqual ("value1", createdKey.GetValue ("name1"), "#2");
1769 					Assert.IsNotNull (createdKey.GetValue ("name2"), "#3");
1770 					Assert.AreEqual ("value2", createdKey.GetValue ("name2"), "#4");
1771 					Assert.IsNull (createdKey.GetValue ("name3"), "#5");
1772 					Assert.AreEqual ("value3", createdKey.GetValue ("name3", "value3"), "#6");
1773 					Assert.IsNull (createdKey.GetValue ("name3", null), "#7");
1774 					Assert.IsNull (createdKey.GetValue (new string ('a', 400)), "#8");
1775 				}
1776 			} finally {
1777 				try {
1778 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1779 					if (createdKey != null) {
1780 						createdKey.Close ();
1781 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1782 					}
1783 				} catch {
1784 				}
1785 			}
1786 		}
1787 
1788 		[Test]
GetValue_Key_Removed()1789 		public void GetValue_Key_Removed ()
1790 		{
1791 			string subKeyName = Guid.NewGuid ().ToString ();
1792 
1793 			try {
1794 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1795 					createdKey.SetValue ("name1", "value1");
1796 					createdKey.SetValue ("name2", "value2");
1797 				}
1798 
1799 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
1800 					Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1801 
1802 					Assert.IsNull (createdKey.GetValue ("name1"), "#1");
1803 					Assert.IsNotNull (createdKey.GetValue ("name1", "default"), "#2");
1804 					Assert.AreEqual ("default", createdKey.GetValue ("name1", "default"), "#3");
1805 					Assert.IsNull (createdKey.GetValue ("name3"), "#3");
1806 					Assert.IsNotNull (createdKey.GetValue ("name3", "default"), "#4");
1807 					Assert.AreEqual ("default", createdKey.GetValue ("name3", "default"), "#5");
1808 				}
1809 			} finally {
1810 				try {
1811 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1812 					if (createdKey != null) {
1813 						createdKey.Close ();
1814 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1815 					}
1816 				} catch {
1817 				}
1818 			}
1819 		}
1820 
1821 		[Test]
GetValue_Name_Empty()1822 		public void GetValue_Name_Empty ()
1823 		{
1824 			string subKeyName = Guid.NewGuid ().ToString ();
1825 
1826 			try {
1827 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1828 					createdKey.SetValue ("name1", "value1");
1829 					createdKey.SetValue ("name2", "value2");
1830 
1831 					Assert.IsNull (createdKey.GetValue (string.Empty), "#A1");
1832 					Assert.IsNotNull (createdKey.GetValue (string.Empty, "default"), "#A2");
1833 					Assert.AreEqual ("default", createdKey.GetValue (string.Empty, "default"), "#A3");
1834 					Assert.IsNull (createdKey.GetValue (string.Empty, null), "#A4");
1835 				}
1836 
1837 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
1838 					Assert.IsNull (createdKey.GetValue (string.Empty), "#B1");
1839 					Assert.IsNotNull (createdKey.GetValue (string.Empty, "default"), "#B2");
1840 					Assert.AreEqual ("default", createdKey.GetValue (string.Empty, "default"), "#B3");
1841 					Assert.IsNull (createdKey.GetValue (string.Empty, null), "#B4");
1842 				}
1843 
1844 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName, true)) {
1845 					createdKey.SetValue (string.Empty, "value1");
1846 					Assert.IsNotNull (createdKey.GetValue (string.Empty), "#C1");
1847 					Assert.AreEqual ("value1", createdKey.GetValue (string.Empty), "#C2");
1848 					Assert.AreEqual ("value1", createdKey.GetValue (string.Empty, "default"), "#C3");
1849 					Assert.AreEqual ("value1", createdKey.GetValue (string.Empty, null), "#C4");
1850 				}
1851 
1852 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
1853 					Assert.IsNotNull (createdKey.GetValue (string.Empty), "#D1");
1854 					Assert.AreEqual ("value1", createdKey.GetValue (string.Empty), "#D2");
1855 					Assert.AreEqual ("value1", createdKey.GetValue (string.Empty, "default"), "#D3");
1856 					Assert.AreEqual ("value1", createdKey.GetValue (string.Empty, null), "#D4");
1857 				}
1858 			} finally {
1859 				try {
1860 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1861 					if (createdKey != null) {
1862 						createdKey.Close ();
1863 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1864 					}
1865 				} catch {
1866 				}
1867 			}
1868 		}
1869 
1870 		[Test]
GetValue_Name_Null()1871 		public void GetValue_Name_Null ()
1872 		{
1873 			string subKeyName = Guid.NewGuid ().ToString ();
1874 
1875 			try {
1876 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1877 					createdKey.SetValue ("name1", "value1");
1878 					createdKey.SetValue ("name2", "value2");
1879 
1880 					Assert.IsNull (createdKey.GetValue (null), "#A1");
1881 					Assert.IsNotNull (createdKey.GetValue (null, "default"), "#A2");
1882 					Assert.AreEqual ("default", createdKey.GetValue (null, "default"), "#A3");
1883 					Assert.IsNull (createdKey.GetValue (null, null), "#A4");
1884 				}
1885 
1886 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
1887 					Assert.IsNull (createdKey.GetValue (null), "#B1");
1888 					Assert.IsNotNull (createdKey.GetValue (null, "default"), "#B2");
1889 					Assert.AreEqual ("default", createdKey.GetValue (null, "default"), "#B3");
1890 					Assert.IsNull (createdKey.GetValue (null, null), "#B4");
1891 				}
1892 
1893 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName, true)) {
1894 					createdKey.SetValue (string.Empty, "value1");
1895 					Assert.IsNotNull (createdKey.GetValue (null), "#C1");
1896 					Assert.AreEqual ("value1", createdKey.GetValue (null), "#C2");
1897 					Assert.AreEqual ("value1", createdKey.GetValue (null, "default"), "#C3");
1898 					Assert.AreEqual ("value1", createdKey.GetValue (null, null), "#C4");
1899 				}
1900 
1901 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
1902 					Assert.IsNotNull (createdKey.GetValue (null), "#D1");
1903 					Assert.AreEqual ("value1", createdKey.GetValue (null), "#D2");
1904 					Assert.AreEqual ("value1", createdKey.GetValue (null, "default"), "#D3");
1905 					Assert.AreEqual ("value1", createdKey.GetValue (null, null), "#D4");
1906 				}
1907 			} finally {
1908 				try {
1909 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
1910 					if (createdKey != null) {
1911 						createdKey.Close ();
1912 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
1913 					}
1914 				} catch {
1915 				}
1916 			}
1917 		}
1918 
1919 		[Test]
GetValue_Expand()1920 		public void GetValue_Expand ()
1921 		{
1922 			string subKeyName = Guid.NewGuid ().ToString ();
1923 
1924 			try {
1925 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
1926 					Environment.SetEnvironmentVariable ("MONO_TEST1", "123");
1927 					Environment.SetEnvironmentVariable ("MONO_TEST2", "456");
1928 
1929 					createdKey.SetValue ("name1", "%MONO_TEST1%/%MONO_TEST2%",
1930 						RegistryValueKind.ExpandString);
1931 					createdKey.SetValue ("name2", "%MONO_TEST1%/%MONO_TEST2%");
1932 					createdKey.SetValue ("name3", "just some text",
1933 						RegistryValueKind.ExpandString);
1934 
1935 					Assert.AreEqual ("123/456", createdKey.GetValue ("name1"), "#A1");
1936 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2"), "#A2");
1937 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3"), "#A3");
1938 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name1",
1939 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#A4");
1940 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2",
1941 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#A5");
1942 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3",
1943 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#A6");
1944 					Assert.AreEqual ("123/456", createdKey.GetValue ("name1",
1945 						null, RegistryValueOptions.None), "#A7");
1946 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2",
1947 						null, RegistryValueOptions.None), "#A8");
1948 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3",
1949 						null, RegistryValueOptions.None), "#A9");
1950 
1951 					Environment.SetEnvironmentVariable ("MONO_TEST1", "789");
1952 					Environment.SetEnvironmentVariable ("MONO_TEST2", "666");
1953 
1954 					Assert.AreEqual ("789/666", createdKey.GetValue ("name1"), "#B1");
1955 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2"), "#B2");
1956 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3"), "#B3");
1957 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name1",
1958 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#B4");
1959 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2",
1960 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#B5");
1961 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3",
1962 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#B6");
1963 					Assert.AreEqual ("789/666", createdKey.GetValue ("name1",
1964 						null, RegistryValueOptions.None), "#B7");
1965 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2",
1966 						null, RegistryValueOptions.None), "#B8");
1967 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3",
1968 						null, RegistryValueOptions.None), "#B9");
1969 				}
1970 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
1971 					Assert.AreEqual ("789/666", createdKey.GetValue ("name1"), "#C1");
1972 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2"), "#C2");
1973 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3"), "#C3");
1974 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name1",
1975 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#C4");
1976 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2",
1977 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#C5");
1978 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3",
1979 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#C6");
1980 					Assert.AreEqual ("789/666", createdKey.GetValue ("name1",
1981 						null, RegistryValueOptions.None), "#C7");
1982 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2",
1983 						null, RegistryValueOptions.None), "#C8");
1984 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3",
1985 						null, RegistryValueOptions.None), "#C9");
1986 
1987 					Environment.SetEnvironmentVariable ("MONO_TEST1", "123");
1988 					Environment.SetEnvironmentVariable ("MONO_TEST2", "456");
1989 
1990 					Assert.AreEqual ("123/456", createdKey.GetValue ("name1"), "#D1");
1991 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2"), "#D2");
1992 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3"), "#D3");
1993 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name1",
1994 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#D4");
1995 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2",
1996 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#D5");
1997 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3",
1998 						null, RegistryValueOptions.DoNotExpandEnvironmentNames), "#D6");
1999 					Assert.AreEqual ("123/456", createdKey.GetValue ("name1",
2000 						null, RegistryValueOptions.None), "#D7");
2001 					Assert.AreEqual ("%MONO_TEST1%/%MONO_TEST2%", createdKey.GetValue ("name2",
2002 						null, RegistryValueOptions.None), "#D8");
2003 					Assert.AreEqual ("just some text", createdKey.GetValue ("name3",
2004 						null, RegistryValueOptions.None), "#D9");
2005 				}
2006 			} finally {
2007 				try {
2008 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
2009 					if (createdKey != null) {
2010 						createdKey.Close ();
2011 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2012 					}
2013 				} catch {
2014 				}
2015 			}
2016 		}
2017 
2018 		[Test]
GetValueNames()2019 		public void GetValueNames ()
2020 		{
2021 			string subKeyName = Guid.NewGuid ().ToString ();
2022 
2023 			try {
2024 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2025 					string [] names = createdKey.GetValueNames ();
2026 					Assert.IsNotNull (names, "#A1");
2027 					Assert.AreEqual (0, names.Length, "#A2");
2028 
2029 					createdKey.SetValue ("name1", "value1");
2030 					createdKey.SetValue ("name2", "value2");
2031 					createdKey.SetValue ("namelong", "value3");
2032 					createdKey.SetValue ("name3", "value4");
2033 
2034 					Assert.AreEqual (4, createdKey.ValueCount, "#B1");
2035 					names = createdKey.GetValueNames ();
2036 					Assert.IsNotNull (names, "#B2");
2037 					Assert.AreEqual (4, names.Length, "#B3");
2038 				}
2039 
2040 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName, true)) {
2041 					string [] names = createdKey.GetValueNames ();
2042 					Assert.IsNotNull (names, "#C1");
2043 					Assert.AreEqual (4, names.Length, "#C2");
2044 
2045 					// Mono's Unix registry API uses a hashtable to store the
2046 					// values (and their names), so names are not returned in
2047 					// order
2048 					//
2049 					// to test whether the names returned by GetValueNames
2050 					// match what we expect, we use these names to remove the
2051 					// the values from the created keys and such we should end
2052 					// up with zero values
2053 					for (int i = 0; i < names.Length; i++) {
2054 						string valueName = names [i];
2055 						createdKey.DeleteValue (valueName);
2056 					}
2057 
2058 					// all values should be removed now
2059 					Assert.AreEqual (0, createdKey.ValueCount, "#C3");
2060 				}
2061 			} finally {
2062 				try {
2063 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
2064 					if (createdKey != null) {
2065 						createdKey.Close ();
2066 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2067 					}
2068 				} catch {
2069 				}
2070 			}
2071 		}
2072 
2073 		[Test]
GetValueNames_Key_Removed()2074 		public void GetValueNames_Key_Removed ()
2075 		{
2076 			string subKeyName = Guid.NewGuid ().ToString ();
2077 
2078 			try {
2079 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2080 					createdKey.SetValue ("name1", "value1");
2081 					createdKey.SetValue ("name2", "value2");
2082 
2083 					string [] names = createdKey.GetValueNames ();
2084 					Assert.IsNotNull (names, "#A1");
2085 					Assert.AreEqual (2, names.Length, "#A2");
2086 				}
2087 
2088 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
2089 					string [] names = createdKey.GetValueNames ();
2090 					Assert.IsNotNull (names, "#B1");
2091 					Assert.AreEqual (2, names.Length, "#B2");
2092 
2093 					Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2094 
2095 					try {
2096 						createdKey.GetValueNames ();
2097 						Assert.Fail ("#C1");
2098 					} catch (IOException ex) {
2099 						// Illegal operation attempted on a registry key that
2100 						// has been marked for deletion
2101 						Assert.AreEqual (typeof (IOException), ex.GetType (), "#C2");
2102 						Assert.IsNotNull (ex.Message, "#C3");
2103 						Assert.IsNull (ex.InnerException, "#C4");
2104 					}
2105 				}
2106 			} finally {
2107 				try {
2108 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
2109 					if (createdKey != null) {
2110 						createdKey.Close ();
2111 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2112 					}
2113 				} catch {
2114 				}
2115 			}
2116 		}
2117 
2118 		[Test] // bug #78519
GetSubKeyNamesTest()2119 		public void GetSubKeyNamesTest ()
2120 		{
2121 			string subKeyName = Guid.NewGuid ().ToString ();
2122 
2123 			RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName);
2124 			try {
2125 				// check if key was successfully created
2126 				Assert.IsNotNull (createdKey, "#A");
2127 
2128 				RegistryKey subKey = createdKey.CreateSubKey ("foo");
2129 				Assert.IsNotNull (subKey, "#B1");
2130 				Assert.AreEqual (1, createdKey.SubKeyCount, "#B2");
2131 				string[] subKeyNames = createdKey.GetSubKeyNames ();
2132 				Assert.IsNotNull (subKeyNames, "#B3");
2133 				Assert.AreEqual (1, subKeyNames.Length, "#B4");
2134 				Assert.AreEqual ("foo", subKeyNames[0], "#B5");
2135 
2136 				subKey = createdKey.CreateSubKey ("longfoo");
2137 				Assert.IsNotNull (subKey, "#C1");
2138 				Assert.AreEqual (2, createdKey.SubKeyCount, "#C2");
2139 				subKeyNames = createdKey.GetSubKeyNames ();
2140 				Assert.IsNotNull (subKeyNames, "#C3");
2141 				Assert.AreEqual (2, subKeyNames.Length, "#C4");
2142 				Assert.AreEqual ("foo", subKeyNames [0], "#C5");
2143 				Assert.AreEqual ("longfoo", subKeyNames [1], "#C6");
2144 
2145 				subKey = createdKey.CreateSubKey ("sfoo");
2146 				Assert.IsNotNull (subKey, "#D1");
2147 				Assert.AreEqual (3, createdKey.SubKeyCount, "#D2");
2148 				subKeyNames = createdKey.GetSubKeyNames ();
2149 				Assert.IsNotNull (subKeyNames, "#D3");
2150 				Assert.AreEqual (3, subKeyNames.Length, "#D4");
2151 				Assert.AreEqual ("foo", subKeyNames [0], "#D5");
2152 				Assert.AreEqual ("longfoo", subKeyNames [1], "#D6");
2153 				Assert.AreEqual ("sfoo", subKeyNames [2], "#D7");
2154 
2155 				foreach (string name in subKeyNames) {
2156 					createdKey.DeleteSubKeyTree (name);
2157 				}
2158 				Assert.AreEqual (0, createdKey.SubKeyCount, "#E");
2159 			} finally {
2160 				// clean-up
2161 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2162 			}
2163 		}
2164 
2165 		[Test]
OpenRemoteBaseKey()2166 		public void OpenRemoteBaseKey ()
2167 		{
2168 			// access to registry of remote machines is not implemented on unix
2169 			if (RunningOnUnix)
2170 				Assert.Ignore ("Running on Unix.");
2171 
2172 			RegistryKey hive = RegistryKey.OpenRemoteBaseKey (
2173 				RegistryHive.CurrentUser, Environment.MachineName);
2174 			Assert.IsNotNull (hive, "#1");
2175 
2176 			RegistryKey key = hive.OpenSubKey ("SOFTWARE");
2177 			Assert.IsNotNull (key, "#2");
2178 			key.Close ();
2179 
2180 			hive.Close ();
2181 		}
2182 
2183 		[Test]
OpenRemoteBaseKey_MachineName_Null()2184 		public void OpenRemoteBaseKey_MachineName_Null ()
2185 		{
2186 			try {
2187 				RegistryKey.OpenRemoteBaseKey (RegistryHive.CurrentUser, null);
2188 				Assert.Fail ("#1");
2189 			} catch (ArgumentNullException ex) {
2190 				Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
2191 				Assert.IsNull (ex.InnerException, "#3");
2192 				Assert.IsNotNull (ex.Message, "#4");
2193 				Assert.AreEqual ("machineName", ex.ParamName, "#5");
2194 			}
2195 		}
2196 
2197 		[Test]
2198 		// This hangs on windows
2199 		[Category ("NotWorking")]
OpenRemoteBaseKey_MachineName_DoesNotExist()2200 		public void OpenRemoteBaseKey_MachineName_DoesNotExist ()
2201 		{
2202 			// access to registry of remote machines is not implemented on unix
2203 			if (RunningOnUnix)
2204 				Assert.Ignore ("Running on Unix.");
2205 
2206 			try {
2207 				RegistryKey.OpenRemoteBaseKey (RegistryHive.CurrentUser,
2208 					"DOESNOTEXIST");
2209 				Assert.Fail ("#1");
2210 			} catch (IOException ex) {
2211 				// The network path was not found
2212 				Assert.AreEqual (typeof (IOException), ex.GetType (), "#2");
2213 				Assert.IsNotNull (ex.Message, "#3");
2214 				Assert.IsNull (ex.InnerException, "#4");
2215 			}
2216 		}
2217 
2218 		[Test] // bug #322839
SetValue1_EntityReferences()2219 		public void SetValue1_EntityReferences ()
2220 		{
2221 			string subKeyName = Guid.NewGuid ().ToString ();
2222 
2223 			try {
2224 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2225 					// we created a new subkey, so value should not exist
2226 					Assert.IsNull (createdKey.GetValue ("FirstName&\"<LastName>\""), "#A1");
2227 					// create value
2228 					createdKey.SetValue ("FirstName&\"<LastName>\"", "<'Miguel' & \"de Icaza\">!");
2229 					// get value
2230 					object name = createdKey.GetValue ("FirstName&\"<LastName>\"");
2231 					// value should exist
2232 					Assert.IsNotNull (name, "#A2");
2233 					// type of value should be string
2234 					Assert.AreEqual (typeof (string), name.GetType (), "#A3");
2235 					// ensure value matches
2236 					Assert.AreEqual ("<'Miguel' & \"de Icaza\">!", name, "#A4");
2237 
2238 					// we created a new subkey, so value should not exist
2239 					Assert.IsNull (createdKey.GetValue ("Info"), "#B1");
2240 					// create value
2241 					createdKey.SetValue ("Info", new string [] { "Mono&<Novell>!", "<CLR&BCL>" });
2242 					// get value
2243 					object info = createdKey.GetValue ("Info");
2244 					// value should exist
2245 					Assert.IsNotNull (info, "#B2");
2246 					// type of value should be string
2247 					Assert.AreEqual (typeof (string []), info.GetType (), "#B3");
2248 					// ensure value matches
2249 					Assert.AreEqual (new string [] { "Mono&<Novell>!", "<CLR&BCL>" }, info, "#B4");
2250 				}
2251 
2252 				using (RegistryKey openedKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
2253 					object name = openedKey.GetValue ("FirstName&\"<LastName>\"");
2254 					Assert.IsNotNull (name, "#C1");
2255 					Assert.AreEqual (typeof (string), name.GetType (), "#C2");
2256 					Assert.AreEqual ("<'Miguel' & \"de Icaza\">!", name, "#C3");
2257 
2258 					object info = openedKey.GetValue ("Info");
2259 					Assert.IsNotNull (info, "#D1");
2260 					Assert.AreEqual (typeof (string []), info.GetType (), "#D2");
2261 					Assert.AreEqual (new string [] { "Mono&<Novell>!", "<CLR&BCL>" }, info, "#D3");
2262 				}
2263 			} finally {
2264 				// clean-up
2265 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2266 			}
2267 		}
2268 
2269 		[Test] // SetValue (String, Object)
SetValue1_Name_Null()2270 		public void SetValue1_Name_Null ()
2271 		{
2272 			string subKeyName = Guid.NewGuid ().ToString ();
2273 
2274 			RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName);
2275 			try {
2276 				createdKey.SetValue (null, "value1");
2277 				string [] names = createdKey.GetValueNames ();
2278 				Assert.IsNotNull (names, "#A1");
2279 				Assert.AreEqual (1, names.Length, "#A2");
2280 				Assert.IsNotNull (names [0], "#A3");
2281 				Assert.AreEqual (string.Empty, names [0], "#A4");
2282 				Assert.IsNotNull (createdKey.GetValue (string.Empty), "#A5");
2283 				Assert.AreEqual ("value1", createdKey.GetValue (string.Empty), "#A6");
2284 				Assert.IsNotNull (createdKey.GetValue (null), "#A7");
2285 				Assert.AreEqual ("value1", createdKey.GetValue (null), "#A8");
2286 
2287 				createdKey.SetValue (string.Empty, "value2");
2288 				names = createdKey.GetValueNames ();
2289 				Assert.IsNotNull (names, "#B1");
2290 				Assert.AreEqual (1, names.Length, "#B2");
2291 				Assert.IsNotNull (names [0], "#B3");
2292 				Assert.AreEqual (string.Empty, names [0], "#B4");
2293 				Assert.IsNotNull (createdKey.GetValue (string.Empty), "#B5");
2294 				Assert.AreEqual ("value2", createdKey.GetValue (string.Empty), "#B6");
2295 				Assert.IsNotNull (createdKey.GetValue (null), "#B7");
2296 				Assert.AreEqual ("value2", createdKey.GetValue (null), "#B8");
2297 			} finally {
2298 				// clean-up
2299 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2300 			}
2301 		}
2302 
2303 		[Test] // SetValue (String, Object)
SetValue1_Name_Empty()2304 		public void SetValue1_Name_Empty ()
2305 		{
2306 			string subKeyName = Guid.NewGuid ().ToString ();
2307 
2308 			RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName);
2309 			try {
2310 				createdKey.SetValue (string.Empty, "value1");
2311 				string [] names = createdKey.GetValueNames ();
2312 				Assert.IsNotNull (names, "#A1");
2313 				Assert.AreEqual (1, names.Length, "#A2");
2314 				Assert.IsNotNull (names [0], "#A3");
2315 				Assert.AreEqual (string.Empty, names [0], "#A4");
2316 				Assert.IsNotNull (createdKey.GetValue (string.Empty), "#A5");
2317 				Assert.AreEqual ("value1", createdKey.GetValue (string.Empty), "#A6");
2318 				Assert.IsNotNull (createdKey.GetValue (null), "#A7");
2319 				Assert.AreEqual ("value1", createdKey.GetValue (null), "#A8");
2320 
2321 				createdKey.SetValue (null, "value2");
2322 				names = createdKey.GetValueNames ();
2323 				Assert.IsNotNull (names, "#B1");
2324 				Assert.AreEqual (1, names.Length, "#B2");
2325 				Assert.IsNotNull (names [0], "#B3");
2326 				Assert.AreEqual (string.Empty, names [0], "#B4");
2327 				Assert.IsNotNull (createdKey.GetValue (string.Empty), "#B5");
2328 				Assert.AreEqual ("value2", createdKey.GetValue (string.Empty), "#B6");
2329 				Assert.IsNotNull (createdKey.GetValue (null), "#B7");
2330 				Assert.AreEqual ("value2", createdKey.GetValue (null), "#B8");
2331 			} finally {
2332 				// clean-up
2333 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2334 			}
2335 		}
2336 
2337 		[Test] // SetValue (String, Object)
SetValue1_Name_MaxLength()2338 		public void SetValue1_Name_MaxLength ()
2339 		{
2340 			string subKeyName = Guid.NewGuid ().ToString ();
2341 
2342 			try {
2343 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2344 					string name = new string ('a', 254);
2345 
2346 					createdKey.SetValue (name, "value1");
2347 					Assert.IsNotNull (createdKey.GetValue (name), "#A1");
2348 					createdKey.DeleteValue (name);
2349 					Assert.IsNull (createdKey.GetValue (name), "#A2");
2350 
2351 					name = new string ('a', 255);
2352 
2353 					createdKey.SetValue (name, "value2");
2354 					Assert.IsNotNull (createdKey.GetValue (name), "#B1");
2355 					createdKey.DeleteValue (name);
2356 					Assert.IsNull (createdKey.GetValue (name), "#B2");
2357 
2358 					name = new string ('a', 256);
2359 
2360 					try {
2361 						createdKey.SetValue (name, "value2");
2362 						Assert.Fail ("#C1");
2363 					} catch (ArgumentException ex) {
2364 						// 1.x: Registry subkeys should not be
2365 						// greater than or equal to 255 characters
2366 						//
2367 						// 2.x: Registry subkeys should not be
2368 						// greater than 255 characters
2369 						Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#C2");
2370 						Assert.IsNull (ex.InnerException, "#C3");
2371 						Assert.IsNotNull (ex.Message, "#C4");
2372 						Assert.IsTrue (ex.Message.IndexOf ("255") != -1, "#C5");
2373 						Assert.IsNull (ex.ParamName, "#C6");
2374 					}
2375 				}
2376 			} finally {
2377 				try {
2378 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
2379 					if (createdKey != null) {
2380 						createdKey.Close ();
2381 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2382 					}
2383 				} catch {
2384 				}
2385 			}
2386 		}
2387 
2388 		[Test] // SetValue (String, Object)
SetValue1_Value_Null()2389 		public void SetValue1_Value_Null ()
2390 		{
2391 			string subKeyName = Guid.NewGuid ().ToString ();
2392 
2393 			RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName);
2394 			try {
2395 				try {
2396 					createdKey.SetValue ("Name", null);
2397 					Assert.Fail ("#1");
2398 				} catch (ArgumentNullException ex) {
2399 					Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
2400 					Assert.IsNull (ex.InnerException, "#3");
2401 					Assert.IsNotNull (ex.Message, "#4");
2402 					Assert.AreEqual ("value", ex.ParamName, "#5");
2403 				}
2404 			} finally {
2405 				// clean-up
2406 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2407 			}
2408 		}
2409 
2410 		[Test] // SetValue (String, Object)
SetValue1_Boolean()2411 		public void SetValue1_Boolean ()
2412 		{
2413 			string subKeyName = Guid.NewGuid ().ToString ();
2414 
2415 			try {
2416 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2417 					// we created a new subkey, so value should not exist
2418 					Assert.IsNull (createdKey.GetValue ("Installed"), "#A1");
2419 					// create value
2420 					createdKey.SetValue ("Installed", true);
2421 					// get value
2422 					object value = createdKey.GetValue ("Installed");
2423 					// value should exist
2424 					Assert.IsNotNull (value, "#A2");
2425 					// type of value should be string
2426 					Assert.AreEqual (typeof (string), value.GetType (), "#A3");
2427 					// ensure value matches
2428 					Assert.AreEqual (true.ToString (), value, "#A4");
2429 				}
2430 
2431 				using (RegistryKey openedKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
2432 					object value = openedKey.GetValue ("Installed");
2433 					Assert.IsNotNull (value, "#B1");
2434 					Assert.AreEqual (typeof (string), value.GetType (), "#B2");
2435 					Assert.AreEqual (true.ToString (), value, "#B3");
2436 				}
2437 			} finally {
2438 				// clean-up
2439 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2440 			}
2441 		}
2442 
2443 		[Test] // SetValue (String, Object)
SetValue1_Byte()2444 		public void SetValue1_Byte ()
2445 		{
2446 			string subKeyName = Guid.NewGuid ().ToString ();
2447 
2448 			try {
2449 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2450 					// we created a new subkey, so value should not exist
2451 					Assert.IsNull (createdKey.GetValue ("Flags"), "#A1");
2452 					// create value
2453 					createdKey.SetValue ("Flags", (byte) 5);
2454 					// get value
2455 					object value = createdKey.GetValue ("Flags");
2456 					// value should exist
2457 					Assert.IsNotNull (value, "#A2");
2458 					// type of value should be string
2459 					Assert.AreEqual (typeof (string), value.GetType (), "#A3");
2460 					// ensure value matches
2461 					Assert.AreEqual ("5", value, "#A4");
2462 				}
2463 
2464 				using (RegistryKey openedKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
2465 					object value = openedKey.GetValue ("Flags");
2466 					Assert.IsNotNull (value, "#B1");
2467 					Assert.AreEqual (typeof (string), value.GetType (), "#B2");
2468 					Assert.AreEqual ("5", value, "#B3");
2469 				}
2470 			} finally {
2471 				// clean-up
2472 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2473 			}
2474 		}
2475 
2476 		[Test] // SetValue (String, Object)
SetValue1_ByteArray()2477 		public void SetValue1_ByteArray ()
2478 		{
2479 			string subKeyName = Guid.NewGuid ().ToString ();
2480 
2481 			try {
2482 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2483 					// we created a new subkey, so value should not exist
2484 					Assert.IsNull (createdKey.GetValue ("Flags"), "#A1");
2485 					// create value
2486 					createdKey.SetValue ("Flags", new byte [] { 1, 5 });
2487 					// get value
2488 					object value = createdKey.GetValue ("Flags");
2489 					// value should exist
2490 					Assert.IsNotNull (value, "#A2");
2491 					// type of value should be string
2492 					Assert.AreEqual (typeof (byte []), value.GetType (), "#3");
2493 					// ensure value matches
2494 					Assert.AreEqual (new byte [] { 1, 5 }, value, "#4");
2495 				}
2496 
2497 				using (RegistryKey openedKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
2498 					object value = openedKey.GetValue ("Flags");
2499 					Assert.IsNotNull (value, "#B1");
2500 					Assert.AreEqual (typeof (byte []), value.GetType (), "#B2");
2501 					Assert.AreEqual (new byte [] { 1, 5 }, value, "#B3");
2502 				}
2503 			} finally {
2504 				// clean-up
2505 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2506 			}
2507 		}
2508 
2509 		[Test] // SetValue (String, Object)
SetValue1_DateTime()2510 		public void SetValue1_DateTime ()
2511 		{
2512 			string subKeyName = Guid.NewGuid ().ToString ();
2513 
2514 			try {
2515 				object rawValue = DateTime.UtcNow;
2516 
2517 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2518 					// we created a new subkey, so value should not exist
2519 					Assert.IsNull (createdKey.GetValue ("Path"), "#A1");
2520 					// create value
2521 					createdKey.SetValue ("Path", rawValue);
2522 					// get value
2523 					object value = createdKey.GetValue ("Path");
2524 					// value should exist
2525 					Assert.IsNotNull (value, "#A2");
2526 					// type of value should be string
2527 					Assert.AreEqual (typeof (string), value.GetType (), "#A3");
2528 					// ensure value matches
2529 					Assert.AreEqual (rawValue.ToString (), value, "#A4");
2530 				}
2531 
2532 				using (RegistryKey openedKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
2533 					object value = openedKey.GetValue ("Path");
2534 					Assert.IsNotNull (value, "#B1");
2535 					Assert.AreEqual (typeof (string), value.GetType (), "#B2");
2536 					Assert.AreEqual (rawValue.ToString (), value, "#B3");
2537 				}
2538 			} finally {
2539 				// clean-up
2540 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2541 			}
2542 		}
2543 
2544 		[Test]
SetValue_Int32()2545 		public void SetValue_Int32 ()
2546 		{
2547 			string subKeyName = Guid.NewGuid ().ToString ();
2548 
2549 			try {
2550 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2551 					// we created a new subkey, so value should not exist
2552 					Assert.IsNull (createdKey.GetValue ("RefCount"), "#A1");
2553 					// create value
2554 					createdKey.SetValue ("RefCount", 5);
2555 					// get value
2556 					object value = createdKey.GetValue ("RefCount");
2557 					// value should exist
2558 					Assert.IsNotNull (value, "#A2");
2559 					// type of value should be int
2560 					Assert.AreEqual (typeof (int), value.GetType (), "#A3");
2561 					// ensure value matches
2562 					Assert.AreEqual (5, value, "#A4");
2563 				}
2564 
2565 				using (RegistryKey openedKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
2566 					object value = openedKey.GetValue ("RefCount");
2567 					Assert.IsNotNull (value, "#B1");
2568 					Assert.AreEqual (typeof (int), value.GetType (), "#B2");
2569 					Assert.AreEqual (5, value, "#B3");
2570 				}
2571 			} finally {
2572 				// clean-up
2573 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2574 			}
2575 		}
2576 
2577 		[Test] // SetValue (String, Object)
SetValue1_Int64()2578 		public void SetValue1_Int64 ()
2579 		{
2580 			string subKeyName = Guid.NewGuid ().ToString ();
2581 
2582 			try {
2583 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2584 					// we created a new subkey, so value should not exist
2585 					Assert.IsNull (createdKey.GetValue ("Ticks"), "#A1");
2586 					// create value
2587 					createdKey.SetValue ("Ticks", 500L);
2588 					// get value
2589 					object value = createdKey.GetValue ("Ticks");
2590 					// value should exist
2591 					Assert.IsNotNull (value, "#A2");
2592 					// type of value should be string
2593 					Assert.AreEqual (typeof (string), value.GetType (), "#A3");
2594 					// ensure value matches
2595 					Assert.AreEqual ("500", value, "#A4");
2596 				}
2597 
2598 				using (RegistryKey openedKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
2599 					object value = openedKey.GetValue ("Ticks");
2600 					Assert.IsNotNull (value, "#B1");
2601 					Assert.AreEqual (typeof (string), value.GetType (), "#B2");
2602 					Assert.AreEqual ("500", value, "#B3");
2603 				}
2604 			} finally {
2605 				// clean-up
2606 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2607 			}
2608 		}
2609 
2610 		[Test] // SetValue (String, Object)
SetValue1_String()2611 		public void SetValue1_String ()
2612 		{
2613 			string subKeyName = Guid.NewGuid ().ToString ();
2614 
2615 			try {
2616 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2617 					// we created a new subkey, so value should not exist
2618 					Assert.IsNull (createdKey.GetValue ("Path"), "#A1");
2619 					// create value
2620 					createdKey.SetValue ("Path", "/usr/lib/whatever");
2621 					// get value
2622 					object path = createdKey.GetValue ("Path");
2623 					// value should exist
2624 					Assert.IsNotNull (path, "#A2");
2625 					// type of value should be string
2626 					Assert.AreEqual (typeof (string), path.GetType (), "#A3");
2627 					// ensure value matches
2628 					Assert.AreEqual ("/usr/lib/whatever", path, "#A4");
2629 				}
2630 
2631 				using (RegistryKey openedKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
2632 					object path = openedKey.GetValue ("Path");
2633 					Assert.IsNotNull (path, "#B1");
2634 					Assert.AreEqual (typeof (string), path.GetType (), "#B2");
2635 					Assert.AreEqual ("/usr/lib/whatever", path, "#B3");
2636 				}
2637 			} finally {
2638 				// clean-up
2639 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2640 			}
2641 		}
2642 
2643 		[Test] // SetValue (String, Object)
SetValue1_StringArray()2644 		public void SetValue1_StringArray ()
2645 		{
2646 			string subKeyName = Guid.NewGuid ().ToString ();
2647 
2648 			try {
2649 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2650 					// we created a new subkey, so value should not exist
2651 					Assert.IsNull (createdKey.GetValue ("DependsOnGroup"), "#A1");
2652 					// create value
2653 					createdKey.SetValue ("DependsOnGroup", new string [] { "A", "B" });
2654 					// get value
2655 					object value = createdKey.GetValue ("DependsOnGroup");
2656 					// value should exist
2657 					Assert.IsNotNull (value, "#A2");
2658 					// type of value should be string
2659 					Assert.AreEqual (typeof (string []), value.GetType (), "#A3");
2660 					// ensure value matches
2661 					Assert.AreEqual (new string [] { "A", "B" }, value, "#A4");
2662 				}
2663 
2664 				using (RegistryKey openedKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
2665 					object value = openedKey.GetValue ("DependsOnGroup");
2666 					Assert.IsNotNull (value, "#B1");
2667 					Assert.AreEqual (typeof (string []), value.GetType (), "#B2");
2668 					Assert.AreEqual (new string [] { "A", "B" }, value, "#B3");
2669 				}
2670 			} finally {
2671 				// clean-up
2672 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2673 			}
2674 		}
2675 
2676 		[Test] // SetValue (String, Object)
SetValue1_Key_ReadOnly()2677 		public void SetValue1_Key_ReadOnly ()
2678 		{
2679 			string subKeyName = Guid.NewGuid ().ToString ();
2680 
2681 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software")) {
2682 				try {
2683 					softwareKey.SetValue ("name1", "value1");
2684 					Assert.Fail ("#1");
2685 				} catch (UnauthorizedAccessException ex) {
2686 					// Cannot write to the registry key
2687 					Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#2");
2688 					Assert.IsNotNull (ex.Message, "#3");
2689 					Assert.IsNull (ex.InnerException, "#4");
2690 				}
2691 			}
2692 
2693 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
2694 				try {
2695 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
2696 					}
2697 
2698 					using (RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName)) {
2699 						try {
2700 							createdKey.SetValue ("name1", "value1");
2701 							Assert.Fail ("#1");
2702 						} catch (UnauthorizedAccessException ex) {
2703 							// Cannot write to the registry key
2704 							Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#2");
2705 							Assert.IsNotNull (ex.Message, "#3");
2706 							Assert.IsNull (ex.InnerException, "#4");
2707 						}
2708 					}
2709 				} finally {
2710 					try {
2711 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
2712 						if (createdKey != null) {
2713 							createdKey.Close ();
2714 							softwareKey.DeleteSubKeyTree (subKeyName);
2715 						}
2716 					} catch {
2717 					}
2718 				}
2719 			}
2720 		}
2721 
2722 		[Test] // SetValue (String, Object)
SetValue1_Key_Removed()2723 		public void SetValue1_Key_Removed ()
2724 		{
2725 			string subKeyName = Guid.NewGuid ().ToString ();
2726 
2727 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
2728 				try {
2729 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
2730 						softwareKey.DeleteSubKeyTree (subKeyName);
2731 						Assert.IsNull (softwareKey.OpenSubKey (subKeyName), "#1");
2732 						try {
2733 							createdKey.SetValue ("name1", "value1");
2734 							Assert.Fail ("#2");
2735 						} catch (IOException ex) {
2736 							// Illegal operation attempted on a registry key that
2737 							// has been marked for deletion
2738 							Assert.AreEqual (typeof (IOException), ex.GetType (), "#3");
2739 							Assert.IsNotNull (ex.Message, "#4");
2740 							Assert.IsNull (ex.InnerException, "#5");
2741 						}
2742 					}
2743 				} finally {
2744 					try {
2745 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
2746 						if (createdKey != null) {
2747 							createdKey.Close ();
2748 							softwareKey.DeleteSubKeyTree (subKeyName);
2749 						}
2750 					} catch {
2751 					}
2752 				}
2753 			}
2754 		}
2755 
2756 		[Test] // SetValue (String, Object, RegistryValueKind)
SetValue2_Key_ReadOnly()2757 		public void SetValue2_Key_ReadOnly ()
2758 		{
2759 			string subKeyName = Guid.NewGuid ().ToString ();
2760 
2761 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software")) {
2762 				try {
2763 					softwareKey.SetValue ("name1", "value1",
2764 						RegistryValueKind.String);
2765 					Assert.Fail ("#1");
2766 				} catch (UnauthorizedAccessException ex) {
2767 					// Cannot write to the registry key
2768 					Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#2");
2769 					Assert.IsNotNull (ex.Message, "#3");
2770 					Assert.IsNull (ex.InnerException, "#4");
2771 				}
2772 			}
2773 
2774 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
2775 				try {
2776 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
2777 					}
2778 
2779 					using (RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName)) {
2780 						try {
2781 							createdKey.SetValue ("name1", "value1",
2782 								RegistryValueKind.String);
2783 							Assert.Fail ("#1");
2784 						} catch (UnauthorizedAccessException ex) {
2785 							// Cannot write to the registry key
2786 							Assert.AreEqual (typeof (UnauthorizedAccessException), ex.GetType (), "#2");
2787 							Assert.IsNotNull (ex.Message, "#3");
2788 							Assert.IsNull (ex.InnerException, "#4");
2789 						}
2790 					}
2791 				} finally {
2792 					try {
2793 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
2794 						if (createdKey != null) {
2795 							createdKey.Close ();
2796 							softwareKey.DeleteSubKeyTree (subKeyName);
2797 						}
2798 					} catch {
2799 					}
2800 				}
2801 			}
2802 		}
2803 
2804 		[Test] // SetValue (String, Object, RegistryValueKind)
SetValue2_Key_Removed()2805 		public void SetValue2_Key_Removed ()
2806 		{
2807 			string subKeyName = Guid.NewGuid ().ToString ();
2808 
2809 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
2810 				try {
2811 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
2812 						softwareKey.DeleteSubKeyTree (subKeyName);
2813 						Assert.IsNull (softwareKey.OpenSubKey (subKeyName), "#1");
2814 						try {
2815 							createdKey.SetValue ("name1", "value1",
2816 								RegistryValueKind.String);
2817 							Assert.Fail ("#2");
2818 						} catch (IOException ex) {
2819 							// Illegal operation attempted on a registry key that
2820 							// has been marked for deletion
2821 							Assert.AreEqual (typeof (IOException), ex.GetType (), "#3");
2822 							Assert.IsNotNull (ex.Message, "#4");
2823 							Assert.IsNull (ex.InnerException, "#5");
2824 						}
2825 					}
2826 				} finally {
2827 					try {
2828 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
2829 						if (createdKey != null) {
2830 							createdKey.Close ();
2831 							softwareKey.DeleteSubKeyTree (subKeyName);
2832 						}
2833 					} catch {
2834 					}
2835 				}
2836 			}
2837 		}
2838 
2839 		[Test] // SetValue (String, Object, RegistryValueKind)
SetValue2_Name_Empty()2840 		public void SetValue2_Name_Empty ()
2841 		{
2842 			string subKeyName = Guid.NewGuid ().ToString ();
2843 
2844 			RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName);
2845 			try {
2846 				createdKey.SetValue (string.Empty, "value1",
2847 					RegistryValueKind.String);
2848 				string [] names = createdKey.GetValueNames ();
2849 				Assert.IsNotNull (names, "#A1");
2850 				Assert.AreEqual (1, names.Length, "#A2");
2851 				Assert.IsNotNull (names [0], "#A3");
2852 				Assert.AreEqual (string.Empty, names [0], "#A4");
2853 				Assert.IsNotNull (createdKey.GetValue (string.Empty), "#A5");
2854 				Assert.AreEqual ("value1", createdKey.GetValue (string.Empty), "#A6");
2855 				Assert.IsNotNull (createdKey.GetValue (null), "#A7");
2856 				Assert.AreEqual ("value1", createdKey.GetValue (null), "#A8");
2857 
2858 				createdKey.SetValue (null, "value2",
2859 					RegistryValueKind.String);
2860 				names = createdKey.GetValueNames ();
2861 				Assert.IsNotNull (names, "#B1");
2862 				Assert.AreEqual (1, names.Length, "#B2");
2863 				Assert.IsNotNull (names [0], "#B3");
2864 				Assert.AreEqual (string.Empty, names [0], "#B4");
2865 				Assert.IsNotNull (createdKey.GetValue (string.Empty), "#B5");
2866 				Assert.AreEqual ("value2", createdKey.GetValue (string.Empty), "#B6");
2867 				Assert.IsNotNull (createdKey.GetValue (null), "#B7");
2868 				Assert.AreEqual ("value2", createdKey.GetValue (null), "#B8");
2869 			} finally {
2870 				// clean-up
2871 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2872 			}
2873 		}
2874 
2875 		[Test] // SetValue (String, Object, RegistryValueKind)
SetValue2_Name_MaxLength()2876 		public void SetValue2_Name_MaxLength ()
2877 		{
2878 			string subKeyName = Guid.NewGuid ().ToString ();
2879 
2880 			try {
2881 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2882 					string name = new string ('a', 254);
2883 
2884 					createdKey.SetValue (name, "value1",
2885 						RegistryValueKind.String);
2886 					Assert.IsNotNull (createdKey.GetValue (name), "#A1");
2887 					createdKey.DeleteValue (name);
2888 					Assert.IsNull (createdKey.GetValue (name), "#A2");
2889 
2890 					name = new string ('a', 255);
2891 
2892 					createdKey.SetValue (name, "value2",
2893 						RegistryValueKind.String);
2894 					Assert.IsNotNull (createdKey.GetValue (name), "#B1");
2895 					createdKey.DeleteValue (name);
2896 					Assert.IsNull (createdKey.GetValue (name), "#B2");
2897 
2898 					name = new string ('a', 256);
2899 
2900 					try {
2901 						createdKey.SetValue (name, "value2",
2902 							RegistryValueKind.String);
2903 						Assert.Fail ("#C1");
2904 					} catch (ArgumentException ex) {
2905 						// Registry subkeys should not be
2906 						// greater than 255 characters
2907 						Assert.AreEqual (typeof (ArgumentException), ex.GetType (), "#C2");
2908 						Assert.IsNull (ex.InnerException, "#C3");
2909 						Assert.IsNotNull (ex.Message, "#C4");
2910 						Assert.IsTrue (ex.Message.IndexOf ("255") != -1, "#C5");
2911 						Assert.IsNull (ex.ParamName, "#C6");
2912 					}
2913 				}
2914 			} finally {
2915 				try {
2916 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
2917 					if (createdKey != null) {
2918 						createdKey.Close ();
2919 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2920 					}
2921 				} catch {
2922 				}
2923 			}
2924 		}
2925 
2926 		[Test] // SetValue (String, Object, RegistryValueKind)
SetValue2_Name_Null()2927 		public void SetValue2_Name_Null ()
2928 		{
2929 			string subKeyName = Guid.NewGuid ().ToString ();
2930 
2931 			RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName);
2932 			try {
2933 				createdKey.SetValue (null, "value1",
2934 					RegistryValueKind.String);
2935 				string [] names = createdKey.GetValueNames ();
2936 				Assert.IsNotNull (names, "#A1");
2937 				Assert.AreEqual (1, names.Length, "#A2");
2938 				Assert.IsNotNull (names [0], "#A3");
2939 				Assert.AreEqual (string.Empty, names [0], "#A4");
2940 				Assert.IsNotNull (createdKey.GetValue (string.Empty), "#A5");
2941 				Assert.AreEqual ("value1", createdKey.GetValue (string.Empty), "#A6");
2942 				Assert.IsNotNull (createdKey.GetValue (null), "#A7");
2943 				Assert.AreEqual ("value1", createdKey.GetValue (null), "#A8");
2944 
2945 				createdKey.SetValue (string.Empty, "value2",
2946 					RegistryValueKind.String);
2947 				names = createdKey.GetValueNames ();
2948 				Assert.IsNotNull (names, "#B1");
2949 				Assert.AreEqual (1, names.Length, "#B2");
2950 				Assert.IsNotNull (names [0], "#B3");
2951 				Assert.AreEqual (string.Empty, names [0], "#B4");
2952 				Assert.IsNotNull (createdKey.GetValue (string.Empty), "#B5");
2953 				Assert.AreEqual ("value2", createdKey.GetValue (string.Empty), "#B6");
2954 				Assert.IsNotNull (createdKey.GetValue (null), "#B7");
2955 				Assert.AreEqual ("value2", createdKey.GetValue (null), "#B8");
2956 			} finally {
2957 				// clean-up
2958 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2959 			}
2960 		}
2961 
2962 		[Test] // SetValue (String, Object, RegistryValueKind)
SetValue2_Value_Null()2963 		public void SetValue2_Value_Null ()
2964 		{
2965 			string subKeyName = Guid.NewGuid ().ToString ();
2966 
2967 			RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName);
2968 			try {
2969 				try {
2970 					createdKey.SetValue ("Name", null,
2971 						RegistryValueKind.String);
2972 					Assert.Fail ("#1");
2973 				} catch (ArgumentNullException ex) {
2974 					Assert.AreEqual (typeof (ArgumentNullException), ex.GetType (), "#2");
2975 					Assert.IsNull (ex.InnerException, "#3");
2976 					Assert.IsNotNull (ex.Message, "#4");
2977 					Assert.AreEqual ("value", ex.ParamName, "#5");
2978 				}
2979 			} finally {
2980 				// clean-up
2981 				Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
2982 			}
2983 		}
2984 
2985 		[Test]
SubKeyCount()2986 		public void SubKeyCount ()
2987 		{
2988 			string subKeyName = Guid.NewGuid ().ToString ();
2989 
2990 			try {
2991 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
2992 					// check if key was successfully created
2993 					Assert.IsNotNull (createdKey, "#A1");
2994 					using (RegistryKey subKey = createdKey.CreateSubKey ("monotemp1")) {
2995 						subKey.Close ();
2996 					}
2997 					Assert.AreEqual (1, createdKey.SubKeyCount, "#A2");
2998 					using (RegistryKey subKey = createdKey.CreateSubKey ("monotemp2")) {
2999 						subKey.Close ();
3000 					}
3001 					Assert.AreEqual (2, createdKey.SubKeyCount, "#A3");
3002 				}
3003 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
3004 					Assert.IsNotNull (createdKey, "#B1");
3005 					Assert.AreEqual (2, createdKey.SubKeyCount, "#B2");
3006 
3007 					using (RegistryKey createdKey2 = Registry.CurrentUser.OpenSubKey (subKeyName, true)) {
3008 						Assert.IsNotNull (createdKey2, "#B3");
3009 						Assert.AreEqual (2, createdKey2.SubKeyCount, "#B4");
3010 						createdKey2.DeleteSubKey ("monotemp1");
3011 						Assert.AreEqual (1, createdKey2.SubKeyCount, "#B5");
3012 					}
3013 					Assert.AreEqual (1, createdKey.SubKeyCount, "#B6");
3014 				}
3015 			} finally {
3016 				try {
3017 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
3018 					if (createdKey != null) {
3019 						createdKey.Close ();
3020 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
3021 					}
3022 				} catch {
3023 				}
3024 			}
3025 		}
3026 
3027 		[Test]
SubKeyCount_Key_Removed()3028 		public void SubKeyCount_Key_Removed ()
3029 		{
3030 			string subKeyName = Guid.NewGuid ().ToString ();
3031 
3032 			try {
3033 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
3034 					// check if key was successfully created
3035 					Assert.IsNotNull (createdKey, "#A1");
3036 					using (RegistryKey subKey = createdKey.CreateSubKey ("monotemp1")) {
3037 						subKey.Close ();
3038 					}
3039 					Assert.AreEqual (1, createdKey.SubKeyCount, "#A2");
3040 					using (RegistryKey subKey = createdKey.CreateSubKey ("monotemp2")) {
3041 						subKey.Close ();
3042 					}
3043 					Assert.AreEqual (2, createdKey.SubKeyCount, "#A3");
3044 				}
3045 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
3046 					Assert.IsNotNull (createdKey, "#B1");
3047 					Assert.AreEqual (2, createdKey.SubKeyCount, "#B2");
3048 
3049 					// remove created key
3050 					Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
3051 
3052 					try {
3053 						Assert.Fail ("#C1: " + createdKey.SubKeyCount);
3054 					} catch (IOException ex) {
3055 						// Illegal operation attempted on a registry key that
3056 						// has been marked for deletion
3057 						Assert.AreEqual (typeof (IOException), ex.GetType (), "#14");
3058 						Assert.IsNotNull (ex.Message, "#15");
3059 						Assert.IsNull (ex.InnerException, "#16");
3060 					}
3061 				}
3062 			} finally {
3063 				try {
3064 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
3065 					if (createdKey != null) {
3066 						createdKey.Close ();
3067 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
3068 					}
3069 				} catch {
3070 				}
3071 			}
3072 		}
3073 
3074 		[Test]
ValueCount()3075 		public void ValueCount ()
3076 		{
3077 			string subKeyName = Guid.NewGuid ().ToString ();
3078 
3079 			try {
3080 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
3081 					// check if key was successfully created
3082 					Assert.IsNotNull (createdKey, "#A1");
3083 					Assert.AreEqual (0, createdKey.ValueCount, "#A2");
3084 					createdKey.SetValue ("name1", "value1");
3085 					Assert.AreEqual (1, createdKey.ValueCount, "#A3");
3086 					createdKey.SetValue ("name2", "value2");
3087 					Assert.AreEqual (2, createdKey.ValueCount, "#A4");
3088 					createdKey.SetValue ("name2", "value2b");
3089 					Assert.AreEqual (2, createdKey.ValueCount, "#A5");
3090 					createdKey.SetValue ("name3", "value3");
3091 					Assert.AreEqual (3, createdKey.ValueCount, "#A6");
3092 				}
3093 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
3094 					Assert.IsNotNull (createdKey, "#B1");
3095 					Assert.AreEqual (3, createdKey.ValueCount, "#B2");
3096 
3097 					using (RegistryKey createdKey2 = Registry.CurrentUser.OpenSubKey (subKeyName, true)) {
3098 						Assert.IsNotNull (createdKey2, "#B3");
3099 						Assert.AreEqual (3, createdKey2.ValueCount, "#B4");
3100 						createdKey2.DeleteValue ("name2");
3101 						Assert.AreEqual (2, createdKey2.ValueCount, "#B5");
3102 					}
3103 					Assert.AreEqual (2, createdKey.ValueCount, "#B6");
3104 				}
3105 			} finally {
3106 				try {
3107 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
3108 					if (createdKey != null) {
3109 						createdKey.Close ();
3110 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
3111 					}
3112 				} catch {
3113 				}
3114 			}
3115 		}
3116 
3117 		[Test]
ValueCount_Key_Removed()3118 		public void ValueCount_Key_Removed ()
3119 		{
3120 			string subKeyName = Guid.NewGuid ().ToString ();
3121 
3122 			try {
3123 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
3124 					// check if key was successfully created
3125 					Assert.IsNotNull (createdKey, "#A1");
3126 					Assert.AreEqual (0, createdKey.ValueCount, "#A2");
3127 					createdKey.SetValue ("name1", "value1");
3128 					Assert.AreEqual (1, createdKey.ValueCount, "#A3");
3129 					createdKey.SetValue ("name2", "value2");
3130 					Assert.AreEqual (2, createdKey.ValueCount, "#A4");
3131 					createdKey.SetValue ("name2", "value2b");
3132 					Assert.AreEqual (2, createdKey.ValueCount, "#A5");
3133 					createdKey.SetValue ("name3", "value3");
3134 					Assert.AreEqual (3, createdKey.ValueCount, "#A6");
3135 				}
3136 				using (RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName)) {
3137 					Assert.IsNotNull (createdKey, "#B1");
3138 					Assert.AreEqual (3, createdKey.ValueCount, "#B2");
3139 
3140 					// remove created key
3141 					Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
3142 
3143 					try {
3144 						Assert.Fail ("#C1: " + createdKey.ValueCount);
3145 					} catch (IOException ex) {
3146 						// Illegal operation attempted on a registry key that
3147 						// has been marked for deletion
3148 						Assert.AreEqual (typeof (IOException), ex.GetType (), "#14");
3149 						Assert.IsNotNull (ex.Message, "#15");
3150 						Assert.IsNull (ex.InnerException, "#16");
3151 					}
3152 				}
3153 			} finally {
3154 				try {
3155 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
3156 					if (createdKey != null) {
3157 						createdKey.Close ();
3158 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
3159 					}
3160 				} catch {
3161 				}
3162 			}
3163 		}
3164 
3165 		[Test]
bug79051()3166 		public void bug79051 ()
3167 		{
3168 			string subKeyName = Guid.NewGuid ().ToString ();
3169 
3170 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
3171 				try {
3172 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
3173 						createdKey.SetValue ("test", "whatever");
3174 						createdKey.Close ();
3175 						softwareKey.DeleteSubKeyTree (subKeyName);
3176 					}
3177 				} finally {
3178 					try {
3179 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
3180 						if (createdKey != null) {
3181 							createdKey.Close ();
3182 							softwareKey.DeleteSubKeyTree (subKeyName);
3183 						}
3184 					} catch {
3185 					}
3186 				}
3187 			}
3188 		}
3189 
3190 		// Bug Xamarin 3632
3191 		[Test]
3192 		[Category ("InterpreterNotWorking")]
TypeCastTests()3193 		public void TypeCastTests ()
3194 		{
3195 			string subKeyName = Guid.NewGuid ().ToString ();
3196 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
3197 				try {
3198 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
3199 						createdKey.SetValue ("test-int", (int) 1, RegistryValueKind.DWord);
3200 						createdKey.SetValue ("test-uint", (uint) 1, RegistryValueKind.DWord);
3201 						createdKey.SetValue ("test-byte", (byte) 1, RegistryValueKind.DWord);
3202 						createdKey.SetValue ("test-sbyte", (sbyte) 1, RegistryValueKind.DWord);
3203 						createdKey.SetValue ("test-short", (short) 1, RegistryValueKind.DWord);
3204 						createdKey.SetValue ("test-ushort", (ushort) 1, RegistryValueKind.DWord);
3205 						createdKey.SetValue ("test-long", (long) 1, RegistryValueKind.DWord);
3206 						createdKey.SetValue ("test-ulong", (ulong) 1, RegistryValueKind.DWord);
3207 						createdKey.SetValue ("test-decimal", (decimal) 1, RegistryValueKind.DWord);
3208 						createdKey.SetValue ("test-float", (float) 1, RegistryValueKind.DWord);
3209 						createdKey.SetValue ("test-bool", true, RegistryValueKind.DWord);
3210 
3211 						createdKey.SetValue ("dtest-int", (int) 1, RegistryValueKind.QWord);
3212 						createdKey.SetValue ("dtest-uint", (uint) 1, RegistryValueKind.QWord);
3213 						createdKey.SetValue ("dtest-byte", (byte) 1, RegistryValueKind.QWord);
3214 						createdKey.SetValue ("dtest-sbyte", (sbyte) 1, RegistryValueKind.QWord);
3215 						createdKey.SetValue ("dtest-short", (short) 1, RegistryValueKind.QWord);
3216 						createdKey.SetValue ("dtest-ushort", (ushort) 1, RegistryValueKind.QWord);
3217 						createdKey.SetValue ("dtest-long", (long) 1, RegistryValueKind.QWord);
3218 						createdKey.SetValue ("dtest-ulong", (ulong) 1, RegistryValueKind.QWord);
3219 						createdKey.SetValue ("dtest-decimal", (decimal) 1, RegistryValueKind.QWord);
3220 						createdKey.SetValue ("dtest-float", (float) 1, RegistryValueKind.QWord);
3221 						createdKey.SetValue ("dtest-bool", true, RegistryValueKind.QWord);
3222 
3223 						object r = createdKey.GetValue ("test-int");
3224 						Assert.AreEqual (r is int, true);
3225 						Assert.AreEqual ((int) r, 1);
3226 
3227 						r = createdKey.GetValue ("test-uint");
3228 						Assert.AreEqual (r is int, true);
3229 						Assert.AreEqual ((int) r, 1);
3230 						r = createdKey.GetValue ("test-byte");
3231 						Assert.AreEqual (r is int, true);
3232 						Assert.AreEqual ((int) r, 1);
3233 						r = createdKey.GetValue ("test-sbyte");
3234 						Assert.AreEqual (r is int, true);
3235 						Assert.AreEqual ((int) r, 1);
3236 						r = createdKey.GetValue ("test-short");
3237 						Assert.AreEqual (r is int, true);
3238 						Assert.AreEqual ((int) r, 1);
3239 						r = createdKey.GetValue ("test-ushort");
3240 						Assert.AreEqual (r is int, true);
3241 						Assert.AreEqual ((int) r, 1);
3242 						r = createdKey.GetValue ("test-long");
3243 						Assert.AreEqual (r is int, true);
3244 						Assert.AreEqual ((int) r, 1);
3245 						r = createdKey.GetValue ("test-ulong");
3246 						Assert.AreEqual (r is int, true);
3247 						Assert.AreEqual ((int) r, 1);
3248 
3249 						r = createdKey.GetValue ("dtest-int");
3250 						Assert.AreEqual (r is long, true);
3251 						Assert.AreEqual ((long) r, 1);
3252 						r = createdKey.GetValue ("dtest-uint");
3253 						Assert.AreEqual (r is long, true);
3254 						Assert.AreEqual ((long) r, 1);
3255 						r = createdKey.GetValue ("dtest-byte");
3256 						Assert.AreEqual (r is long, true);
3257 						Assert.AreEqual ((long) r, 1);
3258 						r = createdKey.GetValue ("dtest-sbyte");
3259 						Assert.AreEqual (r is long, true);
3260 						Assert.AreEqual ((long) r, 1);
3261 						r = createdKey.GetValue ("dtest-short");
3262 						Assert.AreEqual (r is long, true);
3263 						Assert.AreEqual ((long) r, 1);
3264 						r = createdKey.GetValue ("dtest-ushort");
3265 						Assert.AreEqual (r is long, true);
3266 						Assert.AreEqual ((long) r, 1);
3267 						r = createdKey.GetValue ("dtest-long");
3268 						Assert.AreEqual (r is long, true);
3269 						Assert.AreEqual ((long) r, 1);
3270 						r = createdKey.GetValue ("dtest-ulong");
3271 						Assert.AreEqual (r is long, true);
3272 						Assert.AreEqual ((long) r, 1);
3273 						r = createdKey.GetValue ("dtest-decimal");
3274 						Assert.IsTrue (r is long);
3275 						Assert.AreEqual ((long) r, 1);
3276 						r = createdKey.GetValue ("dtest-float");
3277 						Assert.IsTrue (r is long);
3278 						Assert.AreEqual ((long) r, 1);
3279 						r = createdKey.GetValue ("dtest-bool");
3280 						Assert.AreEqual (typeof (long), r.GetType ());
3281 
3282 						try {
3283 							createdKey.SetValue ("test-int", uint.MaxValue, RegistryValueKind.DWord);
3284 							Assert.Fail ("#100");
3285 
3286 							createdKey.SetValue ("test-int", ulong.MaxValue, RegistryValueKind.QWord);
3287 							Assert.Fail ("#101");
3288 						} catch (ArgumentException) {
3289 						}
3290 
3291 						createdKey.Close ();
3292 						softwareKey.DeleteSubKeyTree (subKeyName);
3293 					}
3294 				} finally {
3295 					try {
3296 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
3297 						if (createdKey != null) {
3298 							createdKey.Close ();
3299 							softwareKey.DeleteSubKeyTree (subKeyName);
3300 						}
3301 					} catch {
3302 					}
3303 				}
3304 			}
3305 		}
3306 
3307 		[Test]
bug79059()3308 		public void bug79059 ()
3309 		{
3310 			string subKeyName = Guid.NewGuid ().ToString ();
3311 
3312 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
3313 				try {
3314 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
3315 						using (RegistryKey softwareKey2 = Registry.CurrentUser.OpenSubKey ("software")) {
3316 						}
3317 						createdKey.Close ();
3318 						softwareKey.DeleteSubKeyTree (subKeyName);
3319 					}
3320 				} finally {
3321 					try {
3322 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
3323 						if (createdKey != null) {
3324 							createdKey.Close ();
3325 							softwareKey.DeleteSubKeyTree (subKeyName);
3326 						}
3327 					} catch {
3328 					}
3329 				}
3330 			}
3331 		}
3332 
3333 		[Test]
bugnew1()3334 		public void bugnew1 ()
3335 		{
3336 			string subKeyName = Guid.NewGuid ().ToString ();
3337 
3338 			using (RegistryKey softwareKey = Registry.CurrentUser.OpenSubKey ("software", true)) {
3339 				try {
3340 					using (RegistryKey createdKey = softwareKey.CreateSubKey (subKeyName)) {
3341 						createdKey.SetValue ("name1", "value1");
3342 
3343 						RegistryKey testKey = null;
3344 						try {
3345 							testKey = createdKey.OpenSubKey ("test", true);
3346 							if (testKey == null)
3347 								testKey = createdKey.CreateSubKey ("test");
3348 							testKey.SetValue ("another", "one");
3349 						} finally {
3350 							if (testKey != null)
3351 								testKey.Close ();
3352 						}
3353 
3354 						createdKey.SetValue ("name2", "value2");
3355 						Assert.IsNotNull (createdKey.GetValue ("name1"), "#2");
3356 						Assert.AreEqual ("value1", createdKey.GetValue ("name1"), "#3");
3357 						Assert.IsNotNull (createdKey.GetValue ("name2"), "#4");
3358 						Assert.AreEqual ("value2", createdKey.GetValue ("name2"), "#5");
3359 
3360 						string [] names = createdKey.GetValueNames ();
3361 						Assert.IsNotNull (names, "#6");
3362 						Assert.AreEqual (2, names.Length, "#7");
3363 						Assert.AreEqual ("name1", names [0], "#8");
3364 						Assert.AreEqual ("name2", names [1], "#9");
3365 
3366 						softwareKey.DeleteSubKeyTree (subKeyName);
3367 
3368 						using (RegistryKey openedKey = softwareKey.OpenSubKey (subKeyName, true)) {
3369 							Assert.IsNull (openedKey, "#10");
3370 						}
3371 
3372 						Assert.IsNull (createdKey.GetValue ("name1"), "#11");
3373 						Assert.IsNull (createdKey.GetValue ("name2"), "#12");
3374 
3375 						try {
3376 							createdKey.GetValueNames ();
3377 							Assert.Fail ("#13");
3378 						} catch (IOException ex) {
3379 							// Illegal operation attempted on a registry key that
3380 							// has been marked for deletion
3381 							Assert.AreEqual (typeof (IOException), ex.GetType (), "#14");
3382 							Assert.IsNotNull (ex.Message, "#15");
3383 							Assert.IsNull (ex.InnerException, "#16");
3384 						}
3385 
3386 						try {
3387 							createdKey.SetValue ("name1", "value1");
3388 							Assert.Fail ("#17");
3389 						} catch (IOException ex) {
3390 							// Illegal operation attempted on a registry key that
3391 							// has been marked for deletion
3392 							Assert.AreEqual (typeof (IOException), ex.GetType (), "#18");
3393 							Assert.IsNotNull (ex.Message, "#19");
3394 							Assert.IsNull (ex.InnerException, "#20");
3395 						}
3396 
3397 						try {
3398 							createdKey.SetValue ("newname", "value1");
3399 							Assert.Fail ("#21");
3400 						} catch (IOException ex) {
3401 							// Illegal operation attempted on a registry key that
3402 							// has been marked for deletion
3403 							Assert.AreEqual (typeof (IOException), ex.GetType (), "#22");
3404 							Assert.IsNotNull (ex.Message, "#23");
3405 							Assert.IsNull (ex.InnerException, "#24");
3406 						}
3407 
3408 						Assert.IsNull (createdKey.OpenSubKey ("test"), "#25");
3409 						Assert.IsNull (createdKey.OpenSubKey ("test", true), "#26");
3410 						Assert.IsNull (createdKey.OpenSubKey ("new"), "#27");
3411 						Assert.IsNull (createdKey.OpenSubKey ("new", true), "#28");
3412 
3413 						try {
3414 							createdKey.CreateSubKey ("new");
3415 							Assert.Fail ("#29");
3416 						} catch (IOException ex) {
3417 							// Illegal operation attempted on a registry key that
3418 							// has been marked for deletion
3419 							Assert.AreEqual (typeof (IOException), ex.GetType (), "#30");
3420 							Assert.IsNotNull (ex.Message, "#31");
3421 							Assert.IsNull (ex.InnerException, "#32");
3422 						}
3423 					}
3424 				} finally {
3425 					try {
3426 						RegistryKey createdKey = softwareKey.OpenSubKey (subKeyName);
3427 						if (createdKey != null) {
3428 							createdKey.Close ();
3429 							softwareKey.DeleteSubKeyTree (subKeyName);
3430 						}
3431 					} catch {
3432 					}
3433 				}
3434 			}
3435 		}
3436 
3437 		[Test]
bugnew2()3438 		public void bugnew2 () // values cannot be written on registry root (hive)
3439 		{
3440 			try {
3441 				string [] names = Registry.CurrentUser.GetValueNames ();
3442 				Assert.IsNotNull (names, "#1");
3443 				Registry.CurrentUser.SetValue ("name1", "value1");
3444 				Assert.IsNotNull (Registry.CurrentUser.GetValue ("name1"), "#2");
3445 				Assert.AreEqual ("value1", Registry.CurrentUser.GetValue ("name1"), "#3");
3446 				string [] newNames = Registry.CurrentUser.GetValueNames ();
3447 				Assert.IsNotNull (newNames, "#4");
3448 				Assert.AreEqual (names.Length + 1, newNames.Length, "#5");
3449 				Registry.CurrentUser.DeleteValue ("name1");
3450 			} finally {
3451 				Registry.CurrentUser.DeleteValue ("name1", false);
3452 				Registry.CurrentUser.Flush ();
3453 			}
3454 		}
3455 
3456 		[Test]
bugnew3()3457 		public void bugnew3 () // on Windows, key cannot be closed twice
3458 		{
3459 			string subKeyName = Guid.NewGuid ().ToString ();
3460 
3461 			try {
3462 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
3463 					createdKey.Close ();
3464 				}
3465 
3466 				RegistryKey openedKey = Registry.CurrentUser.OpenSubKey (subKeyName);
3467 				openedKey.Close ();
3468 				openedKey.Close ();
3469 			} finally {
3470 				try {
3471 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
3472 					if (createdKey != null) {
3473 						createdKey.Close ();
3474 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
3475 					}
3476 				} catch {
3477 				}
3478 			}
3479 		}
3480 
3481 		[Test]
bugnew4()3482 		public void bugnew4 () // Key cannot be flushed once it has been closed
3483 		{
3484 			string subKeyName = Guid.NewGuid ().ToString ();
3485 
3486 			try {
3487 				using (RegistryKey createdKey = Registry.CurrentUser.CreateSubKey (subKeyName)) {
3488 					createdKey.Close ();
3489 				}
3490 
3491 				RegistryKey openedKey = Registry.CurrentUser.OpenSubKey (subKeyName);
3492 				openedKey.Close ();
3493 				openedKey.Flush ();
3494 			} finally {
3495 				try {
3496 					RegistryKey createdKey = Registry.CurrentUser.OpenSubKey (subKeyName);
3497 					if (createdKey != null) {
3498 						createdKey.Close ();
3499 						Registry.CurrentUser.DeleteSubKeyTree (subKeyName);
3500 					}
3501 				} catch {
3502 				}
3503 			}
3504 		}
3505 
3506 		private bool RunningOnUnix {
3507 			get {
3508 				int p = (int) Environment.OSVersion.Platform;
3509 				return ((p == 4) || (p == 128) || (p == 6));
3510 			}
3511 		}
3512 	}
3513 }
3514