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