Merge pull request #2780 from alexanderkyte/seq_point_optimize
[mono.git] / mono / metadata / mono-debug.c
1 /*
2  * mono-debug.c: 
3  *
4  * Author:
5  *      Mono Project (http://www.mono-project.com)
6  *
7  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
8  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
9  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
10  * Licensed under the MIT license. See LICENSE file in the project root for full license information.
11  */
12
13 #include <config.h>
14 #include <mono/metadata/assembly.h>
15 #include <mono/metadata/tabledefs.h>
16 #include <mono/metadata/tokentype.h>
17 #include <mono/metadata/appdomain.h>
18 #include <mono/metadata/class-internals.h>
19 #include <mono/metadata/mono-debug.h>
20 #include <mono/metadata/mono-debug-debugger.h>
21 #include <mono/metadata/mono-endian.h>
22 #include <mono/metadata/gc-internals.h>
23 #include <mono/metadata/mempool.h>
24 #include <mono/metadata/debug-mono-ppdb.h>
25 #include <string.h>
26
27 #define ALIGN_TO(val,align) ((((guint64)val) + ((align) - 1)) & ~((align) - 1))
28
29 #if NO_UNALIGNED_ACCESS
30 #define WRITE_UNALIGNED(type, addr, val) \
31         memcpy(addr, &val, sizeof(type))
32 #define READ_UNALIGNED(type, addr, val) \
33         memcpy(&val, addr, sizeof(type))
34 #else
35 #define WRITE_UNALIGNED(type, addr, val) \
36         (*(type *)(addr) = (val))
37 #define READ_UNALIGNED(type, addr, val) \
38         val = (*(type *)(addr))
39 #endif
40
41 /* This contains per-domain info */
42 struct _MonoDebugDataTable {
43         MonoMemPool *mp;
44         GHashTable *method_address_hash;
45 };
46
47 /* This contains JIT debugging information about a method in serialized format */
48 struct _MonoDebugMethodAddress {
49         const guint8 *code_start;
50         guint32 code_size;
51         guint8 data [MONO_ZERO_LEN_ARRAY];
52 };
53
54 static MonoDebugFormat mono_debug_format = MONO_DEBUG_FORMAT_NONE;
55
56 static gboolean mono_debug_initialized = FALSE;
57 /* Maps MonoImage -> MonoMonoDebugHandle */
58 static GHashTable *mono_debug_handles;
59 /* Maps MonoDomain -> MonoDataTable */
60 static GHashTable *data_table_hash;
61
62 static mono_mutex_t debugger_lock_mutex;
63
64 static gboolean is_attached = FALSE;
65
66 static MonoDebugHandle     *mono_debug_open_image      (MonoImage *image, const guint8 *raw_contents, int size);
67
68 static MonoDebugHandle     *mono_debug_get_image      (MonoImage *image);
69 static void                 mono_debug_add_assembly    (MonoAssembly *assembly,
70                                                         gpointer user_data);
71
72 static MonoDebugHandle     *open_symfile_from_bundle   (MonoImage *image);
73
74 static MonoDebugDataTable *
75 create_data_table (MonoDomain *domain)
76 {
77         MonoDebugDataTable *table;
78
79         table = g_new0 (MonoDebugDataTable, 1);
80
81         table->mp = mono_mempool_new ();
82         table->method_address_hash = g_hash_table_new (NULL, NULL);
83
84         if (domain)
85                 g_hash_table_insert (data_table_hash, domain, table);
86
87         return table;
88 }
89
90 static void
91 free_data_table (MonoDebugDataTable *table)
92 {
93         mono_mempool_destroy (table->mp);
94         g_hash_table_destroy (table->method_address_hash);
95
96         g_free (table);
97 }
98
99 static MonoDebugDataTable *
100 lookup_data_table (MonoDomain *domain)
101 {
102         MonoDebugDataTable *table;
103
104         table = (MonoDebugDataTable *)g_hash_table_lookup (data_table_hash, domain);
105         if (!table) {
106                 g_error ("lookup_data_table () failed for %p\n", domain);
107                 g_assert (table);
108         }
109         return table;
110 }
111
112 static void
113 free_debug_handle (MonoDebugHandle *handle)
114 {
115         if (handle->ppdb)
116                 mono_ppdb_close (handle);
117         if (handle->symfile)
118                 mono_debug_close_mono_symbol_file (handle->symfile);
119         /* decrease the refcount added with mono_image_addref () */
120         mono_image_close (handle->image);
121         g_free (handle);
122 }
123
124 /*
125  * Initialize debugging support.
126  *
127  * This method must be called after loading corlib,
128  * but before opening the application's main assembly because we need to set some
129  * callbacks here.
130  */
131 void
132 mono_debug_init (MonoDebugFormat format)
133 {
134         g_assert (!mono_debug_initialized);
135         if (format == MONO_DEBUG_FORMAT_DEBUGGER)
136                 g_error ("The mdb debugger is no longer supported.");
137
138         mono_debug_initialized = TRUE;
139         mono_debug_format = format;
140
141         mono_os_mutex_init_recursive (&debugger_lock_mutex);
142
143         mono_debugger_lock ();
144
145         mono_debug_handles = g_hash_table_new_full
146                 (NULL, NULL, NULL, (GDestroyNotify) free_debug_handle);
147
148         data_table_hash = g_hash_table_new_full (
149                 NULL, NULL, NULL, (GDestroyNotify) free_data_table);
150
151         mono_install_assembly_load_hook (mono_debug_add_assembly, NULL);
152
153         mono_debugger_unlock ();
154 }
155
156 void
157 mono_debug_open_image_from_memory (MonoImage *image, const guint8 *raw_contents, int size)
158 {
159         if (!mono_debug_initialized)
160                 return;
161
162         mono_debug_open_image (image, raw_contents, size);
163 }
164
165 void
166 mono_debug_cleanup (void)
167 {
168         if (mono_debug_handles)
169                 g_hash_table_destroy (mono_debug_handles);
170         mono_debug_handles = NULL;
171
172         if (data_table_hash) {
173                 g_hash_table_destroy (data_table_hash);
174                 data_table_hash = NULL;
175         }
176 }
177
178 void
179 mono_debug_domain_create (MonoDomain *domain)
180 {
181         if (!mono_debug_initialized)
182                 return;
183
184         mono_debugger_lock ();
185
186         create_data_table (domain);
187
188         mono_debugger_unlock ();
189 }
190
191 void
192 mono_debug_domain_unload (MonoDomain *domain)
193 {
194         MonoDebugDataTable *table;
195
196         if (!mono_debug_initialized)
197                 return;
198
199         mono_debugger_lock ();
200
201         table = (MonoDebugDataTable *)g_hash_table_lookup (data_table_hash, domain);
202         if (!table) {
203                 g_warning (G_STRLOC ": unloading unknown domain %p / %d",
204                            domain, mono_domain_get_id (domain));
205                 mono_debugger_unlock ();
206                 return;
207         }
208
209         g_hash_table_remove (data_table_hash, domain);
210
211         mono_debugger_unlock ();
212 }
213
214 /*
215  * LOCKING: Assumes the debug lock is held.
216  */
217 static MonoDebugHandle *
218 mono_debug_get_image (MonoImage *image)
219 {
220         return (MonoDebugHandle *)g_hash_table_lookup (mono_debug_handles, image);
221 }
222
223 void
224 mono_debug_close_image (MonoImage *image)
225 {
226         MonoDebugHandle *handle;
227
228         if (!mono_debug_initialized)
229                 return;
230
231         mono_debugger_lock ();
232
233         handle = mono_debug_get_image (image);
234         if (!handle) {
235                 mono_debugger_unlock ();
236                 return;
237         }
238
239         g_hash_table_remove (mono_debug_handles, image);
240
241         mono_debugger_unlock ();
242 }
243
244 static MonoDebugHandle *
245 mono_debug_open_image (MonoImage *image, const guint8 *raw_contents, int size)
246 {
247         MonoDebugHandle *handle;
248
249         if (mono_image_is_dynamic (image))
250                 return NULL;
251
252         mono_debugger_lock ();
253
254         handle = mono_debug_get_image (image);
255         if (handle != NULL) {
256                 mono_debugger_unlock ();
257                 return handle;
258         }
259
260         handle = g_new0 (MonoDebugHandle, 1);
261
262         handle->image = image;
263         mono_image_addref (image);
264
265         /* Try a ppdb file first */
266         handle->ppdb = mono_ppdb_load_file (handle->image, raw_contents, size);
267
268         if (!handle->ppdb)
269                 handle->symfile = mono_debug_open_mono_symbols (handle, raw_contents, size, FALSE);
270
271         g_hash_table_insert (mono_debug_handles, image, handle);
272
273         mono_debugger_unlock ();
274
275         return handle;
276 }
277
278 static void
279 mono_debug_add_assembly (MonoAssembly *assembly, gpointer user_data)
280 {
281         MonoDebugHandle *handle;
282         MonoImage *image;
283
284         mono_debugger_lock ();
285         image = mono_assembly_get_image (assembly);
286         handle = open_symfile_from_bundle (image);
287         if (!handle)
288                 mono_debug_open_image (image, NULL, 0);
289         mono_debugger_unlock ();
290 }
291
292 struct LookupMethodData
293 {
294         MonoDebugMethodInfo *minfo;
295         MonoMethod *method;
296 };
297
298 static void
299 lookup_method_func (gpointer key, gpointer value, gpointer user_data)
300 {
301         MonoDebugHandle *handle = (MonoDebugHandle *) value;
302         struct LookupMethodData *data = (struct LookupMethodData *) user_data;
303
304         if (data->minfo)
305                 return;
306
307         if (handle->ppdb)
308                 data->minfo = mono_ppdb_lookup_method (handle, data->method);
309         else if (handle->symfile)
310                 data->minfo = mono_debug_symfile_lookup_method (handle, data->method);
311 }
312
313 static MonoDebugMethodInfo *
314 mono_debug_lookup_method_internal (MonoMethod *method)
315 {
316         struct LookupMethodData data;
317
318         data.minfo = NULL;
319         data.method = method;
320
321         if (!mono_debug_handles)
322                 return NULL;
323
324         g_hash_table_foreach (mono_debug_handles, lookup_method_func, &data);
325         return data.minfo;
326 }
327
328 /**
329  * mono_debug_lookup_method:
330  *
331  * Lookup symbol file information for the method @method.  The returned
332  * `MonoDebugMethodInfo' is a private structure, but it can be passed to
333  * mono_debug_symfile_lookup_location().
334  */
335 MonoDebugMethodInfo *
336 mono_debug_lookup_method (MonoMethod *method)
337 {
338         MonoDebugMethodInfo *minfo;
339
340         if (mono_debug_format == MONO_DEBUG_FORMAT_NONE)
341                 return NULL;
342
343         mono_debugger_lock ();
344         minfo = mono_debug_lookup_method_internal (method);
345         mono_debugger_unlock ();
346         return minfo;
347 }
348
349 typedef struct
350 {
351         gboolean found;
352         MonoImage *image;
353 } LookupImageData;
354
355 static void
356 lookup_image_func (gpointer key, gpointer value, gpointer user_data)
357 {
358         MonoDebugHandle *handle = (MonoDebugHandle *) value;
359         LookupImageData *data = (LookupImageData *) user_data;
360
361         if (data->found)
362                 return;
363
364         if (handle->image == data->image && handle->symfile)
365                 data->found = TRUE;
366 }
367
368 gboolean
369 mono_debug_image_has_debug_info (MonoImage *image)
370 {
371         LookupImageData data;
372
373         if (!mono_debug_handles)
374                 return FALSE;
375
376         memset (&data, 0, sizeof (data));
377         data.image = image;
378
379         mono_debugger_lock ();
380         g_hash_table_foreach (mono_debug_handles, lookup_image_func, &data);
381         mono_debugger_unlock ();
382         return data.found;
383 }
384
385 static inline void
386 write_leb128 (guint32 value, guint8 *ptr, guint8 **rptr)
387 {
388         do {
389                 guint8 byte = value & 0x7f;
390                 value >>= 7;
391                 if (value)
392                         byte |= 0x80;
393                 *ptr++ = byte;
394         } while (value);
395
396         *rptr = ptr;
397 }
398
399 static inline void
400 write_sleb128 (gint32 value, guint8 *ptr, guint8 **rptr)
401 {
402         gboolean more = 1;
403
404         while (more) {
405                 guint8 byte = value & 0x7f;
406                 value >>= 7;
407
408                 if (((value == 0) && ((byte & 0x40) == 0)) || ((value == -1) && (byte & 0x40)))
409                         more = 0;
410                 else
411                         byte |= 0x80;
412                 *ptr++ = byte;
413         }
414
415         *rptr = ptr;
416 }
417
418 static void
419 write_variable (MonoDebugVarInfo *var, guint8 *ptr, guint8 **rptr)
420 {
421         write_leb128 (var->index, ptr, &ptr);
422         write_sleb128 (var->offset, ptr, &ptr);
423         write_leb128 (var->size, ptr, &ptr);
424         write_leb128 (var->begin_scope, ptr, &ptr);
425         write_leb128 (var->end_scope, ptr, &ptr);
426         WRITE_UNALIGNED (gpointer, ptr, var->type);
427         ptr += sizeof (gpointer);
428         *rptr = ptr;
429 }
430
431 MonoDebugMethodAddress *
432 mono_debug_add_method (MonoMethod *method, MonoDebugMethodJitInfo *jit, MonoDomain *domain)
433 {
434         MonoDebugDataTable *table;
435         MonoDebugMethodAddress *address;
436         guint8 buffer [BUFSIZ];
437         guint8 *ptr, *oldptr;
438         guint32 i, size, total_size, max_size;
439
440         mono_debugger_lock ();
441
442         table = lookup_data_table (domain);
443
444         max_size = (5 * 5) + 1 + (10 * jit->num_line_numbers) +
445                 (25 + sizeof (gpointer)) * (1 + jit->num_params + jit->num_locals);
446
447         if (max_size > BUFSIZ)
448                 ptr = oldptr = (guint8 *)g_malloc (max_size);
449         else
450                 ptr = oldptr = buffer;
451
452         write_leb128 (jit->prologue_end, ptr, &ptr);
453         write_leb128 (jit->epilogue_begin, ptr, &ptr);
454
455         write_leb128 (jit->num_line_numbers, ptr, &ptr);
456         for (i = 0; i < jit->num_line_numbers; i++) {
457                 MonoDebugLineNumberEntry *lne = &jit->line_numbers [i];
458
459                 write_sleb128 (lne->il_offset, ptr, &ptr);
460                 write_sleb128 (lne->native_offset, ptr, &ptr);
461         }
462         write_leb128 (jit->has_var_info, ptr, &ptr);
463         if (jit->has_var_info) {
464                 *ptr++ = jit->this_var ? 1 : 0;
465                 if (jit->this_var)
466                         write_variable (jit->this_var, ptr, &ptr);
467
468                 write_leb128 (jit->num_params, ptr, &ptr);
469                 for (i = 0; i < jit->num_params; i++)
470                         write_variable (&jit->params [i], ptr, &ptr);
471
472                 write_leb128 (jit->num_locals, ptr, &ptr);
473                 for (i = 0; i < jit->num_locals; i++)
474                         write_variable (&jit->locals [i], ptr, &ptr);
475
476                 *ptr++ = jit->gsharedvt_info_var ? 1 : 0;
477                 if (jit->gsharedvt_info_var) {
478                         write_variable (jit->gsharedvt_info_var, ptr, &ptr);
479                         write_variable (jit->gsharedvt_locals_var, ptr, &ptr);
480                 }
481         }
482
483         size = ptr - oldptr;
484         g_assert (size < max_size);
485         total_size = size + sizeof (MonoDebugMethodAddress);
486
487         if (method_is_dynamic (method)) {
488                 address = (MonoDebugMethodAddress *)g_malloc0 (total_size);
489         } else {
490                 address = (MonoDebugMethodAddress *)mono_mempool_alloc (table->mp, total_size);
491         }
492
493         address->code_start = jit->code_start;
494         address->code_size = jit->code_size;
495
496         memcpy (&address->data, oldptr, size);
497         if (max_size > BUFSIZ)
498                 g_free (oldptr);
499
500         g_hash_table_insert (table->method_address_hash, method, address);
501
502         mono_debugger_unlock ();
503         return address;
504 }
505
506 void
507 mono_debug_remove_method (MonoMethod *method, MonoDomain *domain)
508 {
509         MonoDebugDataTable *table;
510         MonoDebugMethodAddress *address;
511
512         if (!mono_debug_initialized)
513                 return;
514
515         g_assert (method_is_dynamic (method));
516
517         mono_debugger_lock ();
518
519         table = lookup_data_table (domain);
520
521         address = (MonoDebugMethodAddress *)g_hash_table_lookup (table->method_address_hash, method);
522         if (address)
523                 g_free (address);
524
525         g_hash_table_remove (table->method_address_hash, method);
526
527         mono_debugger_unlock ();
528 }
529
530 void
531 mono_debug_add_delegate_trampoline (gpointer code, int size)
532 {
533 }
534
535 static inline guint32
536 read_leb128 (guint8 *ptr, guint8 **rptr)
537 {
538         guint32 result = 0, shift = 0;
539
540         while (TRUE) {
541                 guint8 byte = *ptr++;
542
543                 result |= (byte & 0x7f) << shift;
544                 if ((byte & 0x80) == 0)
545                         break;
546                 shift += 7;
547         }
548
549         *rptr = ptr;
550         return result;
551 }
552
553 static inline gint32
554 read_sleb128 (guint8 *ptr, guint8 **rptr)
555 {
556         gint32 result = 0;
557         guint32 shift = 0;
558
559         while (TRUE) {
560                 guint8 byte = *ptr++;
561
562                 result |= (byte & 0x7f) << shift;
563                 shift += 7;
564
565                 if (byte & 0x80)
566                         continue;
567
568                 if ((shift < 32) && (byte & 0x40))
569                         result |= - (1 << shift);
570                 break;
571         }
572
573         *rptr = ptr;
574         return result;
575 }
576
577 static void
578 read_variable (MonoDebugVarInfo *var, guint8 *ptr, guint8 **rptr)
579 {
580         var->index = read_leb128 (ptr, &ptr);
581         var->offset = read_sleb128 (ptr, &ptr);
582         var->size = read_leb128 (ptr, &ptr);
583         var->begin_scope = read_leb128 (ptr, &ptr);
584         var->end_scope = read_leb128 (ptr, &ptr);
585         READ_UNALIGNED (MonoType *, ptr, var->type);
586         ptr += sizeof (gpointer);
587         *rptr = ptr;
588 }
589
590 void
591 mono_debug_free_method_jit_info (MonoDebugMethodJitInfo *jit)
592 {
593         if (!jit)
594                 return;
595         g_free (jit->line_numbers);
596         g_free (jit->this_var);
597         g_free (jit->params);
598         g_free (jit->locals);
599         g_free (jit->gsharedvt_info_var);
600         g_free (jit->gsharedvt_locals_var);
601         g_free (jit);
602 }
603
604 static MonoDebugMethodJitInfo *
605 mono_debug_read_method (MonoDebugMethodAddress *address)
606 {
607         MonoDebugMethodJitInfo *jit;
608         guint32 i;
609         guint8 *ptr;
610
611         jit = g_new0 (MonoDebugMethodJitInfo, 1);
612         jit->code_start = address->code_start;
613         jit->code_size = address->code_size;
614
615         ptr = (guint8 *) &address->data;
616
617         jit->prologue_end = read_leb128 (ptr, &ptr);
618         jit->epilogue_begin = read_leb128 (ptr, &ptr);
619
620         jit->num_line_numbers = read_leb128 (ptr, &ptr);
621         jit->line_numbers = g_new0 (MonoDebugLineNumberEntry, jit->num_line_numbers);
622         for (i = 0; i < jit->num_line_numbers; i++) {
623                 MonoDebugLineNumberEntry *lne = &jit->line_numbers [i];
624
625                 lne->il_offset = read_sleb128 (ptr, &ptr);
626                 lne->native_offset = read_sleb128 (ptr, &ptr);
627         }
628         jit->has_var_info = read_leb128 (ptr, &ptr);
629         if (jit->has_var_info) {
630                 if (*ptr++) {
631                         jit->this_var = g_new0 (MonoDebugVarInfo, 1);
632                         read_variable (jit->this_var, ptr, &ptr);
633                 }
634
635                 jit->num_params = read_leb128 (ptr, &ptr);
636                 jit->params = g_new0 (MonoDebugVarInfo, jit->num_params);
637                 for (i = 0; i < jit->num_params; i++)
638                         read_variable (&jit->params [i], ptr, &ptr);
639
640                 jit->num_locals = read_leb128 (ptr, &ptr);
641                 jit->locals = g_new0 (MonoDebugVarInfo, jit->num_locals);
642                 for (i = 0; i < jit->num_locals; i++)
643                         read_variable (&jit->locals [i], ptr, &ptr);
644
645                 if (*ptr++) {
646                         jit->gsharedvt_info_var = g_new0 (MonoDebugVarInfo, 1);
647                         jit->gsharedvt_locals_var = g_new0 (MonoDebugVarInfo, 1);
648                         read_variable (jit->gsharedvt_info_var, ptr, &ptr);
649                         read_variable (jit->gsharedvt_locals_var, ptr, &ptr);
650                 }
651         }
652
653         return jit;
654 }
655
656 static MonoDebugMethodJitInfo *
657 find_method (MonoMethod *method, MonoDomain *domain)
658 {
659         MonoDebugDataTable *table;
660         MonoDebugMethodAddress *address;
661
662         table = lookup_data_table (domain);
663         address = (MonoDebugMethodAddress *)g_hash_table_lookup (table->method_address_hash, method);
664
665         if (!address)
666                 return NULL;
667
668         return mono_debug_read_method (address);
669 }
670
671 MonoDebugMethodJitInfo *
672 mono_debug_find_method (MonoMethod *method, MonoDomain *domain)
673 {
674         MonoDebugMethodJitInfo *res;
675
676         if (mono_debug_format == MONO_DEBUG_FORMAT_NONE)
677                 return NULL;
678
679         mono_debugger_lock ();
680         res = find_method (method, domain);
681         mono_debugger_unlock ();
682         return res;
683 }
684
685 MonoDebugMethodAddressList *
686 mono_debug_lookup_method_addresses (MonoMethod *method)
687 {
688         g_assert_not_reached ();
689         return NULL;
690 }
691
692 static gint32
693 il_offset_from_address (MonoMethod *method, MonoDomain *domain, guint32 native_offset)
694 {
695         MonoDebugMethodJitInfo *jit;
696         int i;
697
698         jit = find_method (method, domain);
699         if (!jit || !jit->line_numbers)
700                 goto cleanup_and_fail;
701
702         for (i = jit->num_line_numbers - 1; i >= 0; i--) {
703                 MonoDebugLineNumberEntry lne = jit->line_numbers [i];
704
705                 if (lne.native_offset <= native_offset) {
706                         mono_debug_free_method_jit_info (jit);
707                         return lne.il_offset;
708                 }
709         }
710
711 cleanup_and_fail:
712         mono_debug_free_method_jit_info (jit);
713         return -1;
714 }
715
716 /**
717  * mono_debug_il_offset_from_address:
718  *
719  *   Compute the IL offset corresponding to NATIVE_OFFSET inside the native
720  * code of METHOD in DOMAIN.
721  */
722 gint32
723 mono_debug_il_offset_from_address (MonoMethod *method, MonoDomain *domain, guint32 native_offset)
724 {
725         gint32 res;
726
727         mono_debugger_lock ();
728
729         res = il_offset_from_address (method, domain, native_offset);
730
731         mono_debugger_unlock ();
732
733         return res;
734 }
735
736 /**
737  * mono_debug_lookup_source_location:
738  * @address: Native offset within the @method's machine code.
739  *
740  * Lookup the source code corresponding to the machine instruction located at
741  * native offset @address within @method.
742  *
743  * The returned `MonoDebugSourceLocation' contains both file / line number
744  * information and the corresponding IL offset.  It must be freed by
745  * mono_debug_free_source_location().
746  */
747 MonoDebugSourceLocation *
748 mono_debug_lookup_source_location (MonoMethod *method, guint32 address, MonoDomain *domain)
749 {
750         MonoDebugMethodInfo *minfo;
751         MonoDebugSourceLocation *location;
752         gint32 offset;
753
754         if (mono_debug_format == MONO_DEBUG_FORMAT_NONE)
755                 return NULL;
756
757         mono_debugger_lock ();
758         minfo = mono_debug_lookup_method_internal (method);
759         if (!minfo || !minfo->handle) {
760                 mono_debugger_unlock ();
761                 return NULL;
762         }
763
764         if (!minfo->handle->ppdb && (!minfo->handle->symfile || !mono_debug_symfile_is_loaded (minfo->handle->symfile))) {
765                 mono_debugger_unlock ();
766                 return NULL;
767         }
768
769         offset = il_offset_from_address (method, domain, address);
770         if (offset < 0) {
771                 mono_debugger_unlock ();
772                 return NULL;
773         }
774
775         if (minfo->handle->ppdb)
776                 location = mono_ppdb_lookup_location (minfo, offset);
777         else
778                 location = mono_debug_symfile_lookup_location (minfo, offset);
779         mono_debugger_unlock ();
780         return location;
781 }
782
783 MonoDebugSourceLocation *
784 mono_debug_method_lookup_location (MonoDebugMethodInfo *minfo, int il_offset)
785 {
786         MonoDebugSourceLocation *location;
787
788         mono_debugger_lock ();
789         if (minfo->handle->ppdb)
790                 location = mono_ppdb_lookup_location (minfo, il_offset);
791         else
792                 location = mono_debug_symfile_lookup_location (minfo, il_offset);
793         mono_debugger_unlock ();
794         return location;
795 }
796
797 /*
798  * mono_debug_lookup_locals:
799  *
800  *   Return information about the local variables of MINFO.
801  * The result should be freed using mono_debug_free_locals ().
802  */
803 MonoDebugLocalsInfo*
804 mono_debug_lookup_locals (MonoMethod *method)
805 {
806         MonoDebugMethodInfo *minfo;
807         MonoDebugLocalsInfo *res;
808
809         if (mono_debug_format == MONO_DEBUG_FORMAT_NONE)
810                 return NULL;
811
812         mono_debugger_lock ();
813         minfo = mono_debug_lookup_method_internal (method);
814         if (!minfo || !minfo->handle) {
815                 mono_debugger_unlock ();
816                 return NULL;
817         }
818
819         if (minfo->handle->ppdb) {
820                 res = mono_ppdb_lookup_locals (minfo);
821         } else {
822                 if (!minfo->handle->symfile || !mono_debug_symfile_is_loaded (minfo->handle->symfile))
823                         res = NULL;
824                 else
825                         res = mono_debug_symfile_lookup_locals (minfo);
826         }
827         mono_debugger_unlock ();
828
829         return res;
830 }
831
832 /*
833  * mono_debug_free_locals:
834  *
835  *   Free all the data allocated by mono_debug_lookup_locals ().
836  */
837 void
838 mono_debug_free_locals (MonoDebugLocalsInfo *info)
839 {
840         int i;
841
842         for (i = 0; i < info->num_locals; ++i)
843                 g_free (info->locals [i].name);
844         g_free (info->locals);
845         g_free (info->code_blocks);
846         g_free (info);
847 }
848
849 /**
850  * mono_debug_free_source_location:
851  * @location: A `MonoDebugSourceLocation'.
852  *
853  * Frees the @location.
854  */
855 void
856 mono_debug_free_source_location (MonoDebugSourceLocation *location)
857 {
858         if (location) {
859                 g_free (location->source_file);
860                 g_free (location);
861         }
862 }
863
864 /**
865  * mono_debug_print_stack_frame:
866  * @native_offset: Native offset within the @method's machine code.
867  *
868  * Conventient wrapper around mono_debug_lookup_source_location() which can be
869  * used if you only want to use the location to print a stack frame.
870  */
871 gchar *
872 mono_debug_print_stack_frame (MonoMethod *method, guint32 native_offset, MonoDomain *domain)
873 {
874         MonoDebugSourceLocation *location;
875         gchar *fname, *ptr, *res;
876         int offset;
877
878         fname = mono_method_full_name (method, TRUE);
879         for (ptr = fname; *ptr; ptr++) {
880                 if (*ptr == ':') *ptr = '.';
881         }
882
883         location = mono_debug_lookup_source_location (method, native_offset, domain);
884
885         if (!location) {
886                 if (mono_debug_initialized) {
887                         mono_debugger_lock ();
888                         offset = il_offset_from_address (method, domain, native_offset);
889                         mono_debugger_unlock ();
890                 } else {
891                         offset = -1;
892                 }
893
894                 if (offset < 0)
895                         res = g_strdup_printf ("at %s <0x%05x>", fname, native_offset);
896                 else
897                         res = g_strdup_printf ("at %s <IL 0x%05x, 0x%05x>", fname, offset, native_offset);
898                 g_free (fname);
899                 return res;
900         }
901
902         res = g_strdup_printf ("at %s [0x%05x] in %s:%d", fname, location->il_offset,
903                                location->source_file, location->row);
904
905         g_free (fname);
906         mono_debug_free_source_location (location);
907         return res;
908 }
909
910 void
911 mono_set_is_debugger_attached (gboolean attached)
912 {
913         is_attached = attached;
914 }
915
916 gboolean
917 mono_is_debugger_attached (void)
918 {
919         return is_attached;
920 }
921
922 /*
923  * Bundles
924  */
925
926 typedef struct _BundledSymfile BundledSymfile;
927
928 struct _BundledSymfile {
929         BundledSymfile *next;
930         const char *aname;
931         const mono_byte *raw_contents;
932         int size;
933 };
934
935 static BundledSymfile *bundled_symfiles = NULL;
936
937 void
938 mono_register_symfile_for_assembly (const char *assembly_name, const mono_byte *raw_contents, int size)
939 {
940         BundledSymfile *bsymfile;
941
942         bsymfile = g_new0 (BundledSymfile, 1);
943         bsymfile->aname = assembly_name;
944         bsymfile->raw_contents = raw_contents;
945         bsymfile->size = size;
946         bsymfile->next = bundled_symfiles;
947         bundled_symfiles = bsymfile;
948 }
949
950 static MonoDebugHandle *
951 open_symfile_from_bundle (MonoImage *image)
952 {
953         BundledSymfile *bsymfile;
954
955         for (bsymfile = bundled_symfiles; bsymfile; bsymfile = bsymfile->next) {
956                 if (strcmp (bsymfile->aname, image->module_name))
957                         continue;
958
959                 return mono_debug_open_image (image, bsymfile->raw_contents, bsymfile->size);
960         }
961
962         return NULL;
963 }
964
965 void
966 mono_debugger_lock (void)
967 {
968         g_assert (mono_debug_initialized);
969         mono_os_mutex_lock (&debugger_lock_mutex);
970 }
971
972 void
973 mono_debugger_unlock (void)
974 {
975         g_assert (mono_debug_initialized);
976         mono_os_mutex_unlock (&debugger_lock_mutex);
977 }
978
979 /**
980  * mono_debug_enabled:
981  *
982  * Returns true is debug information is enabled. This doesn't relate if a debugger is present or not.
983  */
984 mono_bool
985 mono_debug_enabled (void)
986 {
987         return mono_debug_format != MONO_DEBUG_FORMAT_NONE;
988 }
989
990 void
991 mono_debug_get_seq_points (MonoDebugMethodInfo *minfo, char **source_file, GPtrArray **source_file_list, int **source_files, MonoSymSeqPoint **seq_points, int *n_seq_points)
992 {
993         if (minfo->handle->ppdb)
994                 mono_ppdb_get_seq_points (minfo, source_file, source_file_list, source_files, seq_points, n_seq_points);
995         else
996                 mono_debug_symfile_get_seq_points (minfo, source_file, source_file_list, source_files, seq_points, n_seq_points);
997 }