~ubuntu-branches/ubuntu/saucy/monodevelop/saucy-proposed

« back to all changes in this revision

Viewing changes to src/addins/MonoDevelop.Debugger.Soft/Mono.Debugging.Soft/SoftDebuggerAdaptor.cs

  • Committer: Package Import Robot
  • Author(s): Jo Shields, 1840cc1
  • Date: 2012-02-05 10:49:36 UTC
  • mfrom: (10.2.12)
  • Revision ID: package-import@ubuntu.com-20120205104936-f3dutq6lnseokb6d
Tags: 2.8.6.3+dfsg-1
[1840cc1] Imported Upstream version 2.8.6.3+dfsg

Show diffs side-by-side

added added

removed removed

Lines of Context:
249
249
                        return new PropertyValueReference (ctx, props[i], target, null, values);
250
250
                }
251
251
                
252
 
                bool IsCompilerGeneratedType (SoftEvaluationContext cx, TypeMirror tm)
253
 
                {
254
 
                        return tm.Name.IndexOf (">c__AnonStorey") != -1 || tm.Name.IndexOf (">c__Iterator") != -1;
255
 
                }
256
 
                
257
 
                bool InCompilerGeneratedType (EvaluationContext ctx)
 
252
                static bool InGeneratedClosureOrIteratorType (EvaluationContext ctx)
258
253
                {
259
254
                        SoftEvaluationContext cx = (SoftEvaluationContext) ctx;
260
255
                        if (cx.Frame.Method.IsStatic)
261
256
                                return false;
262
257
                        TypeMirror tm = cx.Frame.Method.DeclaringType;
263
 
                        return IsCompilerGeneratedType (cx, tm);
 
258
                        return IsGeneratedClosureOrIteratorType (tm);
 
259
                }
 
260
                
 
261
                static bool IsGeneratedClosureOrIteratorType (TypeMirror tm)
 
262
                {
 
263
                        return IsGeneratedClosureType (tm) || IsGeneratedIteratorType (tm);
 
264
                }
 
265
                
 
266
                static bool IsGeneratedClosureType (TypeMirror tm)
 
267
                {
 
268
                        return tm.Name.IndexOf (">c__") != -1;
 
269
                }
 
270
                
 
271
                static bool IsGeneratedIteratorType (TypeMirror tm)
 
272
                {
 
273
                        return
 
274
                                //mcs
 
275
                                tm.Name.IndexOf (">c__Iterator") != -1
 
276
                                //csc is of form <NAME>d__NUMBER
 
277
                                || (tm.Name.StartsWith ("<") && tm.Name.IndexOf (">d__") > -1);
 
278
                }
 
279
                
 
280
                static bool IsHoistedThisReference (FieldInfoMirror field)
 
281
                {
 
282
                        // mcs is "<>f__this"
 
283
                        // csc is "<>4__this"
 
284
                        return field.Name.StartsWith ("<>") && field.Name.EndsWith ("__this");
 
285
                }
 
286
                
 
287
                static bool IsClosureReferenceField (FieldInfoMirror field)
 
288
                {
 
289
                        // mcs is "<>f__ref"
 
290
                        // csc is "CS$<>"
 
291
                        return field.Name.StartsWith ("CS$<>") || field.Name.StartsWith ("<>f__ref");
 
292
                }
 
293
                
 
294
                static bool IsClosureReferenceLocal (LocalVariable local)
 
295
                {
 
296
                        if (local.Name == null)
 
297
                                return false;
 
298
                        
 
299
                        return
 
300
                                // mcs
 
301
                                local.Name.Length == 0 || local.Name.StartsWith ("<") || local.Name.StartsWith ("$locvar")
 
302
                                // csc
 
303
                                || local.Name.StartsWith ("CS$<>");
 
304
                }
 
305
                
 
306
                static bool IsGeneratedTemporaryLocal (LocalVariable local)
 
307
                {
 
308
                        return local.Name != null && local.Name.StartsWith ("CS$");
 
309
                }
 
310
                
 
311
                static string GetHoistedIteratorLocalName (FieldInfoMirror field)
 
312
                {
 
313
                        //mcs captured args, of form <$>name
 
314
                        if (field.Name.StartsWith ("<$>")) {
 
315
                                return field.Name.Substring (3);
 
316
                        }
 
317
                        
 
318
                        // csc, mcs locals of form <name>__0
 
319
                        if (field.Name.StartsWith ("<")) {
 
320
                                int i = field.Name.IndexOf ('>');
 
321
                                if (i > 1) {
 
322
                                        return field.Name.Substring (1, i - 1);
 
323
                                }
 
324
                        }
 
325
                        return null;
264
326
                }
