[sdb] Avoid marking seq points as nonempty-stack if they have a sym seq point. Fix...
[mono.git] / mcs / class / Mono.Debugger.Soft / Test / dtest.cs
1 using System;
2 using System.Collections.Generic;
3 using System.Threading;
4 using System.Net;
5 using System.Reflection;
6 using System.Text;
7 using Mono.Cecil.Cil;
8 using Mono.Debugger.Soft;
9 using Diag = System.Diagnostics;
10 using System.Linq;
11 using System.IO;
12 using System.Security.Cryptography;
13
14 using NUnit.Framework;
15
16 #pragma warning disable 0219
17
18 namespace MonoTests
19 {
20
21 [TestFixture]
22 public class DebuggerTests
23 {
24         VirtualMachine vm;
25         MethodMirror entry_point;
26         StepEventRequest step_req;
27         bool forceExit;
28
29         void AssertThrows<ExType> (Action del) where ExType : Exception {
30                 bool thrown = false;
31
32                 try {
33                         del ();
34                 } catch (ExType) {
35                         thrown = true;
36                 }
37                 Assert.IsTrue (thrown);
38         }
39
40         // No other way to pass arguments to the tests ?
41         public static bool listening = Environment.GetEnvironmentVariable ("DBG_SUSPEND") != null;
42         public static string runtime = Environment.GetEnvironmentVariable ("DBG_RUNTIME");
43         public static string agent_args = Environment.GetEnvironmentVariable ("DBG_AGENT_ARGS");
44
45         Event GetNextEvent () {
46                 var es = vm.GetNextEventSet ();
47                 Assert.AreEqual (1, es.Events.Length);
48                 return es [0];
49         }
50
51         void Start (params string[] args) {
52                 Start (false, args);
53         }
54
55         void Start (bool forceExit, params string[] args) {
56                 this.forceExit = forceExit;
57
58                 if (!listening) {
59                         var pi = new Diag.ProcessStartInfo ();
60
61                         if (runtime != null)
62                                 pi.FileName = runtime;
63                         else
64                                 pi.FileName = "mono";
65                         pi.Arguments = String.Join (" ", args);
66                         vm = VirtualMachineManager.Launch (pi, new LaunchOptions { AgentArgs = agent_args });
67                 } else {
68                         var ep = new IPEndPoint (IPAddress.Any, 10000);
69                         Console.WriteLine ("Listening on " + ep + "...");
70                         vm = VirtualMachineManager.Listen (ep);
71                 }
72
73                 var load_req = vm.CreateAssemblyLoadRequest ();
74                 load_req.Enable ();
75
76                 Event vmstart = GetNextEvent ();
77                 Assert.AreEqual (EventType.VMStart, vmstart.EventType);
78
79                 vm.Resume ();
80
81                 entry_point = null;
82                 step_req = null;
83
84                 Event e;
85
86                 /* Find out the entry point */
87                 while (true) {
88                         e = GetNextEvent ();
89
90                         if (e is AssemblyLoadEvent) {
91                                 AssemblyLoadEvent ae = (AssemblyLoadEvent)e;
92                                 entry_point = ae.Assembly.EntryPoint;
93                                 if (entry_point != null)
94                                         break;
95                         }
96
97                         vm.Resume ();
98                 }
99
100                 load_req.Disable ();
101         }
102
103         BreakpointEvent run_until (string name) {
104                 // String
105                 MethodMirror m = entry_point.DeclaringType.GetMethod (name);
106                 Assert.IsNotNull (m);
107                 //Console.WriteLine ("X: " + name + " " + m.ILOffsets.Count + " " + m.Locations.Count);
108                 var req = vm.SetBreakpoint (m, m.ILOffsets [0]);
109
110                 Event e = null;
111
112                 while (true) {
113                         vm.Resume ();
114                         e = GetNextEvent ();
115                         if (e is BreakpointEvent)
116                                 break;
117                 }
118
119                 req.Disable ();
120
121                 Assert.IsInstanceOfType (typeof (BreakpointEvent), e);
122                 Assert.AreEqual (m.Name, (e as BreakpointEvent).Method.Name);
123
124                 return (e as BreakpointEvent);
125         }
126
127         Event single_step (ThreadMirror t) {
128                 var req = vm.CreateStepRequest (t);
129                 req.Enable ();
130
131                 vm.Resume ();
132                 Event e = GetNextEvent ();
133                 Assert.IsTrue (e is StepEvent);
134
135                 req.Disable ();
136
137                 return e;
138         }
139
140         Event step_until (ThreadMirror t, string method_name) {
141                 Event e;
142                 while (true) {
143                         e = single_step (t);
144                         if ((e as StepEvent).Method.Name == method_name)
145                                 break;
146                 }
147                 return e;
148         }
149
150         void check_arg_val (StackFrame frame, int pos, Type type, object eval) {
151                 object val = frame.GetArgument (pos);
152                 Assert.IsTrue (val is PrimitiveValue);
153                 object v = (val as PrimitiveValue).Value;
154                 Assert.AreEqual (type, v.GetType ());
155                 if (eval is float)
156                         Assert.IsTrue (Math.Abs ((float)eval - (float)v) < 0.0001);
157                 else if (eval is double)
158                         Assert.IsTrue (Math.Abs ((double)eval - (double)v) < 0.0001);
159                 else
160                         Assert.AreEqual (eval, v);
161         }
162
163         void AssertValue (object expected, object val) {
164                 if (expected is string) {
165                         Assert.IsTrue (val is StringMirror);
166                         Assert.AreEqual (expected, (val as StringMirror).Value);
167                 } else if (val is StructMirror && (val as StructMirror).Type.Name == "IntPtr") {
168                         AssertValue (expected, (val as StructMirror).Fields [0]);
169                 } else {
170                         Assert.IsTrue (val is PrimitiveValue);
171                         Assert.AreEqual (expected, (val as PrimitiveValue).Value);
172                 }
173         }
174
175         [SetUp]
176         public void SetUp () {
177                 ThreadMirror.NativeTransitions = false;
178                 Start (new string [] { "dtest-app.exe" });
179         }
180
181         [TearDown]
182         public void TearDown () {
183                 if (vm == null)
184                         return;
185
186                 if (step_req != null)
187                         step_req.Disable ();
188
189                 vm.Resume ();
190                 if (forceExit)
191                         vm.Exit (0);
192
193                 while (true) {
194                         Event e = GetNextEvent ();
195
196                         if (e is VMDeathEvent)
197                                 break;
198
199                         vm.Resume ();
200                 }
201                 vm = null;
202         }
203
204         [Test]
205         public void SimpleBreakpoint () {
206                 Event e;
207
208                 MethodMirror m = entry_point.DeclaringType.GetMethod ("bp1");
209                 Assert.IsNotNull (m);
210
211                 vm.SetBreakpoint (m, 0);
212
213                 vm.Resume ();
214
215                 e = GetNextEvent ();
216                 Assert.AreEqual (EventType.Breakpoint, e.EventType);
217                 Assert.IsTrue (e is BreakpointEvent);
218                 Assert.AreEqual (m.Name, (e as BreakpointEvent).Method.Name);
219
220                 // Argument checking
221                 AssertThrows<ArgumentException> (delegate {
222                                 // Invalid IL offset
223                                 vm.SetBreakpoint (m, 2);
224                         });
225         }
226
227         [Test]
228         public void BreakpointsSameLocation () {
229                 MethodMirror m = entry_point.DeclaringType.GetMethod ("bp2");
230                 Assert.IsNotNull (m);
231
232                 vm.SetBreakpoint (m, 0);
233                 vm.SetBreakpoint (m, 0);
234
235                 vm.Resume ();
236
237                 var es = vm.GetNextEventSet ();
238                 Assert.AreEqual (2, es.Events.Length);
239                 Assert.IsTrue (es [0] is BreakpointEvent);
240                 Assert.AreEqual (m, (es [0] as BreakpointEvent).Method);
241
242                 Assert.IsTrue (es [1] is BreakpointEvent);
243                 Assert.AreEqual (m.Name, (es [1] as BreakpointEvent).Method.Name);
244         }
245
246         [Test]
247         public void BreakpointAlreadyJITted () {
248                 Event e = run_until ("bp1");
249
250                 /* Place a breakpoint on bp3 */
251                 MethodMirror m = entry_point.DeclaringType.GetMethod ("bp3");
252                 Assert.IsNotNull (m);
253                 vm.SetBreakpoint (m, 0);
254
255                 /* Same with generic instances */
256                 MethodMirror m2 = entry_point.DeclaringType.GetMethod ("bp7");
257                 Assert.IsNotNull (m2);
258                 vm.SetBreakpoint (m2, 0);
259
260                 vm.Resume ();
261
262                 e = GetNextEvent ();
263                 Assert.AreEqual (EventType.Breakpoint, e.EventType);
264                 Assert.AreEqual (m.Name, (e as BreakpointEvent).Method.Name);
265
266                 vm.Resume ();
267
268                 /* Non-shared instance */
269                 e = GetNextEvent ();
270                 Assert.AreEqual (EventType.Breakpoint, e.EventType);
271                 Assert.AreEqual (m2.Name, (e as BreakpointEvent).Method.Name);
272
273                 vm.Resume ();
274
275                 /* Shared instance */
276                 e = GetNextEvent ();
277                 Assert.AreEqual (EventType.Breakpoint, e.EventType);
278                 Assert.AreEqual (m2.Name, (e as BreakpointEvent).Method.Name);
279         }
280
281         [Test]
282         public void ClearBreakpoint () {
283                 Event e;
284
285                 MethodMirror m = entry_point.DeclaringType.GetMethod ("bp4");
286                 Assert.IsNotNull (m);
287                 EventRequest req1 = vm.SetBreakpoint (m, 0);
288                 EventRequest req2 = vm.SetBreakpoint (m, 0);
289
290                 MethodMirror m2 = entry_point.DeclaringType.GetMethod ("bp5");
291                 Assert.IsNotNull (m2);
292                 vm.SetBreakpoint (m2, 0);
293
294                 /* Run until bp4 */
295                 vm.Resume ();
296
297                 var es = vm.GetNextEventSet ();
298                 Assert.AreEqual (2, es.Events.Length);
299                 Assert.AreEqual (EventType.Breakpoint, es [0].EventType);
300                 Assert.AreEqual (m.Name, (es [0] as BreakpointEvent).Method.Name);
301                 Assert.AreEqual (EventType.Breakpoint, es [1].EventType);
302                 Assert.AreEqual (m.Name, (es [1] as BreakpointEvent).Method.Name);
303
304                 /* Clear one of them */
305                 req1.Disable ();
306
307                 vm.Resume ();
308
309                 e = GetNextEvent ();
310                 Assert.AreEqual (EventType.Breakpoint, e.EventType);
311                 Assert.AreEqual (m.Name, (e as BreakpointEvent).Method.Name);
312
313                 /* Clear the other */
314                 req2.Disable ();
315
316                 vm.Resume ();
317
318                 e = GetNextEvent ();
319                 Assert.AreEqual (EventType.Breakpoint, e.EventType);
320                 Assert.AreEqual (m2.Name, (e as BreakpointEvent).Method.Name);
321         }
322
323         [Test]
324         public void ClearAllBreakpoints () {
325                 Event e;
326
327                 MethodMirror m = entry_point.DeclaringType.GetMethod ("bp4");
328                 Assert.IsNotNull (m);
329                 vm.SetBreakpoint (m, 0);
330
331                 MethodMirror m2 = entry_point.DeclaringType.GetMethod ("bp5");
332                 Assert.IsNotNull (m2);
333                 vm.SetBreakpoint (m2, 0);
334
335                 vm.ClearAllBreakpoints ();
336
337                 vm.Resume ();
338
339                 e = GetNextEvent ();
340                 Assert.IsTrue (!(e is BreakpointEvent));
341                 if (e is VMDeathEvent)
342                         vm = null;
343         }
344
345         [Test]
346         public void BreakpointOnGShared () {
347                 Event e;
348
349                 MethodMirror m = entry_point.DeclaringType.GetMethod ("bp6");
350                 Assert.IsNotNull (m);
351
352                 vm.SetBreakpoint (m, 0);
353
354                 vm.Resume ();
355
356                 e = GetNextEvent ();
357                 Assert.AreEqual (EventType.Breakpoint, e.EventType);
358                 Assert.IsTrue (e is BreakpointEvent);
359                 Assert.AreEqual (m.Name, (e as BreakpointEvent).Method.Name);
360
361                 // Breakpoint on an open generic method of a closed generic class (#3422)
362                 var frame = e.Thread.GetFrames ()[0];
363                 var ginst = frame.GetValue (frame.Method.GetLocal ("gc"));
364                 var m2 = (ginst as ObjectMirror).Type.GetMethod ("bp");
365                 vm.SetBreakpoint (m2, 0);
366
367                 vm.Resume ();
368
369                 e = GetNextEvent ();
370                 Assert.AreEqual (EventType.Breakpoint, e.EventType);
371                 Assert.IsTrue (e is BreakpointEvent);
372                 Assert.AreEqual (m2.Name, (e as BreakpointEvent).Method.Name);
373         }
374
375         void assert_location (Event e, string method) {
376                 Assert.IsTrue (e is StepEvent);
377                 Assert.AreEqual (method, (e as StepEvent).Method.Name);
378         }
379
380         StepEventRequest create_step (Event e) {
381                 var req = vm.CreateStepRequest (e.Thread);
382                 step_req = req;
383                 return req;
384         }
385
386         [Test]
387         public void SingleStepping () {
388                 Event e = run_until ("single_stepping");
389
390                 var req = create_step (e);
391                 req.Enable ();
392
393                 // Step over 'bool b = true'
394                 e = step_once ();
395                 assert_location (e, "single_stepping");
396
397                 // Skip nop
398                 step_once ();
399
400                 // Step into ss1
401                 e = step_once ();
402                 assert_location (e, "ss1");
403
404                 // Skip }
405                 e = step_once ();
406
407                 // Step out of ss1
408                 e = step_once ();
409                 assert_location (e, "single_stepping");
410
411                 // Step over ss2
412                 e = step_over ();
413                 assert_location (e, "single_stepping");
414
415                 // Step into ss3
416                 e = step_into ();
417                 assert_location (e, "ss3");
418
419                 // Step back into single_stepping
420                 e = step_out ();
421                 assert_location (e, "single_stepping");
422
423                 // Step into next line
424                 e = step_into ();
425                 assert_location (e, "single_stepping");
426
427                 // Step into ss3_2 ()
428                 e = step_into ();
429                 assert_location (e, "ss3_2");
430
431                 // Step over ss3_2_2 ()
432                 e = step_over ();
433                 assert_location (e, "ss3_2");
434
435                 // Recreate the request
436                 req.Disable ();
437                 req.Enable ();
438
439                 // Skip }
440                 e = step_once ();
441
442                 // Step back into single_stepping () with the new request
443                 e = step_once ();
444                 assert_location (e, "single_stepping");
445
446                 // Step into ss4 ()
447                 e = step_into ();
448                 assert_location (e, "ss4");
449
450                 // Skip nop
451                 e = step_once ();
452
453                 // Change to StepSize.Line
454                 req.Disable ();
455                 req.Depth = StepDepth.Over;
456                 req.Size = StepSize.Line;
457                 req.Enable ();
458
459                 // Step over ss1 (); ss1 ();
460                 e = step_once ();
461
462                 // Step into ss2 ()
463                 req.Disable ();
464                 req.Depth = StepDepth.Into;
465                 req.Enable ();
466
467                 e = step_once ();
468                 assert_location (e, "ss2");
469
470                 req.Disable ();
471
472                 // Run until ss5
473                 e = run_until ("ss5");
474
475                 // Add an assembly filter
476                 req.AssemblyFilter = new AssemblyMirror [] { (e as BreakpointEvent).Method.DeclaringType.Assembly };
477                 req.Enable ();
478
479                 // Skip nop
480                 e = step_once ();
481
482                 // Step into is_even, skipping the linq stuff
483                 e = step_once ();
484                 assert_location (e, "is_even");
485
486                 // FIXME: Check that single stepping works with lock (obj)
487                 req.Disable ();
488
489                 // Run until ss6
490                 e = run_until ("ss6");
491
492                 req = create_step (e);
493                 req.Depth = StepDepth.Over;
494                 req.Enable ();
495
496                 // Check that single stepping works in out-of-line bblocks
497                 e = step_once ();
498                 e = step_once ();
499                 assert_location (e, "ss6");
500                 req.Disable ();
501
502                 // Check that a step over stops at an EH clause
503                 e = run_until ("ss7_2");
504                 req = create_step (e);
505                 req.Depth = StepDepth.Out;
506                 req.Enable ();
507                 e = step_once ();
508                 assert_location (e, "ss7");
509                 req.Disable ();
510                 req = create_step (e);
511                 req.Depth = StepDepth.Over;
512                 req.Enable ();
513                 e = step_once ();
514                 assert_location (e, "ss7");
515                 req.Disable ();
516
517                 // Check that stepping stops between nested calls
518                 e = run_until ("ss_nested_2");
519                 e = step_out ();
520                 assert_location (e, "ss_nested");
521                 e = step_into ();
522                 assert_location (e, "ss_nested_1");
523                 e = step_out ();
524                 assert_location (e, "ss_nested");
525                 // Check that step over steps over nested calls
526                 e = step_over ();
527                 assert_location (e, "ss_nested");
528                 e = step_into ();
529                 assert_location (e, "ss_nested_1");
530                 e = step_into ();
531                 assert_location (e, "ss_nested_1");
532                 e = step_into ();
533                 assert_location (e, "ss_nested");
534                 req.Disable ();
535
536                 // Check DebuggerStepThrough support
537                 e = run_until ("ss_step_through");
538                 req = create_step (e);
539                 req.Filter = StepFilter.DebuggerStepThrough;
540                 e = step_into ();
541                 // Step through step_through_1 ()
542                 e = step_into ();
543                 assert_location (e, "ss_step_through");
544                 // Step through StepThroughClass.step_through_2 ()
545                 e = step_into ();
546                 assert_location (e, "ss_step_through");
547                 req.Disable ();
548                 req.Filter = StepFilter.None;
549                 e = step_into ();
550                 assert_location (e, "step_through_3");
551                 req.Disable ();
552
553                 // Check DebuggerNonUserCode support
554                 e = run_until ("ss_non_user_code");
555                 req = create_step (e);
556                 req.Filter = StepFilter.DebuggerNonUserCode;
557                 e = step_into ();
558                 // Step through non_user_code_1 ()
559                 e = step_into ();
560                 assert_location (e, "ss_non_user_code");
561                 // Step through StepThroughClass.non_user_code_2 ()
562                 e = step_into ();
563                 assert_location (e, "ss_non_user_code");
564                 req.Disable ();
565                 req.Filter = StepFilter.None;
566                 e = step_into ();
567                 assert_location (e, "non_user_code_3");
568                 req.Disable ();
569
570                 // Check that step-over doesn't stop at inner frames with recursive functions
571                 e = run_until ("ss_recursive");
572                 req = create_step (e);
573                 e = step_over ();
574                 e = step_over ();
575                 e = step_over ();
576                 var f = e.Thread.GetFrames () [0];
577                 assert_location (e, "ss_recursive");
578                 AssertValue (1, f.GetValue (f.Method.GetLocal ("n")));
579                 req.Disable ();
580
581                 // Check that single stepping doesn't clobber fp values
582                 e = run_until ("ss_fp_clobber");
583                 req = create_step (e);
584                 while (true) {
585                         f = e.Thread.GetFrames ()[0];
586                         e = step_into ();
587                         if ((e as StepEvent).Method.Name == "ss_fp_clobber_2")
588                                 break;
589                         e = step_into ();
590                 }
591                 f = e.Thread.GetFrames ()[0];
592                 AssertValue (7.0, f.GetValue (f.Method.GetParameters ()[0]));
593                 req.Disable ();
594         }
595
596         [Test]
597         public void MethodEntryExit () {
598                 run_until ("single_stepping");
599
600                 var req1 = vm.CreateMethodEntryRequest ();
601                 var req2 = vm.CreateMethodExitRequest ();
602
603                 req1.Enable ();
604                 req2.Enable ();
605
606                 vm.Resume ();
607                 Event e = GetNextEvent ();
608                 Assert.IsTrue (e is MethodEntryEvent);
609                 Assert.AreEqual ("ss1", (e as MethodEntryEvent).Method.Name);
610
611                 vm.Resume ();
612                 e = GetNextEvent ();
613                 Assert.IsTrue (e is MethodExitEvent);
614                 Assert.AreEqual ("ss1", (e as MethodExitEvent).Method.Name);
615
616                 req1.Disable ();
617                 req2.Disable ();
618         }
619
620         [Test]
621         public void CountFilter () {
622                 run_until ("single_stepping");
623
624                 MethodMirror m2 = entry_point.DeclaringType.GetMethod ("ss3");
625                 Assert.IsNotNull (m2);
626                 vm.SetBreakpoint (m2, 0);
627
628                 var req1 = vm.CreateMethodEntryRequest ();
629                 req1.Count = 2;
630                 req1.Enable ();
631
632                 // Enter ss2, ss1 is skipped
633                 vm.Resume ();
634                 Event e = GetNextEvent ();
635                 Assert.IsTrue (e is MethodEntryEvent);
636                 Assert.AreEqual ("ss2", (e as MethodEntryEvent).Method.Name);
637
638                 // Breakpoint on ss3, the entry event is no longer reported
639                 vm.Resume ();
640                 e = GetNextEvent ();
641                 Assert.IsTrue (e is BreakpointEvent);
642
643                 req1.Disable ();
644         }
645
646         [Test]
647         public void Arguments () {
648                 object val;
649
650                 var e = run_until ("arg1");
651
652                 StackFrame frame = e.Thread.GetFrames () [0];
653
654                 check_arg_val (frame, 0, typeof (sbyte), SByte.MaxValue - 5);
655                 check_arg_val (frame, 1, typeof (byte), Byte.MaxValue - 5);
656                 check_arg_val (frame, 2, typeof (bool), true);
657                 check_arg_val (frame, 3, typeof (short), Int16.MaxValue - 5);
658                 check_arg_val (frame, 4, typeof (ushort), UInt16.MaxValue - 5);
659                 check_arg_val (frame, 5, typeof (char), 'F');
660                 check_arg_val (frame, 6, typeof (int), Int32.MaxValue - 5);
661                 check_arg_val (frame, 7, typeof (uint), UInt32.MaxValue - 5);
662                 check_arg_val (frame, 8, typeof (long), Int64.MaxValue - 5);
663                 check_arg_val (frame, 9, typeof (ulong), UInt64.MaxValue - 5);
664                 check_arg_val (frame, 10, typeof (float), 1.2345f);
665                 check_arg_val (frame, 11, typeof (double), 6.78910);
666
667                 e = run_until ("arg2");
668
669                 frame = e.Thread.GetFrames () [0];
670
671                 // String
672                 val = frame.GetArgument (0);
673                 AssertValue ("FOO", val);
674                 Assert.AreEqual ("String", (val as ObjectMirror).Type.Name);
675
676                 // null
677                 val = frame.GetArgument (1);
678                 AssertValue (null, val);
679
680                 // object
681                 val = frame.GetArgument (2);
682                 AssertValue ("BLA", val);
683
684                 // byref
685                 val = frame.GetArgument (3);
686                 AssertValue (42, val);
687
688                 // generic instance
689                 val = frame.GetArgument (4);
690                 Assert.IsTrue (val is ObjectMirror);
691                 Assert.AreEqual ("GClass`1", (val as ObjectMirror).Type.Name);
692
693                 // System.Object
694                 val = frame.GetArgument (5);
695                 Assert.IsTrue (val is ObjectMirror);
696                 Assert.AreEqual ("Object", (val as ObjectMirror).Type.Name);
697
698                 // this on static methods
699                 val = frame.GetThis ();
700                 AssertValue (null, val);
701
702                 e = run_until ("arg3");
703
704                 frame = e.Thread.GetFrames () [0];
705
706                 // this
707                 val = frame.GetThis ();
708                 Assert.IsTrue (val is ObjectMirror);
709                 Assert.AreEqual ("Tests", (val as ObjectMirror).Type.Name);
710
711                 // objref in register
712                 val = frame.GetArgument (0);
713                 AssertValue ("BLA", val);
714         }
715
716         [Test]
717         public void Arrays () {
718                 object val;
719
720                 var e = run_until ("o2");
721
722                 StackFrame frame = e.Thread.GetFrames () [0];
723
724                 // String[]
725                 val = frame.GetArgument (0);
726                 Assert.IsTrue (val is ArrayMirror);
727                 ArrayMirror arr = val as ArrayMirror;
728                 Assert.AreEqual (2, arr.Length);
729                 AssertValue ("BAR", arr [0]);
730                 AssertValue ("BAZ", arr [1]);
731
732                 var vals = arr.GetValues (0, 2);
733                 Assert.AreEqual (2, vals.Count);
734                 AssertValue ("BAR", vals [0]);
735                 AssertValue ("BAZ", vals [1]);
736
737                 arr [0] = vm.RootDomain.CreateString ("ABC");
738                 AssertValue ("ABC", arr [0]);
739
740                 arr [0] = vm.CreateValue (null);
741                 AssertValue (null, arr [0]);
742
743                 arr.SetValues (0, new Value [] { vm.RootDomain.CreateString ("D1"), vm.RootDomain.CreateString ("D2") });
744                 AssertValue ("D1", arr [0]);
745                 AssertValue ("D2", arr [1]);
746
747                 // int
748                 val = frame.GetArgument (1);
749                 Assert.IsTrue (val is ArrayMirror);
750                 arr = val as ArrayMirror;
751                 Assert.AreEqual (2, arr.Length);
752                 AssertValue (42, arr [0]);
753                 AssertValue (43, arr [1]);
754
755                 // Argument checking
756                 AssertThrows<IndexOutOfRangeException> (delegate () {
757                                 val = arr [2];
758                         });
759
760                 AssertThrows<IndexOutOfRangeException> (delegate () {
761                                 val = arr [Int32.MinValue];
762                         });
763
764                 AssertThrows<IndexOutOfRangeException> (delegate () {
765                                 vals = arr.GetValues (0, 3);
766                         });
767
768                 AssertThrows<IndexOutOfRangeException> (delegate () {
769                                 arr [2] = vm.CreateValue (null);
770                         });
771
772                 AssertThrows<IndexOutOfRangeException> (delegate () {
773                                 arr [Int32.MinValue] = vm.CreateValue (null);
774                         });
775
776                 AssertThrows<IndexOutOfRangeException> (delegate () {
777                                 arr.SetValues (0, new Value [] { null, null, null });
778                         });
779
780                 // Multidim arrays
781                 val = frame.GetArgument (2);
782                 Assert.IsTrue (val is ArrayMirror);
783                 arr = val as ArrayMirror;
784                 Assert.AreEqual (2, arr.Rank);
785                 Assert.AreEqual (4, arr.Length);
786                 Assert.AreEqual (2, arr.GetLength (0));
787                 Assert.AreEqual (2, arr.GetLength (1));
788                 Assert.AreEqual (0, arr.GetLowerBound (0));
789                 Assert.AreEqual (0, arr.GetLowerBound (1));
790                 vals = arr.GetValues (0, 4);
791                 AssertValue (1, vals [0]);
792                 AssertValue (2, vals [1]);
793                 AssertValue (3, vals [2]);
794                 AssertValue (4, vals [3]);
795
796                 val = frame.GetArgument (3);
797                 Assert.IsTrue (val is ArrayMirror);
798                 arr = val as ArrayMirror;
799                 Assert.AreEqual (2, arr.Rank);
800                 Assert.AreEqual (4, arr.Length);
801                 Assert.AreEqual (2, arr.GetLength (0));
802                 Assert.AreEqual (2, arr.GetLength (1));
803                 Assert.AreEqual (1, arr.GetLowerBound (0));
804                 Assert.AreEqual (3, arr.GetLowerBound (1));
805
806                 AssertThrows<ArgumentOutOfRangeException> (delegate () {
807                                 arr.GetLength (-1);
808                         });
809                 AssertThrows<ArgumentOutOfRangeException> (delegate () {
810                                 arr.GetLength (2);
811                         });
812
813                 AssertThrows<ArgumentOutOfRangeException> (delegate () {
814                                 arr.GetLowerBound (-1);
815                         });
816                 AssertThrows<ArgumentOutOfRangeException> (delegate () {
817                                 arr.GetLowerBound (2);
818                         });
819
820                 // arrays treated as generic collections
821                 val = frame.GetArgument (4);
822                 Assert.IsTrue (val is ArrayMirror);
823                 arr = val as ArrayMirror;
824         }
825
826         [Test]
827         public void Object_GetValue () {
828                 var e = run_until ("o1");
829                 var frame = e.Thread.GetFrames () [0];
830
831                 object val = frame.GetThis ();
832                 Assert.IsTrue (val is ObjectMirror);
833                 Assert.AreEqual ("Tests", (val as ObjectMirror).Type.Name);
834                 ObjectMirror o = (val as ObjectMirror);
835
836                 TypeMirror t = o.Type;
837
838                 // object fields
839                 object f = o.GetValue (t.GetField ("field_i"));
840                 AssertValue (42, f);
841                 f = o.GetValue (t.GetField ("field_s"));
842                 AssertValue ("S", f);
843                 f = o.GetValue (t.GetField ("field_enum"));
844                 Assert.IsTrue (f is EnumMirror);
845                 Assert.AreEqual (1, (f as EnumMirror).Value);
846                 Assert.AreEqual ("B", (f as EnumMirror).StringValue);
847
848                 // Inherited object fields
849                 TypeMirror parent = t.BaseType;
850                 f = o.GetValue (parent.GetField ("base_field_i"));
851                 AssertValue (43, f);
852                 f = o.GetValue (parent.GetField ("base_field_s"));
853                 AssertValue ("T", f);
854
855                 // Static fields
856                 f = o.GetValue (o.Type.GetField ("static_i"));
857                 AssertValue (55, f);
858
859                 // generic instances
860                 ObjectMirror o2 = frame.GetValue (frame.Method.GetParameters ()[1]) as ObjectMirror;
861                 Assert.AreEqual ("GClass`1", o2.Type.Name);
862                 TypeMirror t2 = o2.Type;
863                 f = o2.GetValue (t2.GetField ("field"));
864                 AssertValue (42, f);
865
866                 ObjectMirror o3 = frame.GetValue (frame.Method.GetParameters ()[2]) as ObjectMirror;
867                 Assert.AreEqual ("GClass`1", o3.Type.Name);
868                 TypeMirror t3 = o3.Type;
869                 f = o3.GetValue (t3.GetField ("field"));
870                 AssertValue ("FOO", f);
871
872                 // Argument checking
873                 AssertThrows<ArgumentNullException> (delegate () {
874                         o.GetValue (null);
875                         });
876         }
877
878         [Test]
879         public void Object_GetValues () {
880                 var e = run_until ("o1");
881                 var frame = e.Thread.GetFrames () [0];
882
883                 object val = frame.GetThis ();
884                 Assert.IsTrue (val is ObjectMirror);
885                 Assert.AreEqual ("Tests", (val as ObjectMirror).Type.Name);
886                 ObjectMirror o = (val as ObjectMirror);
887
888                 ObjectMirror val2 = frame.GetValue (frame.Method.GetParameters ()[0]) as ObjectMirror;
889
890                 TypeMirror t = o.Type;
891
892                 object[] vals = o.GetValues (new FieldInfoMirror [] { t.GetField ("field_i"), t.GetField ("field_s") });
893                 object f = vals [0];
894                 AssertValue (42, f);
895                 f = vals [1];
896                 AssertValue ("S", f);
897
898                 // Argument checking
899                 AssertThrows<ArgumentNullException> (delegate () {
900                         o.GetValues (null);
901                         });
902
903                 AssertThrows<ArgumentNullException> (delegate () {
904                         o.GetValues (new FieldInfoMirror [] { null });
905                         });
906
907                 // field of another class
908                 AssertThrows<ArgumentException> (delegate () {
909                                 o.GetValue (val2.Type.GetField ("field_j"));
910                         });
911         }
912
913         void TestSetValue (ObjectMirror o, string field_name, object val) {
914                 if (val is string)
915                         o.SetValue (o.Type.GetField (field_name), vm.RootDomain.CreateString ((string)val));
916                 else
917                         o.SetValue (o.Type.GetField (field_name), vm.CreateValue (val));
918                 Value f = o.GetValue (o.Type.GetField (field_name));
919                 AssertValue (val, f);
920         }
921
922         [Test]
923         public void Object_SetValues () {
924                 var e = run_until ("o1");
925                 var frame = e.Thread.GetFrames () [0];
926
927                 object val = frame.GetThis ();
928                 Assert.IsTrue (val is ObjectMirror);
929                 Assert.AreEqual ("Tests", (val as ObjectMirror).Type.Name);
930                 ObjectMirror o = (val as ObjectMirror);
931
932                 ObjectMirror val2 = frame.GetValue (frame.Method.GetParameters ()[0]) as ObjectMirror;
933
934                 TestSetValue (o, "field_i", 22);
935                 TestSetValue (o, "field_bool1", false);
936                 TestSetValue (o, "field_bool2", true);
937                 TestSetValue (o, "field_char", 'B');
938                 TestSetValue (o, "field_byte", (byte)129);
939                 TestSetValue (o, "field_sbyte", (sbyte)-33);
940                 TestSetValue (o, "field_short", (short)(Int16.MaxValue - 5));
941                 TestSetValue (o, "field_ushort", (ushort)(UInt16.MaxValue - 5));
942                 TestSetValue (o, "field_long", Int64.MaxValue - 5);
943                 TestSetValue (o, "field_ulong", (ulong)(UInt64.MaxValue - 5));
944                 TestSetValue (o, "field_float", 6.28f);
945                 TestSetValue (o, "field_double", 6.28);
946                 TestSetValue (o, "static_i", 23);
947                 TestSetValue (o, "field_s", "CDEF");
948
949                 Value f;
950
951                 // intptrs
952                 f = o.GetValue (o.Type.GetField ("field_intptr"));
953                 Assert.IsInstanceOfType (typeof (StructMirror), f);
954                 AssertValue (Int32.MaxValue - 5, (f as StructMirror).Fields [0]);
955
956                 // enums
957                 FieldInfoMirror field = o.Type.GetField ("field_enum");
958                 f = o.GetValue (field);
959                 (f as EnumMirror).Value = 5;
960                 o.SetValue (field, f);
961                 f = o.GetValue (field);
962                 Assert.AreEqual (5, (f as EnumMirror).Value);
963
964                 // null
965                 o.SetValue (o.Type.GetField ("field_s"), vm.CreateValue (null));
966                 f = o.GetValue (o.Type.GetField ("field_s"));
967                 AssertValue (null, f);
968
969                 // vtype instances
970                 field = o.Type.GetField ("generic_field_struct");
971                 f = o.GetValue (field);
972                 o.SetValue (field, f);
973
974                 // nullables
975                 field = o.Type.GetField ("field_nullable");
976                 f = o.GetValue (field);
977                 AssertValue (0, (f as StructMirror).Fields [0]);
978                 AssertValue (false, (f as StructMirror).Fields [1]);
979                 o.SetValue (field, vm.CreateValue (6));
980                 f = o.GetValue (field);
981                 AssertValue (6, (f as StructMirror).Fields [0]);
982                 AssertValue (true, (f as StructMirror).Fields [1]);
983                 o.SetValue (field, vm.CreateValue (null));
984                 f = o.GetValue (field);
985                 AssertValue (0, (f as StructMirror).Fields [0]);
986                 AssertValue (false, (f as StructMirror).Fields [1]);
987
988                 // Argument checking
989                 AssertThrows<ArgumentNullException> (delegate () {
990                                 o.SetValues (null, new Value [0]);
991                         });
992
993                 AssertThrows<ArgumentNullException> (delegate () {
994                                 o.SetValues (new FieldInfoMirror [0], null);
995                         });
996
997                 AssertThrows<ArgumentNullException> (delegate () {
998                                 o.SetValues (new FieldInfoMirror [] { null }, new Value [1] { null });
999                         });
1000
1001                 // vtype with a wrong type
1002                 AssertThrows<ArgumentException> (delegate () {
1003                                 o.SetValue (o.Type.GetField ("field_struct"), o.GetValue (o.Type.GetField ("field_enum")));
1004                         });
1005
1006                 // reference type not assignment compatible
1007                 AssertThrows<ArgumentException> (delegate () {
1008                                 o.SetValue (o.Type.GetField ("field_class"), o);
1009                         });
1010
1011                 // field of another class
1012                 AssertThrows<ArgumentException> (delegate () {
1013                                 o.SetValue (val2.Type.GetField ("field_j"), vm.CreateValue (1));
1014                         });
1015         }
1016
1017         [Test]
1018         public void Type_SetValue () {
1019                 var e = run_until ("o1");
1020                 var frame = e.Thread.GetFrames () [0];
1021                 Value f;
1022
1023                 object val = frame.GetThis ();
1024                 Assert.IsTrue (val is ObjectMirror);
1025                 Assert.AreEqual ("Tests", (val as ObjectMirror).Type.Name);
1026                 ObjectMirror o = (val as ObjectMirror);
1027
1028                 ObjectMirror val2 = frame.GetValue (frame.Method.GetParameters ()[0]) as ObjectMirror;
1029
1030                 o.Type.SetValue (o.Type.GetField ("static_i"), vm.CreateValue (55));
1031                 f = o.Type.GetValue (o.Type.GetField ("static_i"));
1032                 AssertValue (55, f);
1033
1034                 o.Type.SetValue (o.Type.GetField ("static_s"), vm.RootDomain.CreateString ("B"));
1035                 f = o.Type.GetValue (o.Type.GetField ("static_s"));
1036                 AssertValue ("B", f);
1037
1038                 // Argument checking
1039                 AssertThrows<ArgumentNullException> (delegate () {
1040                                 o.Type.SetValue (null, vm.CreateValue (0));
1041                         });
1042
1043                 AssertThrows<ArgumentNullException> (delegate () {
1044                                 o.Type.SetValue (o.Type.GetField ("static_i"), null);
1045                         });
1046
1047                 // field of another class
1048                 AssertThrows<ArgumentException> (delegate () {
1049                                 o.SetValue (val2.Type.GetField ("field_j"), vm.CreateValue (1));
1050                         });
1051         }
1052
1053         [Test]
1054         public void TypeInfo () {
1055                 Event e = run_until ("ti2");
1056                 StackFrame frame = e.Thread.GetFrames () [0];
1057
1058                 TypeMirror t;
1059
1060                 // Array types
1061                 t = frame.Method.GetParameters ()[0].ParameterType;
1062
1063                 Assert.AreEqual ("String[]", t.Name);
1064                 Assert.AreEqual ("string[]", t.CSharpName);
1065                 Assert.AreEqual ("Array", t.BaseType.Name);
1066                 Assert.AreEqual (true, t.HasElementType);
1067                 Assert.AreEqual (true, t.IsArray);
1068                 Assert.AreEqual (1, t.GetArrayRank ());
1069                 Assert.AreEqual ("String", t.GetElementType ().Name);
1070
1071                 t = frame.Method.GetParameters ()[2].ParameterType;
1072
1073                 Assert.AreEqual ("Int32[,]", t.Name);
1074                 // FIXME:
1075                 //Assert.AreEqual ("int[,]", t.CSharpName);
1076                 Assert.AreEqual ("Array", t.BaseType.Name);
1077                 Assert.AreEqual (true, t.HasElementType);
1078                 Assert.AreEqual (true, t.IsArray);
1079                 Assert.AreEqual (2, t.GetArrayRank ());
1080                 Assert.AreEqual ("Int32", t.GetElementType ().Name);
1081
1082                 // Byref types
1083                 t = frame.Method.GetParameters ()[3].ParameterType;
1084                 // FIXME:
1085                 //Assert.AreEqual ("Int32&", t.Name);
1086                 //Assert.AreEqual (true, t.IsByRef);
1087                 //Assert.AreEqual (true, t.HasElementType);
1088
1089                 // Pointer types
1090                 t = frame.Method.GetParameters ()[4].ParameterType;
1091                 // FIXME:
1092                 //Assert.AreEqual ("Int32*", t.Name);
1093                 Assert.AreEqual (true, t.IsPointer);
1094                 Assert.AreEqual (true, t.HasElementType);
1095                 Assert.AreEqual ("Int32", t.GetElementType ().Name);
1096                 Assert.AreEqual (false, t.IsPrimitive);
1097
1098                 // primitive types 
1099                 t = frame.Method.GetParameters ()[5].ParameterType;
1100                 Assert.AreEqual (true, t.IsPrimitive);
1101
1102                 // value types
1103                 t = frame.Method.GetParameters ()[6].ParameterType;
1104                 Assert.AreEqual ("AStruct", t.Name);
1105                 Assert.AreEqual (false, t.IsPrimitive);
1106                 Assert.AreEqual (true, t.IsValueType);
1107                 Assert.AreEqual (false, t.IsClass);
1108
1109                 // reference types
1110                 t = frame.Method.GetParameters ()[7].ParameterType;
1111                 Assert.AreEqual ("Tests", t.Name);
1112                 var nested = (from nt in t.GetNestedTypes () where nt.IsNestedPublic select nt).ToArray ();
1113                 Assert.AreEqual (1, nested.Length);
1114                 Assert.AreEqual ("NestedClass", nested [0].Name);
1115                 Assert.IsTrue (t.BaseType.IsAssignableFrom (t));
1116                 Assert.IsTrue (!t.IsAssignableFrom (t.BaseType));
1117
1118                 // generic instances
1119                 t = frame.Method.GetParameters ()[9].ParameterType;
1120                 Assert.AreEqual ("GClass`1", t.Name);
1121                 Assert.IsTrue (t.IsGenericType);
1122                 Assert.IsFalse (t.IsGenericTypeDefinition);
1123
1124                 var args = t.GetGenericArguments ();
1125                 Assert.AreEqual (1, args.Length);
1126                 Assert.AreEqual ("Int32", args [0].Name);
1127
1128                 // generic type definitions
1129                 var gtd = t.GetGenericTypeDefinition ();
1130                 Assert.AreEqual ("GClass`1", gtd.Name);
1131                 Assert.IsTrue (gtd.IsGenericType);
1132                 Assert.IsTrue (gtd.IsGenericTypeDefinition);
1133                 Assert.AreEqual (gtd, gtd.GetGenericTypeDefinition ());
1134
1135                 args = gtd.GetGenericArguments ();
1136                 Assert.AreEqual (1, args.Length);
1137                 Assert.AreEqual ("T", args [0].Name);
1138
1139                 // enums
1140                 t = frame.Method.GetParameters ()[10].ParameterType;
1141                 Assert.AreEqual ("AnEnum", t.Name);
1142                 Assert.IsTrue (t.IsEnum);
1143                 Assert.AreEqual ("Int32", t.EnumUnderlyingType.Name);
1144
1145                 // TypedReferences
1146                 t = frame.Method.GetParameters ()[11].ParameterType;
1147                 Assert.AreEqual ("TypedReference", t.Name);
1148
1149                 // properties
1150                 t = frame.Method.GetParameters ()[7].ParameterType;
1151
1152                 var props = t.GetProperties ();
1153                 Assert.AreEqual (3, props.Length);
1154                 foreach (PropertyInfoMirror prop in props) {
1155                         ParameterInfoMirror[] indexes = prop.GetIndexParameters ();
1156
1157                         if (prop.Name == "IntProperty") {
1158                                 Assert.AreEqual ("Int32", prop.PropertyType.Name);
1159                                 Assert.AreEqual ("get_IntProperty", prop.GetGetMethod ().Name);
1160                                 Assert.AreEqual ("set_IntProperty", prop.GetSetMethod ().Name);
1161                                 Assert.AreEqual (0, indexes.Length);
1162                         } else if (prop.Name == "ReadOnlyProperty") {
1163                                 Assert.AreEqual ("Int32", prop.PropertyType.Name);
1164                                 Assert.AreEqual ("get_ReadOnlyProperty", prop.GetGetMethod ().Name);
1165                                 Assert.AreEqual (null, prop.GetSetMethod ());
1166                                 Assert.AreEqual (0, indexes.Length);
1167                         } else if (prop.Name == "IndexedProperty") {
1168                                 Assert.AreEqual (1, indexes.Length);
1169                                 Assert.AreEqual ("Int32", indexes [0].ParameterType.Name);
1170                         }
1171                 }
1172
1173                 // custom attributes
1174                 t = frame.Method.GetParameters ()[8].ParameterType;
1175                 Assert.AreEqual ("Tests2", t.Name);
1176                 var attrs = t.GetCustomAttributes (true);
1177                 Assert.AreEqual (5, attrs.Length);
1178                 foreach (var attr in attrs) {
1179                         if (attr.Constructor.DeclaringType.Name == "DebuggerDisplayAttribute") {
1180                                 Assert.AreEqual (1, attr.ConstructorArguments.Count);
1181                                 Assert.AreEqual ("Tests", attr.ConstructorArguments [0].Value);
1182                                 Assert.AreEqual (2, attr.NamedArguments.Count);
1183                                 Assert.AreEqual ("Name", attr.NamedArguments [0].Property.Name);
1184                                 Assert.AreEqual ("FOO", attr.NamedArguments [0].TypedValue.Value);
1185                                 Assert.AreEqual ("Target", attr.NamedArguments [1].Property.Name);
1186                                 Assert.IsInstanceOfType (typeof (TypeMirror), attr.NamedArguments [1].TypedValue.Value);
1187                                 Assert.AreEqual ("Int32", (attr.NamedArguments [1].TypedValue.Value as TypeMirror).Name);
1188                         } else if (attr.Constructor.DeclaringType.Name == "DebuggerTypeProxyAttribute") {
1189                                 Assert.AreEqual (1, attr.ConstructorArguments.Count);
1190                                 Assert.IsInstanceOfType (typeof (TypeMirror), attr.ConstructorArguments [0].Value);
1191                                 Assert.AreEqual ("Tests", (attr.ConstructorArguments [0].Value as TypeMirror).Name);
1192                         } else if (attr.Constructor.DeclaringType.Name == "BAttribute") {
1193                                 Assert.AreEqual (2, attr.NamedArguments.Count);
1194                                 Assert.AreEqual ("afield", attr.NamedArguments [0].Field.Name);
1195                                 Assert.AreEqual ("bfield", attr.NamedArguments [1].Field.Name);
1196                         } else if (attr.Constructor.DeclaringType.Name == "ClassInterfaceAttribute") {
1197                                 // inherited from System.Object
1198                                 //} else if (attr.Constructor.DeclaringType.Name == "Serializable") {
1199                                 // inherited from System.Object
1200                         } else if (attr.Constructor.DeclaringType.Name == "ComVisibleAttribute") {
1201                                 // inherited from System.Object
1202                         } else {
1203                                 Assert.Fail (attr.Constructor.DeclaringType.Name);
1204                         }
1205                 }
1206
1207                 var assembly = entry_point.DeclaringType.Assembly;
1208                 var type = assembly.GetType ("Tests4");
1209                 Assert.IsFalse (type.IsInitialized);
1210         }
1211
1212         [Test]
1213         public void FieldInfo () {
1214                 Event e = run_until ("ti2");
1215                 StackFrame frame = e.Thread.GetFrames () [0];
1216
1217                 TypeMirror t;
1218
1219                 t = frame.Method.GetParameters ()[8].ParameterType;
1220                 Assert.AreEqual ("Tests2", t.Name);
1221
1222                 var fi = t.GetField ("field_j");
1223                 var attrs = fi.GetCustomAttributes (true);
1224                 Assert.AreEqual (1, attrs.Length);
1225                 var attr = attrs [0];
1226                 Assert.AreEqual ("DebuggerBrowsableAttribute", attr.Constructor.DeclaringType.Name);
1227                 Assert.AreEqual (1, attr.ConstructorArguments.Count);
1228                 Assert.IsInstanceOfType (typeof (EnumMirror), attr.ConstructorArguments [0].Value);
1229                 Assert.AreEqual ((int)System.Diagnostics.DebuggerBrowsableState.Collapsed, (attr.ConstructorArguments [0].Value as EnumMirror).Value);
1230         }
1231
1232         [Test]
1233         public void PropertyInfo () {
1234                 Event e = run_until ("ti2");
1235                 StackFrame frame = e.Thread.GetFrames () [0];
1236
1237                 TypeMirror t;
1238
1239                 t = frame.Method.GetParameters ()[8].ParameterType;
1240                 Assert.AreEqual ("Tests2", t.Name);
1241
1242                 var pi = t.GetProperty ("AProperty");
1243                 var attrs = pi.GetCustomAttributes (true);
1244                 Assert.AreEqual (1, attrs.Length);
1245                 var attr = attrs [0];
1246                 Assert.AreEqual ("DebuggerBrowsableAttribute", attr.Constructor.DeclaringType.Name);
1247                 Assert.AreEqual (1, attr.ConstructorArguments.Count);
1248                 Assert.IsInstanceOfType (typeof (EnumMirror), attr.ConstructorArguments [0].Value);
1249                 Assert.AreEqual ((int)System.Diagnostics.DebuggerBrowsableState.Collapsed, (attr.ConstructorArguments [0].Value as EnumMirror).Value);
1250         }
1251
1252         [Test]
1253         [Category ("only5")]
1254         public void Type_GetValue () {
1255                 Event e = run_until ("o1");
1256                 StackFrame frame = e.Thread.GetFrames () [0];
1257
1258                 ObjectMirror o = (frame.GetThis () as ObjectMirror);
1259
1260                 TypeMirror t = o.Type;
1261
1262                 ObjectMirror val2 = frame.GetValue (frame.Method.GetParameters ()[0]) as ObjectMirror;
1263
1264                 // static fields
1265                 object f = t.GetValue (o.Type.GetField ("static_i"));
1266                 AssertValue (55, f);
1267
1268                 f = t.GetValue (o.Type.GetField ("static_s"));
1269                 AssertValue ("A", f);
1270
1271                 // literal static fields
1272                 f = t.GetValue (o.Type.GetField ("literal_i"));
1273                 AssertValue (56, f);
1274
1275                 f = t.GetValue (o.Type.GetField ("literal_s"));
1276                 AssertValue ("B", f);
1277
1278                 // Inherited static fields
1279                 TypeMirror parent = t.BaseType;
1280                 f = t.GetValue (parent.GetField ("base_static_i"));
1281                 AssertValue (57, f);
1282
1283                 f = t.GetValue (parent.GetField ("base_static_s"));
1284                 AssertValue ("C", f);
1285
1286                 // thread static field
1287                 f = t.GetValue (t.GetField ("tls_i"), e.Thread);
1288                 AssertValue (42, f);
1289
1290                 // Argument checking
1291                 AssertThrows<ArgumentNullException> (delegate () {
1292                         t.GetValue (null);
1293                         });
1294
1295                 // instance fields
1296                 AssertThrows<ArgumentException> (delegate () {
1297                         t.GetValue (o.Type.GetField ("field_i"));
1298                         });
1299
1300                 // field on another type
1301                 AssertThrows<ArgumentException> (delegate () {
1302                                 t.GetValue (val2.Type.GetField ("static_field_j"));
1303                         });
1304
1305                 // special static field
1306                 AssertThrows<ArgumentException> (delegate () {
1307                                 t.GetValue (t.GetField ("tls_i"));
1308                         });
1309         }
1310
1311         [Test]
1312         public void Type_GetValues () {
1313                 Event e = run_until ("o1");
1314                 StackFrame frame = e.Thread.GetFrames () [0];
1315
1316                 ObjectMirror o = (frame.GetThis () as ObjectMirror);
1317
1318                 TypeMirror t = o.Type;
1319
1320                 // static fields
1321                 object[] vals = t.GetValues (new FieldInfoMirror [] { t.GetField ("static_i"), t.GetField ("static_s") });
1322                 object f = vals [0];
1323                 AssertValue (55, f);
1324
1325                 f = vals [1];
1326                 AssertValue ("A", f);
1327
1328                 // Argument checking
1329                 AssertThrows<ArgumentNullException> (delegate () {
1330                         t.GetValues (null);
1331                         });
1332
1333                 AssertThrows<ArgumentNullException> (delegate () {
1334                         t.GetValues (new FieldInfoMirror [] { null });
1335                         });
1336         }
1337
1338         [Test]
1339         public void ObjRefs () {
1340                 Event e = run_until ("objrefs1");
1341                 StackFrame frame = e.Thread.GetFrames () [0];
1342
1343                 ObjectMirror o = frame.GetThis () as ObjectMirror;
1344                 ObjectMirror child = o.GetValue (o.Type.GetField ("child")) as ObjectMirror;
1345
1346                 Assert.IsTrue (child.Address != 0);
1347
1348                 // Check that object references are internalized correctly
1349                 Assert.AreEqual (o, frame.GetThis ());
1350
1351                 run_until ("objrefs2");
1352
1353                 // child should be gc'd now
1354                 // This is not deterministic
1355                 //Assert.IsTrue (child.IsCollected);
1356
1357                 /*
1358                  * No longer works since Type is read eagerly
1359                  */
1360                 /*
1361                 AssertThrows<ObjectCollectedException> (delegate () {
1362                         TypeMirror t = child.Type;
1363                         });
1364                 */
1365                 /*
1366                 AssertThrows<ObjectCollectedException> (delegate () {
1367                                 long addr = child.Address;
1368                         });
1369                 */
1370         }
1371
1372         [Test]
1373         public void Type_GetObject () {
1374                 Event e = run_until ("o1");
1375                 StackFrame frame = e.Thread.GetFrames () [0];
1376
1377                 ObjectMirror o = (frame.GetThis () as ObjectMirror);
1378
1379                 TypeMirror t = o.Type;
1380
1381                 Assert.AreEqual ("MonoType", t.GetTypeObject ().Type.Name);
1382         }
1383
1384         [Test]
1385         public void VTypes () {
1386                 Event e = run_until ("vtypes1");
1387                 StackFrame frame = e.Thread.GetFrames () [0];
1388
1389                 // vtypes as fields
1390                 ObjectMirror o = frame.GetThis () as ObjectMirror;
1391                 var obj = o.GetValue (o.Type.GetField ("field_struct"));
1392                 Assert.IsTrue (obj is StructMirror);
1393                 var s = obj as StructMirror;
1394                 Assert.AreEqual ("AStruct", s.Type.Name);
1395                 AssertValue (42, s ["i"]);
1396                 obj = s ["s"];
1397                 AssertValue ("S", obj);
1398                 AssertValue (43, s ["k"]);
1399                 obj = o.GetValue (o.Type.GetField ("field_boxed_struct"));
1400                 Assert.IsTrue (obj is StructMirror);
1401                 s = obj as StructMirror;
1402                 Assert.AreEqual ("AStruct", s.Type.Name);
1403                 AssertValue (42, s ["i"]);
1404
1405                 // Check decoding of nested structs (#14942)
1406                 obj = o.GetValue (o.Type.GetField ("nested_struct"));
1407                 o.SetValue (o.Type.GetField ("nested_struct"), obj);
1408
1409                 // Check round tripping of boxed struct fields (#12354)
1410                 obj = o.GetValue (o.Type.GetField ("boxed_struct_field"));
1411                 o.SetValue (o.Type.GetField ("boxed_struct_field"), obj);
1412                 obj = o.GetValue (o.Type.GetField ("boxed_struct_field"));
1413                 s = obj as StructMirror;
1414                 AssertValue (1, s ["key"]);
1415                 obj = s ["value"];
1416                 Assert.IsTrue (obj is StructMirror);
1417                 s = obj as StructMirror;
1418                 AssertValue (42, s ["m_value"]);
1419
1420                 // vtypes as arguments
1421                 s = frame.GetArgument (0) as StructMirror;
1422                 AssertValue (44, s ["i"]);
1423                 obj = s ["s"];
1424                 AssertValue ("T", obj);
1425                 AssertValue (45, s ["k"]);
1426
1427                 // vtypes as array entries
1428                 var arr = frame.GetArgument (1) as ArrayMirror;
1429                 obj = arr [0];
1430                 Assert.IsTrue (obj is StructMirror);
1431                 s = obj as StructMirror;
1432                 AssertValue (1, s ["i"]);
1433                 AssertValue ("S1", s ["s"]);
1434                 obj = arr [1];
1435                 Assert.IsTrue (obj is StructMirror);
1436                 s = obj as StructMirror;
1437                 AssertValue (2, s ["i"]);
1438                 AssertValue ("S2", s ["s"]);
1439
1440                 // typedbyref
1441                 var typedref = frame.GetArgument (2) as StructMirror;
1442                 Assert.IsTrue (typedref is StructMirror);
1443
1444                 // Argument checking
1445                 s = frame.GetArgument (0) as StructMirror;
1446                 AssertThrows<ArgumentException> (delegate () {
1447                                 obj = s ["FOO"];
1448                         });
1449
1450                 // generic vtype instances
1451                 o = frame.GetThis () as ObjectMirror;
1452                 obj = o.GetValue (o.Type.GetField ("generic_field_struct"));
1453                 Assert.IsTrue (obj is StructMirror);
1454                 s = obj as StructMirror;
1455                 Assert.AreEqual ("GStruct`1", s.Type.Name);
1456                 AssertValue (42, s ["i"]);
1457
1458                 // this on vtype methods
1459                 e = run_until ("vtypes2");
1460                 e = step_until (e.Thread, "foo");
1461
1462                 frame = e.Thread.GetFrames () [0];
1463
1464                 Assert.AreEqual ("foo", (e as StepEvent).Method.Name);
1465                 obj = frame.GetThis ();
1466
1467                 Assert.IsTrue (obj is StructMirror);
1468                 s = obj as StructMirror;
1469                 AssertValue (44, s ["i"]);
1470                 AssertValue ("T", s ["s"]);
1471                 AssertValue (45, s ["k"]);
1472
1473                 // this on static vtype methods
1474                 e = run_until ("vtypes3");
1475                 e = step_until (e.Thread, "static_foo");
1476
1477                 frame = e.Thread.GetFrames () [0];
1478
1479                 Assert.AreEqual ("static_foo", (e as StepEvent).Method.Name);
1480                 obj = frame.GetThis ();
1481                 AssertValue (null, obj);
1482
1483                 // vtypes which reference themselves recursively
1484                 e = run_until ("vtypes4_2");
1485                 frame = e.Thread.GetFrames () [0];
1486
1487                 Assert.IsTrue (frame.GetArgument (0) is StructMirror);
1488         }
1489
1490         [Test]
1491         public void AssemblyInfo () {
1492                 Event e = run_until ("single_stepping");
1493
1494                 StackFrame frame = e.Thread.GetFrames () [0];
1495
1496                 var aname = frame.Method.DeclaringType.Assembly.GetName ();
1497                 Assert.AreEqual ("dtest-app, Version=0.0.0.0, Culture=neutral, PublicKeyToken=null", aname.ToString ());
1498
1499                 ModuleMirror m = frame.Method.DeclaringType.Module;
1500
1501                 Assert.AreEqual ("dtest-app.exe", m.Name);
1502                 Assert.AreEqual ("dtest-app.exe", m.ScopeName);
1503                 Assert.IsTrue (m.FullyQualifiedName.IndexOf ("dtest-app.exe") != -1);
1504                 Guid guid = m.ModuleVersionId;
1505                 Assert.AreEqual (frame.Method.DeclaringType.Assembly, m.Assembly);
1506                 Assert.AreEqual (frame.Method.DeclaringType.Assembly.ManifestModule, m);
1507
1508                 // This is no longer true on 4.0
1509                 //Assert.AreEqual ("Assembly", frame.Method.DeclaringType.Assembly.GetAssemblyObject ().Type.Name);
1510
1511                 TypeMirror t = vm.RootDomain.Corlib.GetType ("System.Diagnostics.DebuggerDisplayAttribute");
1512                 Assert.AreEqual ("DebuggerDisplayAttribute", t.Name);
1513         }
1514
1515         [Test]
1516         public void LocalsInfo () {
1517                 Event e = run_until ("locals2");
1518
1519                 StackFrame frame = e.Thread.GetFrames () [0];
1520
1521                 var locals = frame.Method.GetLocals ();
1522                 Assert.AreEqual (9, locals.Length);
1523                 for (int i = 0; i < 9; ++i) {
1524                         if (locals [i].Name == "args") {
1525                                 Assert.IsTrue (locals [i].IsArg);
1526                                 Assert.AreEqual ("String[]", locals [i].Type.Name);
1527                         } else if (locals [i].Name == "arg") {
1528                                 Assert.IsTrue (locals [i].IsArg);
1529                                 Assert.AreEqual ("Int32", locals [i].Type.Name);
1530                         } else if (locals [i].Name == "i") {
1531                                 Assert.IsFalse (locals [i].IsArg);
1532                                 Assert.AreEqual ("Int64", locals [i].Type.Name);
1533                         } else if (locals [i].Name == "j") {
1534                                 Assert.IsFalse (locals [i].IsArg);
1535                                 Assert.AreEqual ("Int32", locals [i].Type.Name);
1536                         } else if (locals [i].Name == "s") {
1537                                 Assert.IsFalse (locals [i].IsArg);
1538                                 Assert.AreEqual ("String", locals [i].Type.Name);
1539                         } else if (locals [i].Name == "t") {
1540                                 // gshared
1541                                 Assert.IsTrue (locals [i].IsArg);
1542                                 Assert.AreEqual ("String", locals [i].Type.Name);
1543                         } else if (locals [i].Name == "rs") {
1544                                 Assert.IsTrue (locals [i].IsArg);
1545                                 Assert.AreEqual ("String", locals [i].Type.Name);
1546                         } else if (locals [i].Name == "astruct") {
1547                         } else if (locals [i].Name == "alist") {
1548                         } else {
1549                                 Assert.Fail ();
1550                         }
1551                 }
1552         }
1553
1554         Event step_once () {
1555                 vm.Resume ();
1556                 var e = GetNextEvent ();
1557                 Assert.IsTrue (e is StepEvent);
1558                 return e;
1559         }
1560
1561         Event step_into () {
1562                 step_req.Disable ();
1563                 step_req.Depth = StepDepth.Into;
1564                 step_req.Enable ();
1565                 return step_once ();
1566         }
1567
1568         Event step_over () {
1569                 step_req.Disable ();
1570                 step_req.Depth = StepDepth.Over;
1571                 step_req.Enable ();
1572                 return step_once ();
1573         }
1574
1575         Event step_out () {
1576                 step_req.Disable ();
1577                 step_req.Depth = StepDepth.Out;
1578                 step_req.Enable ();
1579                 return step_once ();
1580         }
1581
1582         [Test]
1583         public void Locals () {
1584                 var be = run_until ("locals1");
1585
1586                 StackFrame frame = be.Thread.GetFrames () [0];
1587                 MethodMirror m1 = frame.Method;
1588
1589                 // Compiler generated byref local
1590                 foreach (var l in m1.GetLocals ()) {
1591                         // The byval flag is hidden from the type
1592                         if (l.Name != "ri" && l.Type.Name == "Double")
1593                                 AssertValue (null, frame.GetValue (l));
1594                 }
1595
1596                 be = run_until ("locals2");
1597
1598                 frame = be.Thread.GetFrames () [0];
1599
1600                 object val = frame.GetValue (frame.Method.GetLocal ("i"));
1601                 AssertValue (0, val);
1602
1603                 var req = create_step (be);
1604                 req.Enable ();
1605
1606                 // Skip nop
1607                 step_once ();
1608
1609                 // Execute i = 42
1610                 var e = step_once ();
1611                 Assert.AreEqual ("locals2", (e as StepEvent).Method.Name);
1612
1613                 // Execute s = "AB";
1614                 e = step_once ();
1615                 Assert.AreEqual ("locals2", (e as StepEvent).Method.Name);
1616
1617                 frame = e.Thread.GetFrames () [0];
1618
1619                 val = frame.GetValue (frame.Method.GetLocal ("i"));
1620                 AssertValue (42, val);
1621
1622                 LocalVariable[] locals = frame.Method.GetLocals ();
1623                 var vals = frame.GetValues (locals);
1624                 Assert.AreEqual (locals.Length, vals.Length);
1625                 for (int i = 0; i < locals.Length; ++i) {
1626                         if (locals [i].Name == "i")
1627                                 AssertValue (42, vals [i]);
1628                         if (locals [i].Name == "s")
1629                                 AssertValue ("AB", vals [i]);
1630                         if (locals [i].Name == "t")
1631                                 AssertValue ("ABC", vals [i]);
1632                         if (locals [i].Name == "alist") {
1633                         }
1634                 }
1635
1636                 // Argument checking
1637
1638                 // GetValue () null
1639                 AssertThrows<ArgumentNullException> (delegate () {
1640                                 frame.GetValue ((LocalVariable)null);
1641                         });
1642                 // GetValue () local from another method
1643                 AssertThrows<ArgumentException> (delegate () {
1644                                 frame.GetValue (m1.GetLocal ("foo"));
1645                         });
1646
1647                 // GetValue () null
1648                 AssertThrows<ArgumentNullException> (delegate () {
1649                                 frame.GetValue ((ParameterInfoMirror)null);
1650                         });
1651                 // GetValue () local from another method
1652                 AssertThrows<ArgumentException> (delegate () {
1653                                 frame.GetValue (m1.GetParameters ()[0]);
1654                         });
1655
1656                 // GetValues () null
1657                 AssertThrows<ArgumentNullException> (delegate () {
1658                                 frame.GetValues (null);
1659                         });
1660                 // GetValues () embedded null
1661                 AssertThrows<ArgumentNullException> (delegate () {
1662                                 frame.GetValues (new LocalVariable [] { null });
1663                         });
1664                 // GetValues () local from another method
1665                 AssertThrows<ArgumentException> (delegate () {
1666                                 frame.GetValues (new LocalVariable [] { m1.GetLocal ("foo") });
1667                         });
1668                 // return value
1669                 AssertThrows<ArgumentException> (delegate () {
1670                                 val = frame.GetValue (frame.Method.ReturnParameter);
1671                         });
1672
1673                 // invalid stack frames
1674                 vm.Resume ();
1675                 e = GetNextEvent ();
1676                 Assert.IsTrue (e is StepEvent);
1677                 Assert.AreEqual ("locals2", (e as StepEvent).Method.Name);
1678
1679                 AssertThrows<InvalidStackFrameException> (delegate () {
1680                                 frame.GetValue (frame.Method.GetLocal ("i"));
1681                         });
1682
1683                 req.Disable ();
1684
1685                 // gsharedvt
1686                 be = run_until ("locals7");
1687
1688                 req = create_step (be);
1689                 req.Enable ();
1690
1691                 // Skip nop
1692                 e = step_once ();
1693
1694                 // Test that locals are initialized
1695                 frame = e.Thread.GetFrames () [0];
1696                 val = frame.GetValue (frame.Method.GetLocal ("t"));
1697                 AssertValue (0, val);
1698
1699                 // Execute t = arg
1700                 e = step_once ();
1701                 Assert.AreEqual ("locals7", (e as StepEvent).Method.Name);
1702
1703                 // Execute t2 = t
1704                 e = step_once ();
1705                 Assert.AreEqual ("locals7", (e as StepEvent).Method.Name);
1706
1707                 frame = e.Thread.GetFrames () [0];
1708                 val = frame.GetValue (frame.Method.GetParameters ()[0]);
1709                 AssertValue (22, val);
1710                 val = frame.GetValue (frame.Method.GetLocal ("t"));
1711                 AssertValue (22, val);
1712                 val = frame.GetValue (frame.Method.GetLocal ("t2"));
1713                 AssertValue (22, val);
1714         }
1715
1716         [Test]
1717         public void GetVisibleVariables () {
1718                 Event e = run_until ("locals4");
1719
1720                 // First scope
1721                 var locals = e.Thread.GetFrames ()[1].GetVisibleVariables ();
1722                 Assert.AreEqual (2, locals.Count);
1723                 var loc = locals.First (l => l.Name == "i");
1724                 Assert.AreEqual ("Int64", loc.Type.Name);
1725                 loc = locals.First (l => l.Name == "s");
1726                 Assert.AreEqual ("String", loc.Type.Name);
1727
1728                 loc = e.Thread.GetFrames ()[1].GetVisibleVariableByName ("i");
1729                 Assert.AreEqual ("i", loc.Name);
1730                 Assert.AreEqual ("Int64", loc.Type.Name);
1731
1732                 e = run_until ("locals5");
1733
1734                 // Second scope
1735                 locals = e.Thread.GetFrames ()[1].GetVisibleVariables ();
1736                 Assert.AreEqual (2, locals.Count);
1737                 loc = locals.First (l => l.Name == "i");
1738                 Assert.AreEqual ("String", loc.Type.Name);
1739                 loc = locals.First (l => l.Name == "s");
1740                 Assert.AreEqual ("String", loc.Type.Name);
1741
1742                 loc = e.Thread.GetFrames ()[1].GetVisibleVariableByName ("i");
1743                 Assert.AreEqual ("i", loc.Name);
1744                 Assert.AreEqual ("String", loc.Type.Name);
1745
1746                 // Variable in another scope
1747                 loc = e.Thread.GetFrames ()[1].GetVisibleVariableByName ("j");
1748                 Assert.IsNull (loc);
1749         }
1750
1751         [Test]
1752         public void Exit () {
1753                 run_until ("Main");
1754
1755                 vm.Exit (5);
1756
1757                 var e = GetNextEvent ();
1758                 Assert.IsInstanceOfType (typeof (VMDeathEvent), e);
1759
1760                 Assert.AreEqual (5, (e as VMDeathEvent).ExitCode);
1761
1762                 var p = vm.Process;
1763                 /* Could be a remote vm with no process */
1764                 if (p != null) {
1765                         p.WaitForExit ();
1766                         Assert.AreEqual (5, p.ExitCode);
1767
1768                         // error handling
1769                         AssertThrows<VMDisconnectedException> (delegate () {
1770                                         vm.Resume ();
1771                                 });
1772                 }
1773
1774                 vm = null;
1775         }
1776
1777         [Test]
1778         public void Dispose () {
1779                 run_until ("Main");
1780
1781                 vm.Detach ();
1782
1783                 var e = GetNextEvent ();
1784                 Assert.IsInstanceOfType (typeof (VMDisconnectEvent), e);
1785
1786                 var p = vm.Process;
1787                 /* Could be a remote vm with no process */
1788                 if (p != null) {
1789                         p.WaitForExit ();
1790                         Assert.AreEqual (3, p.ExitCode);
1791
1792                         // error handling
1793                         AssertThrows<VMDisconnectedException> (delegate () {
1794                                         vm.Resume ();
1795                                 });
1796                 }
1797
1798                 vm = null;
1799         }
1800
1801         [Test]
1802         public void ColumnNumbers () {
1803                 Event e = run_until ("line_numbers");
1804
1805                 // FIXME: Merge this with LineNumbers () when its fixed
1806
1807                 step_req = create_step (e);
1808                 step_req.Depth = StepDepth.Into;
1809                 step_req.Enable ();
1810
1811                 Location l;
1812                 
1813                 while (true) {
1814                         vm.Resume ();
1815
1816                         e = GetNextEvent ();
1817                         Assert.IsTrue (e is StepEvent);
1818                         if (e.Thread.GetFrames ()[0].Method.Name == "ln1")
1819                                 break;
1820                 }
1821
1822                 // Do an additional step over so we are not on the beginning line of the method
1823                 step_req.Disable ();
1824                 step_req.Depth = StepDepth.Over;
1825                 step_req.Enable ();
1826                 vm.Resume ();
1827                 e = GetNextEvent ();
1828                 Assert.IsTrue (e is StepEvent);         
1829
1830                 l = e.Thread.GetFrames ()[0].Location;
1831
1832                 Assert.AreEqual (3, l.ColumnNumber);
1833
1834                 step_req.Disable ();
1835         }
1836
1837         [Test]
1838         // Broken by mcs+runtime changes (#5438)
1839         [Category("NotWorking")]
1840         public void LineNumbers () {
1841                 Event e = run_until ("line_numbers");
1842
1843                 step_req = create_step (e);
1844                 step_req.Depth = StepDepth.Into;
1845                 step_req.Enable ();
1846
1847                 Location l;
1848                 
1849                 vm.Resume ();
1850
1851                 e = GetNextEvent ();
1852                 Assert.IsTrue (e is StepEvent);
1853
1854                 l = e.Thread.GetFrames ()[0].Location;
1855
1856                 Assert.IsTrue (l.SourceFile.IndexOf ("dtest-app.cs") != -1);
1857                 Assert.AreEqual ("ln1", l.Method.Name);
1858
1859                 // Check hash
1860                 using (FileStream fs = new FileStream (l.SourceFile, FileMode.Open, FileAccess.Read)) {
1861                         MD5 md5 = MD5.Create ();
1862                         var hash = md5.ComputeHash (fs);
1863
1864                         for (int i = 0; i < 16; ++i)
1865                                 Assert.AreEqual (hash [i], l.SourceFileHash [i]);
1866                 }
1867                 
1868                 int line_base = l.LineNumber;
1869
1870                 vm.Resume ();
1871                 e = GetNextEvent ();
1872                 Assert.IsTrue (e is StepEvent);
1873                 l = e.Thread.GetFrames ()[0].Location;
1874                 Assert.AreEqual ("ln2", l.Method.Name);
1875                 Assert.AreEqual (line_base + 6, l.LineNumber);
1876
1877                 vm.Resume ();
1878                 e = GetNextEvent ();
1879                 Assert.IsTrue (e is StepEvent);
1880                 l = e.Thread.GetFrames ()[0].Location;
1881                 Assert.AreEqual ("ln1", l.Method.Name);
1882                 Assert.AreEqual (line_base + 1, l.LineNumber);
1883
1884                 vm.Resume ();
1885                 e = GetNextEvent ();
1886                 Assert.IsTrue (e is StepEvent);
1887                 l = e.Thread.GetFrames ()[0].Location;
1888                 Assert.AreEqual ("ln3", l.Method.Name);
1889                 Assert.AreEqual (line_base + 11, l.LineNumber);
1890
1891                 vm.Resume ();
1892                 e = GetNextEvent ();
1893                 Assert.IsTrue (e is StepEvent);
1894                 l = e.Thread.GetFrames ()[0].Location;
1895                 Assert.AreEqual ("ln3", l.Method.Name);
1896                 Assert.IsTrue (l.SourceFile.EndsWith ("FOO"));
1897                 Assert.AreEqual (55, l.LineNumber);
1898
1899                 vm.Resume ();
1900                 e = GetNextEvent ();
1901                 Assert.IsTrue (e is StepEvent);
1902                 l = e.Thread.GetFrames ()[0].Location;
1903                 Assert.AreEqual ("ln1", l.Method.Name);
1904                 Assert.AreEqual (line_base + 2, l.LineNumber);
1905
1906                 // GetSourceFiles ()
1907                 string[] sources = l.Method.DeclaringType.GetSourceFiles ();
1908                 Assert.AreEqual (2, sources.Length);
1909                 Assert.AreEqual ("dtest-app.cs", sources [0]);
1910                 Assert.AreEqual ("FOO", sources [1]);
1911
1912                 sources = l.Method.DeclaringType.GetSourceFiles (true);
1913                 Assert.AreEqual (2, sources.Length);
1914                 Assert.IsTrue (sources [0].EndsWith ("dtest-app.cs"));
1915                 Assert.IsTrue (sources [1].EndsWith ("FOO"));
1916         }
1917
1918         [Test]
1919         public void Suspend () {
1920                 vm.Detach ();
1921
1922                 Start (new string [] { "dtest-app.exe", "suspend-test" });
1923
1924                 Event e = run_until ("suspend");
1925
1926                 ThreadMirror main = e.Thread;
1927
1928                 vm.Resume ();
1929
1930                 Thread.Sleep (100);
1931
1932                 vm.Suspend ();
1933
1934                 // The debuggee should be suspended while it is running the infinite loop
1935                 // in suspend ()
1936                 StackFrame frame = main.GetFrames ()[0];
1937                 Assert.AreEqual ("suspend", frame.Method.Name);
1938
1939                 vm.Resume ();
1940
1941                 // resuming when not suspended
1942                 AssertThrows<InvalidOperationException> (delegate () {
1943                                 vm.Resume ();
1944                         });
1945
1946                 vm.Exit (0);
1947
1948                 vm = null;
1949         }
1950
1951         [Test]
1952         public void AssemblyLoad () {
1953                 Event e = run_until ("assembly_load");
1954
1955                 var load_req = vm.CreateAssemblyLoadRequest ();
1956                 load_req.Enable ();
1957
1958                 vm.Resume ();
1959
1960                 e = GetNextEvent ();
1961                 Assert.IsInstanceOfType (typeof (AssemblyLoadEvent), e);
1962                 Assert.IsTrue ((e as AssemblyLoadEvent).Assembly.Location.EndsWith ("System.dll"));
1963
1964                 var frames = e.Thread.GetFrames ();
1965                 Assert.IsTrue (frames.Length > 0);
1966                 Assert.AreEqual ("assembly_load", frames [0].Method.Name);
1967         }
1968
1969         [Test]
1970         public void CreateValue () {
1971                 PrimitiveValue v;
1972
1973                 v = vm.CreateValue (1);
1974                 Assert.AreEqual (vm, v.VirtualMachine);
1975                 Assert.AreEqual (1, v.Value);
1976
1977                 v = vm.CreateValue (null);
1978                 Assert.AreEqual (vm, v.VirtualMachine);
1979                 Assert.AreEqual (null, v.Value);
1980
1981                 // Argument checking
1982                 AssertThrows <ArgumentException> (delegate () {
1983                                 v = vm.CreateValue ("FOO");
1984                         });
1985         }
1986
1987         [Test]
1988         public void CreateString () {
1989                 StringMirror s = vm.RootDomain.CreateString ("ABC");
1990
1991                 Assert.AreEqual (vm, s.VirtualMachine);
1992                 Assert.AreEqual ("ABC", s.Value);
1993                 Assert.AreEqual (vm.RootDomain, s.Domain);
1994
1995                 // Long strings
1996                 StringBuilder sb = new StringBuilder ();
1997                 for (int i = 0; i < 1024; ++i)
1998                         sb.Append ('A');
1999                 s = vm.RootDomain.CreateString (sb.ToString ());
2000
2001                 // Argument checking
2002                 AssertThrows <ArgumentNullException> (delegate () {
2003                                 s = vm.RootDomain.CreateString (null);
2004                         });
2005         }
2006
2007         [Test]
2008         public void CreateBoxedValue () {
2009                 ObjectMirror o = vm.RootDomain.CreateBoxedValue (new PrimitiveValue (vm, 42));
2010
2011                 Assert.AreEqual ("Int32", o.Type.Name);
2012                 //AssertValue (42, m.GetValue (o.Type.GetField ("m_value")));
2013
2014                 // Argument checking
2015                 AssertThrows <ArgumentNullException> (delegate () {
2016                                 vm.RootDomain.CreateBoxedValue (null);
2017                         });
2018
2019                 AssertThrows <ArgumentException> (delegate () {
2020                                 vm.RootDomain.CreateBoxedValue (o);
2021                         });
2022         }
2023
2024         [Test]
2025         public void Invoke () {
2026                 Event e = run_until ("invoke1");
2027
2028                 StackFrame frame = e.Thread.GetFrames () [0];
2029
2030                 TypeMirror t = frame.Method.DeclaringType;
2031                 ObjectMirror this_obj = (ObjectMirror)frame.GetThis ();
2032
2033                 TypeMirror t2 = frame.Method.GetParameters ()[0].ParameterType;
2034
2035                 MethodMirror m;
2036                 Value v;
2037
2038                 // return void
2039                 m = t.GetMethod ("invoke_return_void");
2040                 v = this_obj.InvokeMethod (e.Thread, m, null);
2041                 Assert.IsNull (v);
2042
2043                 // return ref
2044                 m = t.GetMethod ("invoke_return_ref");
2045                 v = this_obj.InvokeMethod (e.Thread, m, null);
2046                 AssertValue ("ABC", v);
2047
2048                 // return null
2049                 m = t.GetMethod ("invoke_return_null");
2050                 v = this_obj.InvokeMethod (e.Thread, m, null);
2051                 AssertValue (null, v);
2052
2053                 // return primitive
2054                 m = t.GetMethod ("invoke_return_primitive");
2055                 v = this_obj.InvokeMethod (e.Thread, m, null);
2056                 AssertValue (42, v);
2057
2058                 // return nullable
2059                 m = t.GetMethod ("invoke_return_nullable");
2060                 v = this_obj.InvokeMethod (e.Thread, m, null);
2061                 Assert.IsInstanceOfType (typeof (StructMirror), v);
2062                 var s = v as StructMirror;
2063                 AssertValue (42, s.Fields [0]);
2064                 AssertValue (true, s.Fields [1]);
2065
2066                 // pass nullable as this
2067                 //m = vm.RootDomain.Corlib.GetType ("System.Object").GetMethod ("ToString");
2068                 m = s.Type.GetMethod ("ToString");
2069                 v = s.InvokeMethod (e.Thread, m, null);
2070
2071                 // return nullable null
2072                 m = t.GetMethod ("invoke_return_nullable_null");
2073                 v = this_obj.InvokeMethod (e.Thread, m, null);
2074                 Assert.IsInstanceOfType (typeof (StructMirror), v);
2075                 s = v as StructMirror;
2076                 AssertValue (0, s.Fields [0]);
2077                 AssertValue (false, s.Fields [1]);
2078
2079                 // pass nullable as this
2080                 //m = vm.RootDomain.Corlib.GetType ("System.Object").GetMethod ("ToString");
2081                 m = s.Type.GetMethod ("ToString");
2082                 v = s.InvokeMethod (e.Thread, m, null);
2083
2084                 // pass primitive
2085                 m = t.GetMethod ("invoke_pass_primitive");
2086                 Value[] args = new Value [] {
2087                         vm.CreateValue ((byte)Byte.MaxValue),
2088                         vm.CreateValue ((sbyte)SByte.MaxValue),
2089                         vm.CreateValue ((short)1),
2090                         vm.CreateValue ((ushort)1),
2091                         vm.CreateValue ((int)1),
2092                         vm.CreateValue ((uint)1),
2093                         vm.CreateValue ((long)1),
2094                         vm.CreateValue ((ulong)1),
2095                         vm.CreateValue ('A'),
2096                         vm.CreateValue (true),
2097                         vm.CreateValue (3.14f),
2098                         vm.CreateValue (3.14) };
2099
2100                 v = this_obj.InvokeMethod (e.Thread, m, args);
2101                 AssertValue ((int)Byte.MaxValue + (int)SByte.MaxValue + 1 + 1 + 1 + 1 + 1 + 1 + 'A' + 1 + 3 + 3, v);
2102
2103                 // pass ref
2104                 m = t.GetMethod ("invoke_pass_ref");
2105                 v = this_obj.InvokeMethod (e.Thread, m, new Value [] { vm.RootDomain.CreateString ("ABC") });
2106                 AssertValue ("ABC", v);
2107
2108                 // pass null
2109                 m = t.GetMethod ("invoke_pass_ref");
2110                 v = this_obj.InvokeMethod (e.Thread, m, new Value [] { vm.CreateValue (null) });
2111                 AssertValue (null, v);
2112
2113                 // static
2114                 m = t.GetMethod ("invoke_static_pass_ref");
2115                 v = t.InvokeMethod (e.Thread, m, new Value [] { vm.RootDomain.CreateString ("ABC") });
2116                 AssertValue ("ABC", v);
2117
2118                 // static invoked using ObjectMirror.InvokeMethod
2119                 m = t.GetMethod ("invoke_static_pass_ref");
2120                 v = this_obj.InvokeMethod (e.Thread, m, new Value [] { vm.RootDomain.CreateString ("ABC") });
2121                 AssertValue ("ABC", v);
2122
2123                 // method which throws an exception
2124                 try {
2125                         m = t.GetMethod ("invoke_throws");
2126                         v = this_obj.InvokeMethod (e.Thread, m, null);
2127                         Assert.Fail ();
2128                 } catch (InvocationException ex) {
2129                         Assert.AreEqual ("Exception", ex.Exception.Type.Name);
2130                 }
2131
2132 #if NET_4_5
2133                 // out argument
2134                 m = t.GetMethod ("invoke_out");
2135                 var out_task = this_obj.InvokeMethodAsyncWithResult (e.Thread, m, new Value [] { vm.CreateValue (1), vm.CreateValue (null) }, InvokeOptions.ReturnOutArgs);
2136                 var out_args = out_task.Result.OutArgs;
2137                 AssertValue (5, out_args [0]);
2138                 Assert.IsTrue (out_args [1] is ArrayMirror);
2139                 Assert.AreEqual (10, (out_args [1] as ArrayMirror).Length);
2140
2141                 // without ReturnOutArgs flag
2142                 out_task = this_obj.InvokeMethodAsyncWithResult (e.Thread, m, new Value [] { vm.CreateValue (1), vm.CreateValue (null) });
2143                 out_args = out_task.Result.OutArgs;
2144                 Assert.IsNull (out_args);
2145 #endif
2146
2147                 // newobj
2148                 m = t.GetMethod (".ctor");
2149                 v = t.InvokeMethod (e.Thread, m, null);
2150                 Assert.IsInstanceOfType (typeof (ObjectMirror), v);
2151                 Assert.AreEqual ("Tests", (v as ObjectMirror).Type.Name);
2152
2153                 // interface method
2154                 var cl1 = frame.Method.DeclaringType.Assembly.GetType ("ITest2");
2155                 m = cl1.GetMethod ("invoke_iface");
2156                 v = this_obj.InvokeMethod (e.Thread, m, null);
2157                 AssertValue (42, v);
2158
2159                 // virtual call
2160                 m = t.BaseType.GetMethod ("virtual_method");
2161                 v = this_obj.InvokeMethod (e.Thread, m, null, InvokeOptions.Virtual);
2162                 AssertValue ("V2", v);
2163
2164                 // virtual call on static method
2165                 m = t.GetMethod ("invoke_static_pass_ref");
2166                 v = t.InvokeMethod (e.Thread, m, new Value [] { vm.RootDomain.CreateString ("ABC") }, InvokeOptions.Virtual);
2167                 AssertValue ("ABC", v);
2168
2169 #if NET_4_5
2170                 // instance
2171                 m = t.GetMethod ("invoke_pass_ref");
2172                 var task = this_obj.InvokeMethodAsync (e.Thread, m, new Value [] { vm.RootDomain.CreateString ("ABC") });
2173                 AssertValue ("ABC", task.Result);
2174
2175                 // static
2176                 m = t.GetMethod ("invoke_static_pass_ref");
2177                 task = t.InvokeMethodAsync (e.Thread, m, new Value [] { vm.RootDomain.CreateString ("ABC") });
2178                 AssertValue ("ABC", task.Result);
2179 #endif
2180
2181                 // Argument checking
2182                 
2183                 // null thread
2184                 AssertThrows<ArgumentNullException> (delegate {
2185                                 m = t.GetMethod ("invoke_pass_ref");
2186                                 v = this_obj.InvokeMethod (null, m, new Value [] { vm.CreateValue (null) });                            
2187                         });
2188
2189                 // null method
2190                 AssertThrows<ArgumentNullException> (delegate {
2191                                 v = this_obj.InvokeMethod (e.Thread, null, new Value [] { vm.CreateValue (null) });                             
2192                         });
2193
2194                 // invalid number of arguments
2195                 m = t.GetMethod ("invoke_pass_ref");
2196                 AssertThrows<ArgumentException> (delegate {
2197                                 v = this_obj.InvokeMethod (e.Thread, m, null);
2198                         });
2199
2200                 // invalid type of argument (ref != primitive)
2201                 m = t.GetMethod ("invoke_pass_ref");
2202                 AssertThrows<ArgumentException> (delegate {
2203                                 v = this_obj.InvokeMethod (e.Thread, m, new Value [] { vm.CreateValue (1) });
2204                         });
2205
2206                 // invalid type of argument (primitive != primitive)
2207                 m = t.GetMethod ("invoke_pass_primitive_2");
2208                 AssertThrows<ArgumentException> (delegate {
2209                                 v = this_obj.InvokeMethod (e.Thread, m, new Value [] { vm.CreateValue (1) });
2210                         });
2211
2212                 // invoking a non-static method as static
2213                 m = t.GetMethod ("invoke_pass_ref");
2214                 AssertThrows<ArgumentException> (delegate {
2215                                 v = t.InvokeMethod (e.Thread, m, new Value [] { vm.RootDomain.CreateString ("ABC") });
2216                         });
2217
2218                 // invoking a method defined in another class
2219                 m = t2.GetMethod ("invoke");
2220                 AssertThrows<ArgumentException> (delegate {
2221                                 v = this_obj.InvokeMethod (e.Thread, m, null);
2222                         });
2223         }
2224
2225         [Test]
2226         public void InvokeVType () {
2227                 Event e = run_until ("invoke1");
2228
2229                 StackFrame frame = e.Thread.GetFrames () [0];
2230
2231                 var s = frame.GetArgument (1) as StructMirror;
2232
2233                 TypeMirror t = s.Type;
2234
2235                 MethodMirror m;
2236                 Value v;
2237
2238                 // Pass struct as this, receive int
2239                 m = t.GetMethod ("invoke_return_int");
2240                 v = s.InvokeMethod (e.Thread, m, null);
2241                 AssertValue (42, v);
2242
2243                 // Pass struct as this, receive intptr
2244                 m = t.GetMethod ("invoke_return_intptr");
2245                 v = s.InvokeMethod (e.Thread, m, null);
2246                 AssertValue (43, v);
2247
2248                 // Static method
2249                 m = t.GetMethod ("invoke_static");
2250                 v = t.InvokeMethod (e.Thread, m, null);
2251                 AssertValue (5, v);
2252
2253                 // Pass generic struct as this
2254                 s = frame.GetArgument (2) as StructMirror;
2255                 t = s.Type;
2256                 m = t.GetMethod ("invoke_return_int");
2257                 v = s.InvokeMethod (e.Thread, m, null);
2258                 AssertValue (42, v);
2259
2260 #if NET_4_5
2261                 // Invoke a method which changes state
2262                 s = frame.GetArgument (1) as StructMirror;
2263                 t = s.Type;
2264                 m = t.GetMethod ("invoke_mutate");
2265                 var task = s.InvokeMethodAsyncWithResult (e.Thread, m, null, InvokeOptions.ReturnOutThis);
2266                 var out_this = task.Result.OutThis as StructMirror;
2267                 AssertValue (5, out_this ["l"]);
2268
2269                 // Without the ReturnOutThis flag
2270                 s = frame.GetArgument (1) as StructMirror;
2271                 t = s.Type;
2272                 m = t.GetMethod ("invoke_mutate");
2273                 task = s.InvokeMethodAsyncWithResult (e.Thread, m, null);
2274                 out_this = task.Result.OutThis as StructMirror;
2275                 Assert.AreEqual (null, out_this);
2276
2277                 // interface method
2278                 var cl1 = frame.Method.DeclaringType.Assembly.GetType ("ITest2");
2279                 m = cl1.GetMethod ("invoke_iface");
2280                 v = s.InvokeMethod (e.Thread, m, null);
2281                 AssertValue (42, v);
2282
2283                 // virtual method
2284                 m = vm.RootDomain.Corlib.GetType ("System.Object").GetMethod ("ToString");
2285                 v = s.InvokeMethod (e.Thread, m, null, InvokeOptions.Virtual);
2286                 AssertValue ("42", v);
2287 #endif
2288         }
2289
2290         [Test]
2291         public void BreakpointDuringInvoke () {
2292                 Event e = run_until ("invoke1");
2293
2294                 MethodMirror m = entry_point.DeclaringType.GetMethod ("invoke2");
2295                 Assert.IsNotNull (m);
2296                 vm.SetBreakpoint (m, 0);
2297
2298                 StackFrame frame = e.Thread.GetFrames () [0];
2299                 var o = frame.GetThis () as ObjectMirror;
2300
2301                 bool failed = false;
2302
2303                 bool finished = false;
2304                 object wait = new object ();
2305
2306                 // Have to invoke in a separate thread as the invoke is suspended until we
2307                 // resume after the breakpoint
2308                 Thread t = new Thread (delegate () {
2309                                 try {
2310                                         o.InvokeMethod (e.Thread, m, null);
2311                                 } catch {
2312                                         failed = true;
2313                                 }
2314                                 lock (wait) {
2315                                         finished = true;
2316                                         Monitor.Pulse (wait);
2317                                 }
2318                         });
2319
2320                 t.Start ();
2321
2322                 StackFrame invoke_frame = null;
2323
2324                 try {
2325                         e = GetNextEvent ();
2326                         Assert.IsInstanceOfType (typeof (BreakpointEvent), e);
2327                         // Check stack trace support and invokes
2328                         var frames = e.Thread.GetFrames ();
2329                         invoke_frame = frames [0];
2330                         Assert.AreEqual ("invoke2", frames [0].Method.Name);
2331                         Assert.IsTrue (frames [0].IsDebuggerInvoke);
2332                         Assert.AreEqual ("invoke1", frames [1].Method.Name);
2333                 } finally {
2334                         vm.Resume ();
2335                 }
2336
2337                 lock (wait) {
2338                         if (!finished)
2339                                 Monitor.Wait (wait);
2340                 }
2341
2342                 // Check that the invoke frames are no longer valid
2343                 AssertThrows<InvalidStackFrameException> (delegate {
2344                                 invoke_frame.GetThis ();
2345                         });
2346
2347                 // Check InvokeOptions.DisableBreakpoints flag
2348                 o.InvokeMethod (e.Thread, m, null, InvokeOptions.DisableBreakpoints);
2349         }
2350
2351         [Test]
2352         public void DisabledExceptionDuringInvoke () {
2353                 Event e = run_until ("invoke_ex");
2354
2355                 MethodMirror m = entry_point.DeclaringType.GetMethod ("invoke_ex_inner");
2356
2357                 StackFrame frame = e.Thread.GetFrames () [0];
2358                 var o = frame.GetThis () as ObjectMirror;
2359
2360                 var req = vm.CreateExceptionRequest (null);
2361                 req.Enable ();
2362
2363                 // Check InvokeOptions.DisableBreakpoints flag
2364                 o.InvokeMethod (e.Thread, m, null, InvokeOptions.DisableBreakpoints);
2365
2366                 req.Disable ();
2367         }
2368
2369         [Test]
2370         public void InvokeSingleThreaded () {
2371                 vm.Detach ();
2372
2373                 Start (new string [] { "dtest-app.exe", "invoke-single-threaded" });
2374
2375                 Event e = run_until ("invoke_single_threaded_2");
2376
2377                 StackFrame f = e.Thread.GetFrames ()[0];
2378
2379                 var obj = f.GetThis () as ObjectMirror;
2380
2381                 // Check that the counter value incremented by the other thread does not increase
2382                 // during the invoke.
2383                 object counter1 = (obj.GetValue (obj.Type.GetField ("counter")) as PrimitiveValue).Value;
2384
2385                 var m = obj.Type.GetMethod ("invoke_return_void");
2386                 obj.InvokeMethod (e.Thread, m, null, InvokeOptions.SingleThreaded);
2387
2388             object counter2 = (obj.GetValue (obj.Type.GetField ("counter")) as PrimitiveValue).Value;
2389
2390                 Assert.AreEqual ((int)counter1, (int)counter2);
2391
2392                 // Test multiple invokes done in succession
2393                 m = obj.Type.GetMethod ("invoke_return_void");
2394                 obj.InvokeMethod (e.Thread, m, null, InvokeOptions.SingleThreaded);
2395
2396                 // Test events during single-threaded invokes
2397                 vm.EnableEvents (EventType.TypeLoad);
2398                 m = obj.Type.GetMethod ("invoke_type_load");
2399                 obj.BeginInvokeMethod (e.Thread, m, null, InvokeOptions.SingleThreaded, delegate {
2400                                 vm.Resume ();
2401                         }, null);
2402
2403                 e = GetNextEvent ();
2404                 Assert.AreEqual (EventType.TypeLoad, e.EventType);
2405         }
2406
2407         List<Value> invoke_results;
2408
2409         [Test]
2410         public void InvokeMultiple () {
2411                 Event e = run_until ("invoke1");
2412
2413                 StackFrame frame = e.Thread.GetFrames () [0];
2414
2415                 TypeMirror t = frame.Method.DeclaringType;
2416                 ObjectMirror this_obj = (ObjectMirror)frame.GetThis ();
2417
2418                 TypeMirror t2 = frame.Method.GetParameters ()[0].ParameterType;
2419
2420                 var methods = new MethodMirror [2];
2421                 methods [0] = t.GetMethod ("invoke_return_ref");
2422                 methods [1] = t.GetMethod ("invoke_return_primitive");
2423
2424                 invoke_results = new List<Value> ();
2425
2426                 var r = this_obj.BeginInvokeMultiple (e.Thread, methods, null, InvokeOptions.SingleThreaded, invoke_multiple_cb, this_obj);
2427                 WaitHandle.WaitAll (new WaitHandle[] { r.AsyncWaitHandle });
2428                 this_obj.EndInvokeMultiple (r);
2429                 // The callback might still be running
2430                 while (invoke_results.Count < 2) {
2431                         Thread.Sleep (100);
2432                 }
2433                 if (invoke_results [0] is PrimitiveValue) {
2434                         AssertValue ("ABC", invoke_results [1]);
2435                         AssertValue (42, invoke_results [0]);
2436                 } else {
2437                         AssertValue ("ABC", invoke_results [0]);
2438                         AssertValue (42, invoke_results [1]);
2439                 }
2440         }
2441
2442         void invoke_multiple_cb (IAsyncResult ar) {
2443                 ObjectMirror this_obj = (ObjectMirror)ar.AsyncState;
2444
2445                 var res = this_obj.EndInvokeMethod (ar);
2446                 lock (invoke_results)
2447                         invoke_results.Add (res);
2448         }
2449
2450         [Test]
2451         public void GetThreads () {
2452                 vm.GetThreads ();
2453         }
2454
2455         [Test]
2456         public void Threads () {
2457                 Event e = run_until ("threads");
2458
2459                 Assert.AreEqual (ThreadState.Running, e.Thread.ThreadState);
2460
2461                 Assert.IsTrue (e.Thread.ThreadId > 0);
2462
2463                 Assert.AreEqual (e.Thread.TID, e.Thread.TID);
2464
2465                 vm.EnableEvents (EventType.ThreadStart, EventType.ThreadDeath);
2466
2467                 vm.Resume ();
2468
2469                 e = GetNextEvent ();
2470                 Assert.IsInstanceOfType (typeof (ThreadStartEvent), e);
2471                 var state = e.Thread.ThreadState;
2472                 Assert.IsTrue (state == ThreadState.Running || state == ThreadState.Unstarted);
2473
2474                 vm.Resume ();
2475
2476                 e = GetNextEvent ();
2477                 Assert.IsInstanceOfType (typeof (ThreadDeathEvent), e);
2478                 Assert.AreEqual (ThreadState.Stopped, e.Thread.ThreadState);
2479         }
2480
2481         [Test]
2482         public void Frame_SetValue () {
2483                 Event e = run_until ("locals2");
2484
2485                 StackFrame frame = e.Thread.GetFrames () [0];
2486
2487                 // primitive
2488                 var l = frame.Method.GetLocal ("i");
2489                 frame.SetValue (l, vm.CreateValue ((long)55));
2490                 AssertValue (55, frame.GetValue (l));
2491
2492                 // reference
2493                 l = frame.Method.GetLocal ("s");
2494                 frame.SetValue (l, vm.RootDomain.CreateString ("DEF"));
2495                 AssertValue ("DEF", frame.GetValue (l));
2496
2497                 // argument as local
2498                 l = frame.Method.GetLocal ("arg");
2499                 frame.SetValue (l, vm.CreateValue (6));
2500                 AssertValue (6, frame.GetValue (l));
2501
2502                 // argument
2503                 var p = frame.Method.GetParameters ()[1];
2504                 frame.SetValue (p, vm.CreateValue (7));
2505                 AssertValue (7, frame.GetValue (p));
2506
2507                 // gshared
2508                 p = frame.Method.GetParameters ()[2];
2509                 frame.SetValue (p, vm.RootDomain.CreateString ("DEF"));
2510                 AssertValue ("DEF", frame.GetValue (p));
2511
2512                 // byref
2513                 p = frame.Method.GetParameters ()[3];
2514                 frame.SetValue (p, vm.RootDomain.CreateString ("DEF2"));
2515                 AssertValue ("DEF2", frame.GetValue (p));
2516
2517                 // byref struct
2518                 p = frame.Method.GetParameters ()[4];
2519                 var v = frame.GetValue (p) as StructMirror;
2520                 v ["i"] = vm.CreateValue (43);
2521                 frame.SetValue (p, v);
2522                 v = frame.GetValue (p) as StructMirror;
2523                 AssertValue (43, v ["i"]);
2524
2525                 // argument checking
2526
2527                 // variable null
2528                 AssertThrows<ArgumentNullException> (delegate () {
2529                                 frame.SetValue ((LocalVariable)null, vm.CreateValue (55));
2530                         });
2531
2532                 // value null
2533                 AssertThrows<ArgumentNullException> (delegate () {
2534                                 l = frame.Method.GetLocal ("i");
2535                                 frame.SetValue (l, null);
2536                         });
2537
2538                 // value of invalid type
2539                 AssertThrows<ArgumentException> (delegate () {
2540                                 l = frame.Method.GetLocal ("i");
2541                                 frame.SetValue (l, vm.CreateValue (55));
2542                         });
2543         }
2544
2545         [Test]
2546         [Category ("only")]
2547         public void Frame_SetValue_Registers () {
2548                 Event e = run_until ("locals6_1");
2549
2550                 StackFrame frame = e.Thread.GetFrames () [1];
2551
2552                 // Set 'j' to 99
2553                 var l = frame.Method.GetLocal ("j");
2554                 frame.SetValue (l, vm.CreateValue (99));
2555                 AssertValue (99, frame.GetValue (l));
2556
2557                 // Check it during execution
2558                 e = run_until ("locals6_2");
2559                 frame = e.Thread.GetFrames () [0];
2560                 AssertValue (99, frame.GetValue (frame.Method.GetParameters ()[0]));
2561
2562                 // Set it while in a frame which clobbers its register
2563                 e = run_until ("locals6_3");
2564                 frame = e.Thread.GetFrames () [1];
2565                 frame.SetValue (l, vm.CreateValue (100));
2566                 AssertValue (100, frame.GetValue (l));
2567
2568                 // Check it during execution
2569                 e = run_until ("locals6_4");
2570                 frame = e.Thread.GetFrames () [0];
2571                 AssertValue (100, frame.GetValue (frame.Method.GetParameters ()[0]));
2572
2573                 // Signed byte value
2574                 e = run_until ("locals6_5");
2575                 frame = e.Thread.GetFrames () [1];
2576                 var l2 = frame.Method.GetLocal ("sb");
2577                 frame.SetValue (l2, vm.CreateValue ((sbyte)-99));
2578                 AssertValue (-99, frame.GetValue (l2));
2579
2580                 // Check it during execution
2581                 e = run_until ("locals6_6");
2582                 frame = e.Thread.GetFrames () [0];
2583                 AssertValue (-99, frame.GetValue (frame.Method.GetParameters ()[0]));
2584         }
2585
2586         [Test]
2587         public void InvokeRegress () {
2588                 Event e = run_until ("invoke1");
2589
2590                 StackFrame frame = e.Thread.GetFrames () [0];
2591
2592                 TypeMirror t = frame.Method.DeclaringType;
2593                 ObjectMirror this_obj = (ObjectMirror)frame.GetThis ();
2594
2595                 TypeMirror t2 = frame.Method.GetParameters ()[0].ParameterType;
2596
2597                 MethodMirror m;
2598                 Value v;
2599
2600                 // do an invoke
2601                 m = t.GetMethod ("invoke_return_void");
2602                 v = this_obj.InvokeMethod (e.Thread, m, null);
2603                 Assert.IsNull (v);
2604
2605                 // Check that the stack frames remain valid during the invoke
2606                 Assert.AreEqual ("Tests", (frame.GetThis () as ObjectMirror).Type.Name);
2607
2608                 // do another invoke
2609                 m = t.GetMethod ("invoke_return_void");
2610                 v = this_obj.InvokeMethod (e.Thread, m, null);
2611                 Assert.IsNull (v);
2612
2613                 // Try a single step after the invoke
2614                 var req = create_step (e);
2615                 req.Depth = StepDepth.Into;
2616                 req.Size = StepSize.Line;
2617                 req.Enable ();
2618
2619                 // Skip nop
2620                 step_once ();
2621
2622                 // Step into invoke2
2623                 vm.Resume ();
2624                 e = GetNextEvent ();
2625                 Assert.IsTrue (e is StepEvent);
2626                 Assert.AreEqual ("invoke2", (e as StepEvent).Method.Name);
2627
2628                 req.Disable ();
2629
2630                 frame = e.Thread.GetFrames () [0];
2631         }
2632
2633         [Test]
2634         public void Exceptions () {
2635                 Event e = run_until ("exceptions");
2636                 var req = vm.CreateExceptionRequest (null);
2637                 req.Enable ();
2638
2639                 vm.Resume ();
2640
2641                 e = GetNextEvent ();
2642                 Assert.IsInstanceOfType (typeof (ExceptionEvent), e);
2643                 Assert.AreEqual ("OverflowException", (e as ExceptionEvent).Exception.Type.Name);
2644
2645                 var frames = e.Thread.GetFrames ();
2646                 Assert.AreEqual ("exceptions", frames [0].Method.Name);
2647                 req.Disable ();
2648
2649                 // exception type filter
2650
2651                 req = vm.CreateExceptionRequest (vm.RootDomain.Corlib.GetType ("System.ArgumentException"));
2652                 req.Enable ();
2653
2654                 // Skip the throwing of the second OverflowException       
2655                 vm.Resume ();
2656
2657                 e = GetNextEvent ();
2658                 Assert.IsInstanceOfType (typeof (ExceptionEvent), e);
2659                 Assert.AreEqual ("ArgumentException", (e as ExceptionEvent).Exception.Type.Name);
2660                 req.Disable ();
2661
2662                 // exception type filter for subclasses
2663                 req = vm.CreateExceptionRequest (vm.RootDomain.Corlib.GetType ("System.Exception"));
2664                 req.Enable ();
2665
2666                 vm.Resume ();
2667
2668                 e = GetNextEvent ();
2669                 Assert.IsInstanceOfType (typeof (ExceptionEvent), e);
2670                 Assert.AreEqual ("OverflowException", (e as ExceptionEvent).Exception.Type.Name);
2671                 req.Disable ();
2672
2673                 // no subclasses
2674                 req.IncludeSubclasses = false;
2675                 req.Enable ();
2676
2677                 vm.Resume ();
2678
2679                 e = GetNextEvent ();
2680                 Assert.IsInstanceOfType (typeof (ExceptionEvent), e);
2681                 Assert.AreEqual ("Exception", (e as ExceptionEvent).Exception.Type.Name);
2682                 req.Disable ();
2683
2684                 // Implicit exceptions
2685                 req = vm.CreateExceptionRequest (null);
2686                 req.Enable ();
2687
2688                 vm.Resume ();
2689
2690                 e = GetNextEvent ();
2691                 Assert.IsInstanceOfType (typeof (ExceptionEvent), e);
2692                 Assert.AreEqual ("NullReferenceException", (e as ExceptionEvent).Exception.Type.Name);
2693                 req.Disable ();
2694
2695                 // Single stepping after an exception
2696                 req = vm.CreateExceptionRequest (null);
2697                 req.Enable ();
2698
2699                 vm.Resume ();
2700
2701                 e = GetNextEvent ();
2702                 Assert.IsInstanceOfType (typeof (ExceptionEvent), e);
2703                 Assert.AreEqual ("Exception", (e as ExceptionEvent).Exception.Type.Name);
2704                 frames = e.Thread.GetFrames ();
2705                 Assert.AreEqual ("exceptions2", frames [0].Method.Name);
2706                 req.Disable ();
2707
2708                 var sreq = create_step (e);
2709                 sreq.Depth = StepDepth.Over;
2710                 sreq.Size = StepSize.Line;
2711                 sreq.Enable ();
2712
2713                 vm.Resume ();
2714                 e = GetNextEvent ();
2715                 Assert.IsInstanceOfType (typeof (StepEvent), e);
2716                 frames = e.Thread.GetFrames ();
2717                 Assert.AreEqual ("exceptions", frames [0].Method.Name);
2718                 sreq.Disable ();
2719
2720                 // Argument checking
2721                 AssertThrows<ArgumentException> (delegate {
2722                                 vm.CreateExceptionRequest (e.Thread.Type);
2723                         });
2724         }
2725
2726         [Test]
2727         public void ExceptionFilter () {
2728                 Event e = run_until ("exception_filter");
2729
2730                 MethodMirror m = entry_point.DeclaringType.GetMethod ("exception_filter_filter");
2731                 Assert.IsNotNull (m);
2732
2733                 vm.SetBreakpoint (m, 0);
2734
2735                 vm.Resume ();
2736
2737                 e = GetNextEvent ();
2738                 Assert.AreEqual (EventType.Breakpoint, e.EventType);
2739                 Assert.IsTrue (e is BreakpointEvent);
2740                 Assert.AreEqual (m.Name, (e as BreakpointEvent).Method.Name);
2741
2742                 var frames = e.Thread.GetFrames ();
2743
2744                 Assert.IsTrue (frames [0].Location.SourceFile.IndexOf ("dtest-app.cs") != -1);
2745                 Assert.AreEqual ("exception_filter_filter", frames [0].Location.Method.Name);
2746
2747                 Assert.AreEqual (0, frames [1].Location.Method.MetadataToken);
2748                 Assert.AreEqual (0x0f, frames [1].Location.ILOffset);
2749
2750                 Assert.AreEqual ("exception_filter_method", frames [2].Location.Method.Name);
2751                 Assert.AreEqual (0x06, frames [2].Location.ILOffset);
2752
2753                 Assert.AreEqual (0, frames [3].Location.Method.MetadataToken, 0);
2754                 Assert.AreEqual (0, frames [3].Location.ILOffset);
2755
2756                 Assert.AreEqual ("exception_filter", frames [4].Location.Method.Name);
2757         }
2758
2759         [Test]
2760         public void ExceptionFilter2 () {
2761                 vm.Detach ();
2762
2763                 Start (new string [] { "dtest-excfilter.exe" });
2764
2765                 MethodMirror filter_method = entry_point.DeclaringType.GetMethod ("Filter");
2766                 Assert.IsNotNull (filter_method);
2767
2768                 MethodMirror test_method = entry_point.DeclaringType.GetMethod ("Test");
2769                 Assert.IsNotNull (test_method);
2770
2771                 vm.SetBreakpoint (filter_method, 0);
2772
2773                 vm.Resume ();
2774
2775                 var e = GetNextEvent ();
2776                 Assert.AreEqual (EventType.Breakpoint, e.EventType);
2777                 Assert.IsTrue (e is BreakpointEvent);
2778                 Assert.AreEqual (filter_method.Name, (e as BreakpointEvent).Method.Name);
2779
2780                 var frames = e.Thread.GetFrames ();
2781
2782                 Assert.AreEqual (4, frames.Count ());
2783
2784                 Assert.AreEqual (filter_method.Name, frames [0].Location.Method.Name);
2785                 Assert.AreEqual (20, frames [0].Location.LineNumber);
2786                 Assert.AreEqual (0, frames [0].Location.ILOffset);
2787
2788                 Assert.AreEqual (test_method.Name, frames [1].Location.Method.Name);
2789                 Assert.AreEqual (37, frames [1].Location.LineNumber);
2790                 Assert.AreEqual (0x0b, frames [1].Location.ILOffset);
2791
2792                 Assert.AreEqual (test_method.Name, frames [2].Location.Method.Name);
2793                 Assert.AreEqual (33, frames [2].Location.LineNumber);
2794                 Assert.AreEqual (0x05, frames [2].Location.ILOffset);
2795
2796                 Assert.AreEqual (entry_point.Name, frames [3].Location.Method.Name);
2797                 Assert.AreEqual (14, frames [3].Location.LineNumber);
2798                 Assert.AreEqual (0x00, frames [3].Location.ILOffset);
2799
2800                 vm.Exit (0);
2801
2802                 vm = null;
2803         }
2804
2805         [Test]
2806         public void EventSets () {
2807                 //
2808                 // Create two filter which both match the same exception
2809                 //
2810                 Event e = run_until ("exceptions");
2811
2812                 var req = vm.CreateExceptionRequest (null);
2813                 req.Enable ();
2814
2815                 var req2 = vm.CreateExceptionRequest (vm.RootDomain.Corlib.GetType ("System.OverflowException"));
2816                 req2.Enable ();
2817
2818                 vm.Resume ();
2819
2820                 var es = vm.GetNextEventSet ();
2821                 Assert.AreEqual (2, es.Events.Length);
2822
2823                 e = es [0];
2824                 Assert.IsInstanceOfType (typeof (ExceptionEvent), e);
2825                 Assert.AreEqual ("OverflowException", (e as ExceptionEvent).Exception.Type.Name);
2826
2827                 e = es [1];
2828                 Assert.IsInstanceOfType (typeof (ExceptionEvent), e);
2829                 Assert.AreEqual ("OverflowException", (e as ExceptionEvent).Exception.Type.Name);
2830
2831                 req.Disable ();
2832                 req2.Disable ();
2833         }
2834
2835         //
2836         // Test single threaded invokes during processing of nullref exceptions.
2837         // These won't work if the exception handling is done from the sigsegv signal
2838         // handler, since the sigsegv signal is disabled until control returns from the
2839         // signal handler.
2840         //
2841         [Test]
2842         [Category ("only3")]
2843         public void NullRefExceptionAndSingleThreadedInvoke () {
2844                 Event e = run_until ("exceptions");
2845                 var req = vm.CreateExceptionRequest (vm.RootDomain.Corlib.GetType ("System.NullReferenceException"));
2846                 req.Enable ();
2847
2848                 vm.Resume ();
2849
2850                 e = GetNextEvent ();
2851                 Assert.IsInstanceOfType (typeof (ExceptionEvent), e);
2852                 Assert.AreEqual ("NullReferenceException", (e as ExceptionEvent).Exception.Type.Name);
2853
2854                 var ex = (e as ExceptionEvent).Exception;
2855                 var tostring_method = vm.RootDomain.Corlib.GetType ("System.Object").GetMethod ("ToString");
2856                 ex.InvokeMethod (e.Thread, tostring_method, null, InvokeOptions.SingleThreaded);
2857         }
2858
2859         [Test]
2860         public void Domains () {
2861                 vm.Detach ();
2862
2863                 Start (new string [] { "dtest-app.exe", "domain-test" });
2864
2865                 vm.EnableEvents (EventType.AppDomainCreate, EventType.AppDomainUnload, EventType.AssemblyUnload);
2866
2867                 Event e = run_until ("domains");
2868
2869                 vm.Resume ();
2870                 
2871                 e = GetNextEvent ();
2872                 Assert.IsInstanceOfType (typeof (AppDomainCreateEvent), e);
2873
2874                 var domain = (e as AppDomainCreateEvent).Domain;
2875
2876                 // Check the object type
2877                 e = run_until ("domains_2");
2878                 var frame = e.Thread.GetFrames ()[0];
2879                 var o = frame.GetArgument (0) as ObjectMirror;
2880                 Assert.AreEqual ("CrossDomain", o.Type.Name);
2881
2882                 // Do a remoting invoke
2883                 var cross_domain_type = o.Type;
2884                 var v = o.InvokeMethod (e.Thread, cross_domain_type.GetMethod ("invoke_3"), null);
2885                 AssertValue (42, v);
2886
2887                 // Run until the callback in the domain
2888                 MethodMirror m = entry_point.DeclaringType.GetMethod ("invoke_in_domain");
2889                 Assert.IsNotNull (m);
2890                 vm.SetBreakpoint (m, 0);
2891
2892                 while (true) {
2893                         vm.Resume ();
2894                         e = GetNextEvent ();
2895                         if (e is BreakpointEvent)
2896                                 break;
2897                 }
2898
2899                 Assert.AreEqual ("invoke_in_domain", (e as BreakpointEvent).Method.Name);
2900
2901                 // d_method is from another domain
2902                 MethodMirror d_method = (e as BreakpointEvent).Method;
2903                 Assert.IsTrue (m != d_method);
2904
2905                 var frames = e.Thread.GetFrames ();
2906                 Assert.AreEqual ("invoke_in_domain", frames [0].Method.Name);
2907                 Assert.AreEqual (domain, frames [0].Domain);
2908                 Assert.AreEqual ("invoke", frames [1].Method.Name);
2909                 Assert.AreEqual ("domains", frames [2].Method.Name);
2910                 Assert.AreEqual (vm.RootDomain, frames [2].Domain);
2911
2912                 // Test breakpoints on already JITted methods in other domains
2913                 m = entry_point.DeclaringType.GetMethod ("invoke_in_domain_2");
2914                 Assert.IsNotNull (m);
2915                 vm.SetBreakpoint (m, 0);
2916
2917                 while (true) {
2918                         vm.Resume ();
2919                         e = GetNextEvent ();
2920                         if (e is BreakpointEvent)
2921                                 break;
2922                 }
2923
2924                 Assert.AreEqual ("invoke_in_domain_2", (e as BreakpointEvent).Method.Name);
2925
2926                 // This is empty when receiving the AppDomainCreateEvent
2927                 Assert.AreEqual ("domain", domain.FriendlyName);
2928
2929                 // Run until the unload
2930                 while (true) {
2931                         vm.Resume ();
2932                         e = GetNextEvent ();
2933                         if (e is AssemblyUnloadEvent) {
2934                                 continue;
2935                         } else {
2936                                 break;
2937                         }
2938                 }
2939                 Assert.IsInstanceOfType (typeof (AppDomainUnloadEvent), e);
2940                 Assert.AreEqual (domain, (e as AppDomainUnloadEvent).Domain);
2941
2942                 // Run past the unload
2943                 e = run_until ("domains_3");
2944
2945                 // Test access to unloaded types
2946                 // FIXME: Add an exception type for this
2947                 AssertThrows<Exception> (delegate {
2948                                 d_method.DeclaringType.GetValue (d_method.DeclaringType.GetField ("static_i"));
2949                         });
2950
2951                 // Check that .Domain is accessible for stack frames with native transitions
2952                 e = run_until ("called_from_invoke");
2953                 ThreadMirror.NativeTransitions = true;
2954                 foreach (var f in e.Thread.GetFrames ()) {
2955                         var dom = f.Domain;
2956                 }
2957         }
2958
2959         [Test]
2960         public void DynamicMethods () {
2961                 Event e = run_until ("dyn_call");
2962
2963                 var m = e.Thread.GetFrames ()[1].Method;
2964                 Assert.AreEqual ("dyn_method", m.Name);
2965
2966                 // Test access to IL
2967                 var body = m.GetMethodBody ();
2968
2969                 ILInstruction ins = body.Instructions [0];
2970                 Assert.AreEqual (OpCodes.Ldstr, ins.OpCode);
2971                 Assert.AreEqual ("FOO", ins.Operand);
2972         }
2973
2974         [Test]
2975         public void RefEmit () {
2976                 vm.Detach ();
2977
2978                 Start (new string [] { "dtest-app.exe", "ref-emit-test" });
2979
2980                 Event e = run_until ("ref_emit_call");
2981
2982                 var m = e.Thread.GetFrames ()[1].Method;
2983                 Assert.AreEqual ("ref_emit_method", m.Name);
2984
2985                 // Test access to IL
2986                 var body = m.GetMethodBody ();
2987
2988                 ILInstruction ins;
2989
2990                 ins = body.Instructions [0];
2991                 Assert.AreEqual (OpCodes.Ldstr, ins.OpCode);
2992                 Assert.AreEqual ("FOO", ins.Operand);
2993
2994                 ins = body.Instructions [1];
2995                 Assert.AreEqual (OpCodes.Call, ins.OpCode);
2996                 Assert.IsInstanceOfType (typeof (MethodMirror), ins.Operand);
2997                 Assert.AreEqual ("ref_emit_call", (ins.Operand as MethodMirror).Name);
2998         }
2999
3000         [Test]
3001         public void IsAttached () {
3002                 var f = entry_point.DeclaringType.GetField ("is_attached");
3003
3004                 Event e = run_until ("Main");
3005
3006                 AssertValue (true, entry_point.DeclaringType.GetValue (f));
3007         }
3008
3009         [Test]
3010         public void StackTraceInNative () {
3011                 // Check that stack traces can be produced for threads in native code
3012                 vm.Detach ();
3013
3014                 Start (new string [] { "dtest-app.exe", "frames-in-native" });
3015
3016                 var e = run_until ("frames_in_native");
3017
3018                 // FIXME: This is racy
3019                 vm.Resume ();
3020
3021                 Thread.Sleep (100);
3022
3023                 vm.Suspend ();
3024
3025                 StackFrame[] frames = e.Thread.GetFrames ();
3026
3027                 int frame_index = -1;
3028                 for (int i = 0; i < frames.Length; ++i) {
3029                         if (frames [i].Method.Name == "Sleep") {
3030                                 frame_index = i;
3031                                 break;
3032                         }
3033                 }
3034
3035                 Assert.IsTrue (frame_index != -1);
3036                 Assert.AreEqual ("Sleep", frames [frame_index].Method.Name);
3037                 Assert.AreEqual ("frames_in_native", frames [frame_index + 1].Method.Name);
3038                 Assert.AreEqual ("Main", frames [frame_index + 2].Method.Name);
3039
3040                 // Check that invokes are disabled for such threads
3041                 TypeMirror t = frames [frame_index + 1].Method.DeclaringType;
3042
3043                 var m = t.GetMethod ("invoke_static_return_void");
3044                 AssertThrows<InvalidOperationException> (delegate {
3045                                 t.InvokeMethod (e.Thread, m, null);
3046                         });
3047
3048                 // Check that the frame info is invalidated
3049                 run_until ("frames_in_native_2");
3050
3051                 AssertThrows<InvalidStackFrameException> (delegate {
3052                                 Console.WriteLine (frames [frame_index].GetThis ());
3053                         });
3054         }
3055
3056         [Test]
3057         public void VirtualMachine_CreateEnumMirror () {
3058                 var e = run_until ("o1");
3059                 var frame = e.Thread.GetFrames () [0];
3060
3061                 object val = frame.GetThis ();
3062                 Assert.IsTrue (val is ObjectMirror);
3063                 Assert.AreEqual ("Tests", (val as ObjectMirror).Type.Name);
3064                 ObjectMirror o = (val as ObjectMirror);
3065
3066                 FieldInfoMirror field = o.Type.GetField ("field_enum");
3067                 Value f = o.GetValue (field);
3068                 TypeMirror enumType = (f as EnumMirror).Type;
3069
3070                 o.SetValue (field, vm.CreateEnumMirror (enumType, vm.CreateValue (1)));
3071                 f = o.GetValue (field);
3072                 Assert.AreEqual (1, (f as EnumMirror).Value);
3073
3074                 // Argument checking
3075                 AssertThrows<ArgumentNullException> (delegate () {
3076                                 vm.CreateEnumMirror (enumType, null);
3077                         });
3078
3079                 AssertThrows<ArgumentNullException> (delegate () {
3080                                 vm.CreateEnumMirror (null, vm.CreateValue (1));
3081                         });
3082
3083                 // null value
3084                 AssertThrows<ArgumentException> (delegate () {
3085                                 vm.CreateEnumMirror (enumType, vm.CreateValue (null));
3086                         });
3087
3088                 // value of a wrong type
3089                 AssertThrows<ArgumentException> (delegate () {
3090                                 vm.CreateEnumMirror (enumType, vm.CreateValue ((long)1));
3091                         });
3092         }
3093
3094         [Test]
3095         public void VirtualMachine_EnableEvents_Breakpoint () {
3096                 AssertThrows<ArgumentException> (delegate () {
3097                                 vm.EnableEvents (EventType.Breakpoint);
3098                         });
3099         }
3100
3101         [Test]
3102         public void SingleStepRegress654694 () {
3103                 int il_offset = -1;
3104
3105                 MethodMirror m = entry_point.DeclaringType.GetMethod ("ss_regress_654694");
3106                 foreach (Location l in m.Locations) {
3107                         if (l.ILOffset > 0 && il_offset == -1)
3108                                 il_offset = l.ILOffset;
3109                 }
3110
3111                 Event e = run_until ("ss_regress_654694");
3112
3113                 Assert.IsNotNull (m);
3114                 vm.SetBreakpoint (m, il_offset);
3115
3116                 vm.Resume ();
3117
3118                 e = GetNextEvent ();
3119                 Assert.IsTrue (e is BreakpointEvent);
3120
3121                 var req = create_step (e);
3122                 req.Depth = StepDepth.Over;
3123                 req.Size = StepSize.Line;
3124                 req.Enable ();
3125
3126                 vm.Resume ();
3127
3128                 e = GetNextEvent ();
3129                 Assert.IsTrue (e is StepEvent);
3130
3131                 req.Disable ();
3132         }
3133
3134         [Test]
3135         public void DebugBreak () {
3136                 vm.EnableEvents (EventType.UserBreak);
3137
3138                 run_until ("user");
3139
3140                 vm.Resume ();
3141                 var e = GetNextEvent ();
3142                 Assert.IsTrue (e is UserBreakEvent);
3143         }
3144
3145         [Test]
3146         public void DebugLog () {
3147                 vm.EnableEvents (EventType.UserLog);
3148
3149                 run_until ("user");
3150
3151                 vm.Resume ();
3152                 var e = GetNextEvent ();
3153                 Assert.IsTrue (e is UserLogEvent);
3154                 var le = e as UserLogEvent;
3155
3156                 Assert.AreEqual (5, le.Level);
3157                 Assert.AreEqual ("A", le.Category);
3158                 Assert.AreEqual ("B", le.Message);
3159         }
3160
3161         [Test]
3162         public void TypeGetMethodsByNameFlags () {
3163                 MethodMirror[] mm;
3164                 var assembly = entry_point.DeclaringType.Assembly;
3165                 var type = assembly.GetType ("Tests3");
3166
3167                 Assert.IsNotNull (type);
3168
3169                 mm = type.GetMethodsByNameFlags (null, BindingFlags.Static | BindingFlags.Public, false);
3170                 Assert.AreEqual (1, mm.Length, "#1");
3171                 Assert.AreEqual ("M1", mm[0].Name, "#2");
3172
3173                 mm = type.GetMethodsByNameFlags (null, BindingFlags.Static | BindingFlags.NonPublic, false);
3174                 Assert.AreEqual (1, mm.Length, "#3");
3175                 Assert.AreEqual ("M2", mm[0].Name, "#4");
3176
3177                 mm = type.GetMethodsByNameFlags (null, BindingFlags.Instance | BindingFlags.Public, false);
3178                 Assert.AreEqual (7, mm.Length, "#5"); //M3 plus Equals, GetHashCode, GetType, ToString, .ctor
3179
3180                 mm = type.GetMethodsByNameFlags (null, BindingFlags.Instance | BindingFlags.Public | BindingFlags.DeclaredOnly, false);
3181                 Assert.AreEqual (2, mm.Length, "#7");
3182
3183                 mm = type.GetMethodsByNameFlags (null, BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.DeclaredOnly, false);
3184                 Assert.AreEqual (1, mm.Length, "#9");
3185
3186                 mm = type.GetMethodsByNameFlags (null, BindingFlags.Static | BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.DeclaredOnly, false);
3187                 Assert.AreEqual (5, mm.Length, "#11");
3188
3189                 //Now with name
3190                 mm = type.GetMethodsByNameFlags ("M1", BindingFlags.Static | BindingFlags.Public, false);
3191                 Assert.AreEqual (1, mm.Length, "#12");
3192                 Assert.AreEqual ("M1", mm[0].Name, "#13");
3193
3194                 mm = type.GetMethodsByNameFlags ("m1", BindingFlags.Static | BindingFlags.Public, true);
3195                 Assert.AreEqual (1, mm.Length, "#14");
3196                 Assert.AreEqual ("M1", mm[0].Name, "#15");
3197
3198                 mm = type.GetMethodsByNameFlags ("M1", BindingFlags.Static  | BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, false);
3199                 Assert.AreEqual (1, mm.Length, "#16");
3200                 Assert.AreEqual ("M1", mm[0].Name, "#17");
3201         }
3202
3203         [Test]
3204         [Category ("only88")]
3205         public void TypeLoadSourceFileFilter () {
3206                 Event e = run_until ("type_load");
3207
3208                 if (!vm.Version.AtLeast (2, 7))
3209                         return;
3210
3211                 string srcfile = (e as BreakpointEvent).Method.DeclaringType.GetSourceFiles (true)[0];
3212
3213                 var req = vm.CreateTypeLoadRequest ();
3214                 req.SourceFileFilter = new string [] { srcfile.ToUpper () };
3215                 req.Enable ();
3216
3217                 vm.Resume ();
3218                 e = GetNextEvent ();
3219                 Assert.IsTrue (e is TypeLoadEvent);
3220                 Assert.AreEqual ("TypeLoadClass", (e as TypeLoadEvent).Type.FullName);
3221         }
3222
3223         [Test]
3224         public void TypeLoadTypeNameFilter () {
3225                 Event e = run_until ("type_load");
3226
3227                 var req = vm.CreateTypeLoadRequest ();
3228                 req.TypeNameFilter = new string [] { "TypeLoadClass2" };
3229                 req.Enable ();
3230
3231                 vm.Resume ();
3232                 e = GetNextEvent ();
3233                 Assert.IsTrue (e is TypeLoadEvent);
3234                 Assert.AreEqual ("TypeLoadClass2", (e as TypeLoadEvent).Type.FullName);
3235         }
3236
3237         [Test]
3238         public void GetTypesForSourceFile () {
3239                 run_until ("user");
3240
3241                 var types = vm.GetTypesForSourceFile ("dtest-app.cs", false);
3242                 Assert.IsTrue (types.Any (t => t.FullName == "Tests"));
3243                 Assert.IsFalse (types.Any (t => t.FullName == "System.Int32"));
3244
3245                 types = vm.GetTypesForSourceFile ("DTEST-app.cs", true);
3246                 Assert.IsTrue (types.Any (t => t.FullName == "Tests"));
3247                 Assert.IsFalse (types.Any (t => t.FullName == "System.Int32"));
3248         }
3249
3250         [Test]
3251         public void GetTypesNamed () {
3252                 run_until ("user");
3253
3254                 var types = vm.GetTypes ("Tests", false);
3255                 Assert.AreEqual (1, types.Count);
3256                 Assert.AreEqual ("Tests", types [0].FullName);
3257
3258                 types = vm.GetTypes ("System.Exception", false);
3259                 Assert.AreEqual (1, types.Count);
3260                 Assert.AreEqual ("System.Exception", types [0].FullName);
3261         }
3262
3263         [Test]
3264         public void String_GetChars () {
3265                 object val;
3266
3267                 // Reuse this test
3268                 var e = run_until ("arg2");
3269
3270                 var frame = e.Thread.GetFrames () [0];
3271
3272                 val = frame.GetArgument (0);
3273                 Assert.IsTrue (val is StringMirror);
3274                 AssertValue ("FOO", val);
3275                 var s = (val as StringMirror);
3276                 Assert.AreEqual (3, s.Length);
3277
3278                 var c = s.GetChars (0, 2);
3279                 Assert.AreEqual (2, c.Length);
3280                 Assert.AreEqual ('F', c [0]);
3281                 Assert.AreEqual ('O', c [1]);
3282
3283                 AssertThrows<ArgumentException> (delegate () {          
3284                                 s.GetChars (2, 2);
3285                         });
3286         }
3287
3288         [Test]
3289         public void GetInterfaces () {
3290                 var e = run_until ("arg2");
3291
3292                 var frame = e.Thread.GetFrames () [0];
3293
3294                 var cl1 = frame.Method.DeclaringType.Assembly.GetType ("TestIfaces");
3295                 var ifaces = cl1.GetInterfaces ();
3296                 Assert.AreEqual (1, ifaces.Length);
3297                 Assert.AreEqual ("ITest", ifaces [0].Name);
3298
3299                 var cl2 = cl1.GetMethod ("Baz").ReturnType;
3300                 var ifaces2 = cl2.GetInterfaces ();
3301                 Assert.AreEqual (1, ifaces2.Length);
3302                 Assert.AreEqual ("ITest`1", ifaces2 [0].Name);
3303         }
3304
3305         [Test]
3306         public void GetInterfaceMap () {
3307                 var e = run_until ("arg2");
3308
3309                 var frame = e.Thread.GetFrames () [0];
3310
3311                 var cl1 = frame.Method.DeclaringType.Assembly.GetType ("TestIfaces");
3312                 var iface = cl1.Assembly.GetType ("ITest");
3313                 var map = cl1.GetInterfaceMap (iface);
3314                 Assert.AreEqual (cl1, map.TargetType);
3315                 Assert.AreEqual (iface, map.InterfaceType);
3316                 Assert.AreEqual (2, map.InterfaceMethods.Length);
3317                 Assert.AreEqual (2, map.TargetMethods.Length);
3318         }
3319
3320         [Test]
3321         public void StackAlloc_Breakpoints_Regress2775 () {
3322                 // Check that breakpoints on arm don't overwrite stackalloc-ed memory
3323                 var e = run_until ("regress_2755");
3324
3325                 var frame = e.Thread.GetFrames () [0];
3326                 var m = e.Method;
3327                 // This breaks at the call site
3328                 vm.SetBreakpoint (m, m.Locations [2].ILOffset);
3329
3330                 vm.Resume ();
3331                 var e2 = GetNextEvent ();
3332                 Assert.IsTrue (e2 is BreakpointEvent);
3333
3334                 e = run_until ("regress_2755_3");
3335                 frame = e.Thread.GetFrames () [1];
3336                 var res = frame.GetValue (m.GetLocal ("sum"));
3337                 AssertValue (0, res);
3338         }
3339
3340         [Test]
3341         public void MethodInfo () {
3342                 Event e = run_until ("locals2");
3343
3344                 StackFrame frame = e.Thread.GetFrames () [0];
3345                 var m = frame.Method;
3346
3347                 Assert.IsTrue (m.IsGenericMethod);
3348                 Assert.IsFalse (m.IsGenericMethodDefinition);
3349
3350                 var args = m.GetGenericArguments ();
3351                 Assert.AreEqual (1, args.Length);
3352                 Assert.AreEqual ("String", args [0].Name);
3353
3354                 var gmd = m.GetGenericMethodDefinition ();
3355                 Assert.IsTrue (gmd.IsGenericMethod);
3356                 Assert.IsTrue (gmd.IsGenericMethodDefinition);
3357                 Assert.AreEqual (gmd, gmd.GetGenericMethodDefinition ());
3358
3359                 args = gmd.GetGenericArguments ();
3360                 Assert.AreEqual (1, args.Length);
3361                 Assert.AreEqual ("T", args [0].Name);
3362
3363                 var attrs = m.GetCustomAttributes (true);
3364                 Assert.AreEqual (1, attrs.Length);
3365                 Assert.AreEqual ("StateMachineAttribute", attrs [0].Constructor.DeclaringType.Name);
3366         }
3367
3368         [Test]
3369         public void UnhandledException () {
3370                 vm.Exit (0);
3371
3372                 Start (new string [] { "dtest-app.exe", "unhandled-exception" });
3373
3374                 var req = vm.CreateExceptionRequest (null, false, true);
3375                 req.Enable ();
3376
3377                 var e = run_until ("unhandled_exception");
3378                 vm.Resume ();
3379
3380                 var e2 = GetNextEvent ();
3381                 Assert.IsTrue (e2 is ExceptionEvent);
3382
3383                 vm.Exit (0);
3384                 vm = null;
3385         }
3386
3387         [Test]
3388         public void UnhandledException_2 () {
3389                 vm.Exit (0);
3390
3391                 Start (new string [] { "dtest-app.exe", "unhandled-exception-endinvoke" });
3392
3393                 var req = vm.CreateExceptionRequest (null, false, true);
3394                 req.Enable ();
3395
3396                 MethodMirror m = entry_point.DeclaringType.GetMethod ("unhandled_exception_endinvoke_2");
3397                 Assert.IsNotNull (m);
3398                 vm.SetBreakpoint (m, m.ILOffsets [0]);
3399
3400                 var e = run_until ("unhandled_exception_endinvoke");
3401                 vm.Resume ();
3402
3403                 var e2 = GetNextEvent ();
3404                 Assert.IsFalse (e2 is ExceptionEvent);
3405
3406                 vm.Exit (0);
3407                 vm = null;
3408         }
3409
3410 #if NET_4_5
3411         [Test]
3412         public void UnhandledExceptionUserCode () {
3413                 vm.Detach ();
3414
3415                 // Exceptions caught in non-user code are treated as unhandled
3416                 Start (new string [] { "dtest-app.exe", "unhandled-exception-user" });
3417
3418                 var req = vm.CreateExceptionRequest (null, false, true);
3419                 req.AssemblyFilter = new List<AssemblyMirror> () { entry_point.DeclaringType.Assembly };
3420                 req.Enable ();
3421
3422                 var e = run_until ("unhandled_exception_user");
3423                 vm.Resume ();
3424
3425                 var e2 = GetNextEvent ();
3426                 Assert.IsTrue (e2 is ExceptionEvent);
3427
3428                 vm.Exit (0);
3429                 vm = null;
3430         }
3431 #endif
3432
3433         [Test]
3434         public void GCWhileSuspended () {
3435                 // Check that objects are kept alive during suspensions
3436                 Event e = run_until ("gc_suspend_1");
3437
3438                 MethodMirror m = entry_point.DeclaringType.GetMethod ("gc_suspend_invoke");
3439
3440                 var o = entry_point.DeclaringType.GetValue (entry_point.DeclaringType.GetField ("gc_suspend_field")) as ObjectMirror;
3441                 //Console.WriteLine (o);
3442
3443                 StackFrame frame = e.Thread.GetFrames () [0];
3444                 TypeMirror t = frame.Method.DeclaringType;
3445                 for (int i = 0; i < 10; ++i)
3446                         t.InvokeMethod (e.Thread, m, new Value [] { });
3447
3448                 // This throws an exception if the object is collected
3449                 long addr = o.Address;
3450
3451                 var o2 = entry_point.DeclaringType.GetValue (entry_point.DeclaringType.GetField ("gc_suspend_field")) as ObjectMirror;
3452                 Assert.IsNull (o2);
3453         }
3454
3455         [Test]
3456         public void MakeGenericMethod () {
3457                 Event e = run_until ("bp1");
3458
3459                 var intm = vm.RootDomain.GetCorrespondingType (typeof (int));
3460                 var stringm = vm.RootDomain.GetCorrespondingType (typeof (string));
3461                 var gm = entry_point.DeclaringType.GetMethod ("generic_method");
3462                 var res = gm.MakeGenericMethod (new TypeMirror [] { stringm });
3463                 var args = res.GetGenericArguments ();
3464                 Assert.AreEqual (1, args.Length);
3465                 Assert.AreEqual (stringm, args [0]);
3466
3467                 // Error checking
3468                 AssertThrows<ArgumentNullException> (delegate {
3469                                 gm.MakeGenericMethod (null);
3470                         });
3471                 AssertThrows<ArgumentNullException> (delegate {
3472                                 gm.MakeGenericMethod (new TypeMirror [] { null });
3473                         });
3474                 AssertThrows<ArgumentException> (delegate {
3475                                 gm.MakeGenericMethod (new TypeMirror [] { stringm, stringm });
3476                         });
3477                 AssertThrows<InvalidOperationException> (delegate {
3478                                 gm.MakeGenericMethod (new TypeMirror [] { intm });
3479                         });
3480                 AssertThrows<InvalidOperationException> (delegate {
3481                                 entry_point.DeclaringType.GetMethod ("Main").MakeGenericMethod (new TypeMirror [] { intm });
3482                         });
3483         }
3484
3485         [Test]
3486         public void InspectThreadSuspenedOnWaitOne () {
3487                 TearDown ();
3488                 Start (true, "dtest-app.exe", "wait-one" );
3489
3490                 ThreadMirror.NativeTransitions = true;
3491
3492                 var evt = run_until ("wait_one");
3493                 Assert.IsNotNull (evt, "#1");
3494
3495                 var thread = evt.Thread;
3496                 Assert.AreEqual (ThreadState.Running, thread.ThreadState, "#1.1");
3497
3498                 var frames = thread.GetFrames ();
3499                 Assert.IsNotNull (frames, "#2");
3500                 Assert.AreEqual (2, frames.Length, "#3");
3501                 Assert.AreEqual ("wait_one", frames [0].Method.Name, "#4");
3502                 Assert.AreEqual ("Main", frames [1].Method.Name, "#5");
3503
3504                 vm.Resume ();
3505
3506                 Thread.Sleep (500); //FIXME this is racy, maybe single step? or something?
3507
3508                 vm.Suspend ();
3509                 Assert.AreEqual (ThreadState.WaitSleepJoin, thread.ThreadState, "#6");
3510
3511                 frames = thread.GetFrames ();
3512                 Assert.AreEqual (4, frames.Length, "#7");
3513                 Assert.AreEqual ("WaitOne_internal", frames [0].Method.Name, "#8");
3514                 Assert.AreEqual ("WaitOne", frames [1].Method.Name, "#8.1");
3515                 Assert.AreEqual ("wait_one", frames [2].Method.Name, "#9");
3516                 Assert.AreEqual ("Main", frames [3].Method.Name, "#10");
3517
3518
3519                 var frame = frames [0];
3520                 Assert.IsTrue (frame.IsNativeTransition, "#11.1");
3521                 try {
3522                         frame.GetThis ();
3523                         Assert.Fail ("Known limitation - can't get info from m2n frames");
3524                 } catch (AbsentInformationException) {}
3525
3526                 frame = frames [1];
3527                 Assert.IsFalse (frame.IsNativeTransition, "#12.1");
3528                 var wait_one_this = frame.GetThis ();
3529                 Assert.IsNotNull (wait_one_this, "#12.2");
3530
3531                 frame = frames [2];
3532                 var locals = frame.GetVisibleVariables ();
3533                 Assert.AreEqual (1, locals.Count, "#13.1");
3534
3535                 var local_0 = frame.GetValue (locals [0]);
3536                 Assert.IsNotNull (local_0, "#13.2");
3537
3538                 Assert.AreEqual (wait_one_this, local_0, "#14.2");
3539         }
3540
3541         [Test]
3542         public void GetMethodBody () {
3543                 var bevent = run_until ("Main");
3544
3545                 var m = bevent.Method.DeclaringType.GetMethod ("get_IntProperty");
3546                 var body = m.GetMethodBody ();
3547                 foreach (var ins in body.Instructions) {
3548                         if (ins.OpCode == OpCodes.Ldfld) {
3549                                 var field = (FieldInfoMirror)ins.Operand;
3550                                 Assert.AreEqual ("field_i", field.Name);
3551                         }
3552                 }
3553         }
3554
3555         [Test]
3556         public void EvaluateMethod () {
3557                 var bevent = run_until ("evaluate_method_2");
3558
3559                 var m = bevent.Method.DeclaringType.GetMethod ("get_IntProperty");
3560
3561                 var this_obj = bevent.Thread.GetFrames ()[0].GetThis ();
3562                 var v = m.Evaluate (this_obj, null);
3563                 AssertValue (42, v);
3564         }
3565
3566         [Test]
3567         public void SetIP () {
3568                 var bevent = run_until ("set_ip_1");
3569
3570                 var invalid_loc = bevent.Thread.GetFrames ()[0].Location;
3571
3572                 var req = create_step (bevent);
3573                 var e = step_out ();
3574                 req.Disable ();
3575                 var frames = e.Thread.GetFrames ();
3576                 var locs = frames [0].Method.Locations;
3577                 var next_loc = locs.First (l => (l.LineNumber == frames [0].Location.LineNumber + 2));
3578
3579                 e.Thread.SetIP (next_loc);
3580
3581                 /* Check that i ++; j = 5; was skipped */
3582                 bevent = run_until ("set_ip_2");
3583                 var f = bevent.Thread.GetFrames ()[1];
3584                 AssertValue (2, f.GetValue (f.Method.GetLocal ("i")));
3585                 AssertValue (0, f.GetValue (f.Method.GetLocal ("j")));
3586
3587                 // Error handling
3588                 AssertThrows<ArgumentNullException> (delegate {
3589                                 e.Thread.SetIP (null);
3590                         });
3591
3592                 AssertThrows<ArgumentException> (delegate {
3593                                 e.Thread.SetIP (invalid_loc);
3594                         });
3595         }
3596
3597         [Test]
3598         public void SetIPSingleStep () {
3599                 // Check that single stepping after set-ip steps from the new ip
3600                 var bevent = run_until ("set_ip_1");
3601
3602                 var invalid_loc = bevent.Thread.GetFrames ()[0].Location;
3603
3604                 var req = create_step (bevent);
3605                 req.Size = StepSize.Line;
3606                 var e = step_out ();
3607                 req.Disable ();
3608                 var frames = e.Thread.GetFrames ();
3609                 var locs = frames [0].Method.Locations;
3610                 var prev_loc = locs.First (l => (l.LineNumber == frames [0].Location.LineNumber - 3));
3611                 AssertValue (2, frames [0].GetValue (frames [0].Method.GetLocal ("i")));
3612
3613                 // Set back the ip to the first i ++; line
3614                 e.Thread.SetIP (prev_loc);
3615
3616                 e = step_over ();
3617                 var f = e.Thread.GetFrames ()[0];
3618                 AssertValue (3, f.GetValue (f.Method.GetLocal ("i")));
3619         }
3620
3621         [Test]
3622         public void NewInstanceNoCtor () {
3623                 var bevent = run_until ("Main");
3624
3625                 var stype = bevent.Method.DeclaringType.Assembly.GetType ("AStruct");
3626                 var obj = stype.NewInstance ();
3627                 Assert.IsTrue (obj is ObjectMirror);
3628                 Assert.AreEqual ("AStruct", (obj as ObjectMirror).Type.Name);
3629         }
3630
3631         [Test]
3632         public void StaticCtorFilterInCctor () {
3633                 // Check that single stepping when in a cctor only ignores
3634                 // other cctors, not the current one
3635                 var bevent = run_until ("step_filters");
3636
3637                 var assembly = entry_point.DeclaringType.Assembly;
3638                 var type = assembly.GetType ("Tests/ClassWithCctor");
3639                 var cctor = type.GetMethod (".cctor");
3640                 vm.SetBreakpoint (cctor, 0);
3641
3642                 vm.Resume ();
3643                 var e = vm.GetNextEvent ();
3644                 Assert.IsTrue (e is BreakpointEvent);
3645
3646                 var req = create_step (e);
3647                 req.Filter = StepFilter.StaticCtor;
3648                 e = step_into ();
3649                 // Make sure we are still in the cctor
3650                 Assert.AreEqual (".cctor", e.Thread.GetFrames ()[0].Location.Method.Name);
3651         }
3652 }
3653
3654 }