265
327
 
266
 
                IEnumerable<ValueReference> GetCompilerGeneratedLocalVariables (SoftEvaluationContext cx, ValueReference vthis)
 
328
                IEnumerable<ValueReference> GetHoistedLocalVariables (SoftEvaluationContext cx, ValueReference vthis)
267
329
                {
268
330
                        if (vthis == null)
269
331
                                return new ValueReference [0];
273
335
                                return new ValueReference [0];
274
336
                        
275
337
                        TypeMirror tm = (TypeMirror) vthis.Type;
276
 
                        bool isIterator = tm.Name.IndexOf (">c__Iterator") != -1;
 
338
                        bool isIterator = IsGeneratedIteratorType (tm);
277
339
                        
278
340
                        var list = new List<ValueReference> ();
279
341
                        TypeMirror type = (TypeMirror) vthis.Type;
280
342
                        foreach (FieldInfoMirror field in type.GetFields ()) {
281
 
                                if (field.Name == "<>f__this")
 
343
                                if (IsHoistedThisReference (field))
282
344
                                        continue;
283
 
                                if (field.Name.StartsWith ("<>f__ref")) {
284
 
                                        list.AddRange (GetCompilerGeneratedLocalVariables (cx, new FieldValueReference (cx, field, val, type)));
 
345
                                if (IsClosureReferenceField (field)) {
 
346
                                        list.AddRange (GetHoistedLocalVariables (cx, new FieldValueReference (cx, field, val, type)));
285
347
                                        continue;
286
348
                                }
287
349
                                if (field.Name.StartsWith ("<")) {
288
350
                                        if (isIterator) {
289
 
                                                int i = field.Name.IndexOf ('>');
290
 
                                                if (i > 1) {
291
 
                                                        string vname = field.Name.Substring (1, i - 1);
292
 
                                                        list.Add (new FieldValueReference (cx, field, val, type, vname, ObjectValueFlags.Variable));
 
351
                                                var name = GetHoistedIteratorLocalName (field);
 
352
                                                if (!string.IsNullOrEmpty (name)) {
 
353
                                                        list.Add (new FieldValueReference (cx, field, val, type, name, ObjectValueFlags.Variable));
293
354
                                                }
294
355
                                        }
295
 
                                }
296
 
                                else
 
356
                                } else if (!field.Name.Contains ("$")) {
297
357
                                        list.Add (new FieldValueReference (cx, field, val, type, field.Name, ObjectValueFlags.Variable));
 
358
                                }
298
359
                        }
299
360
                        return list;
300
361
                }
301
362
                
302
 
                ValueReference GetCompilerGeneratedThisReference (SoftEvaluationContext cx)
 
363
                ValueReference GetHoistedThisReference (SoftEvaluationContext cx)
303
364
                {
304
365
                        try {
305
366
                                Value val = cx.Frame.GetThis ();
306
367
                                TypeMirror type = (TypeMirror) GetValueType (cx, val);
307
 
                                FieldInfoMirror field = type.GetField ("<>f__this");
308
 
                                if (field != null)
 
368
                                return GetHoistedThisReference (cx, type, val);
 
369
                        } catch (AbsentInformationException) {
 
370
                        }
 
371
                        return null;
 
372
                }
 
373
                
 
374
                ValueReference GetHoistedThisReference (SoftEvaluationContext cx, TypeMirror type, object val)
 
375
                {
 
376
                        foreach (FieldInfoMirror field in type.GetFields ()) {
 
377
                                if (IsHoistedThisReference (field)) {
309
378
                                        return new FieldValueReference (cx, field, val, type, "this", ObjectValueFlags.Literal);
310
 
                        } catch (AbsentInformationException) {
 
379
                                } else if (IsClosureReferenceField (field)) {
 
380
                                        var fieldRef = new FieldValueReference (cx, field, val, type);
 
381
                                        var thisRef = GetHoistedThisReference (cx, field.FieldType, fieldRef.Value);
 
382
                                        if (thisRef != null)
 
383
                                                return thisRef;
 
384
                                }
311
385
                        }
312
386
                        return null;
313
387
                }
314
388
                
 
389
                // if the local does not have a name, constructs one from the index
 
390
                static string GetLocalName (SoftEvaluationContext cx, LocalVariable local)
 
391
                {
 
392
                        var name = local.Name;
 
393
                        if (!string.IsNullOrEmpty (local.Name) || cx.SourceCodeAvailable)
 
394
                                return name;
 
395
                        return "loc" + local.Index;
 
396
                }
 
397
                
315
398
                protected override ValueReference OnGetLocalVariable (EvaluationContext ctx, string name)
316
399
                {
317
400
                        SoftEvaluationContext cx = (SoftEvaluationContext) ctx;
318
 
                        if (InCompilerGeneratedType (cx))
 
401
                        if (InGeneratedClosureOrIteratorType (cx))
319
402
                                return FindByName (OnGetLocalVariables (cx), v => v.Name, name, ctx.CaseSensitive);
320
403
                        
321
404
                        try {
326
409
                                                if (int.TryParse (name.Substring (3), out idx))
327
410
                                                        local = cx.Frame.Method.GetLocals ().FirstOrDefault (loc => loc.Index == idx);
328
411
                                        }
329
 
                                } else
330
 
                                        local = ctx.CaseSensitive ? cx.Frame.GetVisibleVariableByName (name) : FindByName (cx.Frame.GetVisibleVariables(), v => v.Name, name, false);
331
 
                                
 
412
                                } else {
 
413
                                        local = ctx.CaseSensitive
 
414
                                                ? cx.Frame.GetVisibleVariableByName (name)
 
415
                                                : FindByName (cx.Frame.GetVisibleVariables(), v => v.Name, name, false);
 
416
                                }
332
417
                                if (local != null) {
333
 
                                        string vname = !string.IsNullOrEmpty (local.Name) || cx.SourceCodeAvailable ? local.Name : "loc" + local.Index;
334
 
                                        return new VariableValueReference (ctx, vname, local);
 
418
                                        return new VariableValueReference (ctx, GetLocalName (cx, local), local);
335
419
                                }
336
420
                                return FindByName (OnGetLocalVariables (ctx), v => v.Name, name, ctx.CaseSensitive);;
337
421
                        } catch (AbsentInformationException) {
342
426
                protected override IEnumerable<ValueReference> OnGetLocalVariables (EvaluationContext ctx)
343
427
                {
344
428
                        SoftEvaluationContext cx = (SoftEvaluationContext) ctx;
345
 
                        if (InCompilerGeneratedType (cx)) {
 
429
                        if (InGeneratedClosureOrIteratorType (cx)) {
346
430
                                ValueReference vthis = GetThisReference (cx);
347
 
                                return GetCompilerGeneratedLocalVariables (cx, vthis).Union (GetLocalVariables (cx));
 
431
                                return GetHoistedLocalVariables (cx, vthis).Union (GetLocalVariables (cx));
348
432
                        }
349
433
                        else
350
434
                                return GetLocalVariables (cx);
358
442
                        } catch (AbsentInformationException) {
359
443
                                yield break;
360
444
                        }
361
 
                        foreach (LocalVariable var in locals) {
362
 
                                if (!var.IsArg) {
363
 
                                        string name = !string.IsNullOrEmpty (var.Name) || cx.SourceCodeAvailable ? var.Name : "loc" + var.Index;
364
 
                                        if (name.Length == 0 || name.StartsWith ("<")) {
365
 
                                                if (IsCompilerGeneratedType (cx, var.Type)) {
366
 
                                                        foreach (var gv in GetCompilerGeneratedLocalVariables (cx, new VariableValueReference (cx, name, var)))
367
 
                                                                yield return gv;
368
 
                                                }
 
445
                        foreach (LocalVariable local in locals) {
 
446
                                if (local.IsArg)
 
447
                                        continue;
 
448
                                if (IsClosureReferenceLocal (local) && IsGeneratedClosureType (local.Type)) {
 
449
                                        foreach (var gv in GetHoistedLocalVariables (cx, new VariableValueReference (cx, local.Name, local))) {
 
450
                                                yield return gv;
369
451
                                        }
370
 
                                        else
371
 
                                                yield return new VariableValueReference (cx, name, var);
 
452
                                } else if (!IsGeneratedTemporaryLocal (local)) {
 
453
                                        yield return new VariableValueReference (cx, GetLocalName (cx, local), local);
372
454
                                }
373
455
                        }
374
456
                }
508
590
                protected override ValueReference OnGetThisReference (EvaluationContext ctx)
509
591
                {
510
592
                        SoftEvaluationContext cx = (SoftEvaluationContext) ctx;
511
 
                        if (InCompilerGeneratedType (cx))
512
 
                                return GetCompilerGeneratedThisReference (cx);
 
593
                        if (InGeneratedClosureOrIteratorType (cx))
 
594
                                return GetHoistedThisReference (cx);
513
595
                        else
514
596
                                return GetThisReference (cx);
515
597
                }