2004-01-19 Zoltan Varga <vargaz@freemail.hu>
[mono.git] / mono / metadata / mono-debug-debugger.c
index d3e1ab5792c9f66412a12efb2ce9e6d017603895..e402d26477109ccf9e865b66f257737dd9c52338 100644 (file)
@@ -47,7 +47,8 @@ void (*mono_debugger_event_handler) (MonoDebuggerEvent event, gpointer data, gui
 MonoDebuggerIOLayer mono_debugger_io_layer = {
        InitializeCriticalSection, DeleteCriticalSection, TryEnterCriticalSection,
        EnterCriticalSection, LeaveCriticalSection, WaitForSingleObject, SignalObjectAndWait,
-       WaitForMultipleObjects, CreateSemaphore, ReleaseSemaphore, CreateThread
+       WaitForMultipleObjects, CreateSemaphore, ReleaseSemaphore, CreateThread,
+       GetCurrentThreadId
 };
 
 #endif
@@ -82,6 +83,8 @@ allocate_symbol_file_entry (MonoDebuggerSymbolTable *table)
 
        symfile = g_new0 (MonoDebuggerSymbolFile, 1);
        symfile->index = table->num_symbol_files;
+       symfile->range_entry_size = sizeof (MonoDebuggerRangeInfo);
+       symfile->class_entry_size = sizeof (MonoDebuggerClassInfo);
        table->symbol_files [table->num_symbol_files++] = symfile;
        return symfile;
 }
@@ -121,6 +124,7 @@ mono_debugger_add_symbol_file (MonoDebugHandle *handle)
        MonoDebuggerSymbolFile *info;
 
        g_assert (mono_debugger_initialized);
+       mono_debugger_lock ();
 
        info = g_hash_table_lookup (images, handle->image);
        if (info)
@@ -132,6 +136,7 @@ mono_debugger_add_symbol_file (MonoDebugHandle *handle)
        info->image_file = handle->image_file;
 
        g_hash_table_insert (images, handle->image, info);
+       mono_debugger_unlock ();
 
        return info;
 }
@@ -470,8 +475,6 @@ allocate_range_entry (MonoDebuggerSymbolFile *symfile)
        MonoDebuggerRangeInfo *retval;
        guint32 size, chunks;
 
-       symfile->range_entry_size = sizeof (MonoDebuggerRangeInfo);
-
        if (!symfile->range_table) {
                size = sizeof (MonoDebuggerRangeInfo) * RANGE_TABLE_CHUNK_SIZE;
                symfile->range_table = g_malloc0 (size);
@@ -497,8 +500,6 @@ allocate_class_entry (MonoDebuggerSymbolFile *symfile)
        MonoDebuggerClassInfo *retval;
        guint32 size, chunks;
 
-       symfile->class_entry_size = sizeof (MonoDebuggerClassInfo);
-
        if (!symfile->class_table) {
                size = sizeof (MonoDebuggerClassInfo) * CLASS_TABLE_CHUNK_SIZE;
                symfile->class_table = g_malloc0 (size);
@@ -591,9 +592,10 @@ static guint32
 write_class (MonoDebuggerSymbolTable *table, MonoClass *klass)
 {
        guint8 buffer [BUFSIZ], *ptr = buffer, *old_ptr;
-       GPtrArray *methods = NULL, *static_methods = NULL;
+       GPtrArray *methods = NULL, *static_methods = NULL, *ctors = NULL;
        int num_fields = 0, num_static_fields = 0, num_properties = 0, num_static_properties = 0;
        int num_methods = 0, num_static_methods = 0, num_params = 0, num_static_params = 0, base_offset = 0;
+       int num_ctors = 0, num_ctor_params = 0;
        guint32 size, data_size, offset;
        GHashTable *method_slots = NULL;
        int i;
@@ -631,16 +633,25 @@ write_class (MonoDebuggerSymbolTable *table, MonoClass *klass)
        method_slots = g_hash_table_new (NULL, NULL);
        methods = g_ptr_array_new ();
        static_methods = g_ptr_array_new ();
+       ctors = g_ptr_array_new ();
 
        for (i = 0; i < klass->method.count; i++) {
                MonoMethod *method = klass->methods [i];
 
-               if (strcmp (method->name, ".ctor") == 0 || strcmp (method->name, ".cctor") == 0)
-                       continue;
-               if (method->flags & METHOD_ATTRIBUTE_SPECIAL_NAME)
+               if (!strcmp (method->name, ".cctor"))
                        continue;
                if (!((method->flags & METHOD_ATTRIBUTE_MEMBER_ACCESS_MASK) == METHOD_ATTRIBUTE_PUBLIC))
                        continue;
+
+               if (!strcmp (method->name, ".ctor")) {
+                       ++num_ctors;
+                       num_ctor_params += method->signature->param_count;
+                       g_ptr_array_add (ctors, method);
+                       continue;
+               }
+
+               if (method->flags & METHOD_ATTRIBUTE_SPECIAL_NAME)
+                       continue;
                if (g_hash_table_lookup (method_slots, GUINT_TO_POINTER (method->slot)))
                        continue;
                g_hash_table_insert (method_slots, GUINT_TO_POINTER (method->slot), method);
@@ -658,9 +669,10 @@ write_class (MonoDebuggerSymbolTable *table, MonoClass *klass)
 
        g_hash_table_destroy (method_slots);
 
-       size = 58 + sizeof (gpointer) + num_fields * 8 + num_static_fields * 8 + num_properties * (4 + 2 * sizeof (gpointer)) +
+       size = 66 + sizeof (gpointer) + num_fields * 8 + num_static_fields * 8 + num_properties * (4 + 2 * sizeof (gpointer)) +
                num_static_properties * (4 + 2 * sizeof (gpointer)) + num_methods * (8 + sizeof (gpointer)) + num_params * 4 +
-               num_static_methods * (8 + sizeof (gpointer)) + num_static_params * 4;
+               num_static_methods * (8 + sizeof (gpointer)) + num_static_params * 4 + num_ctors * (8 + sizeof (gpointer)) +
+               num_ctor_params * 4;
 
        data_size = size;
 
@@ -689,6 +701,9 @@ write_class (MonoDebuggerSymbolTable *table, MonoClass *klass)
        WRITE_UINT32 (ptr, num_methods * (4 + 2 * sizeof (gpointer)) + num_params * sizeof (gpointer));
        WRITE_UINT32 (ptr, num_static_methods);
        WRITE_UINT32 (ptr, num_static_methods * (4 + 2 * sizeof (gpointer)) + num_static_params * sizeof (gpointer));
+       WRITE_UINT32 (ptr, num_ctors);
+       WRITE_UINT32 (ptr, num_ctors * (4 + 2 * sizeof (gpointer)) + num_ctor_params * sizeof (gpointer));
+
        for (i = 0; i < klass->field.count; i++) {
                if (klass->fields [i].type->attrs & FIELD_ATTRIBUTE_STATIC)
                        continue;
@@ -759,6 +774,21 @@ write_class (MonoDebuggerSymbolTable *table, MonoClass *klass)
                        WRITE_UINT32 (ptr, write_type (table, method->signature->params [j]));
        }
 
+       g_ptr_array_free (static_methods, FALSE);
+
+       for (i = 0; i < ctors->len; i++) {
+               MonoMethod *ctor = g_ptr_array_index (ctors, i);
+               int j;
+
+               WRITE_POINTER (ptr, ctor);
+               WRITE_UINT32 (ptr, 0);
+               WRITE_UINT32 (ptr, ctor->signature->param_count);
+               for (j = 0; j < ctor->signature->param_count; j++)
+                       WRITE_UINT32 (ptr, write_type (table, ctor->signature->params [j]));
+       }
+
+       g_ptr_array_free (ctors, FALSE);
+
        if (klass->parent && (klass->parent != mono_defaults.object_class))
                WRITE_UINT32 (ptr, write_class (table, klass->parent));
        else
@@ -1108,7 +1138,13 @@ mono_debugger_runtime_invoke (MonoMethod *method, void *obj, void **params, Mono
        if (method->klass->valuetype && (obj != NULL))
                obj = mono_value_box (mono_domain_get (), method->klass, obj);
 
-       retval = mono_runtime_invoke (method, obj, params, exc);
+       if (!strcmp (method->name, ".ctor")) {
+               retval = obj = mono_object_new (mono_domain_get (), method->klass);
+
+               mono_runtime_invoke (method, obj, params, exc);
+       } else
+               retval = mono_runtime_invoke (method, obj, params, exc);
+
        if (*exc == NULL)
                return retval;
 
@@ -1120,3 +1156,29 @@ mono_debugger_runtime_invoke (MonoMethod *method, void *obj, void **params, Mono
 
        return retval;
 }
+
+guint32
+mono_debugger_lookup_type (const gchar *type_name)
+{
+       int i;
+
+       mono_debugger_lock ();
+
+       for (i = 0; i < mono_debugger_symbol_table->num_symbol_files; i++) {
+               MonoDebuggerSymbolFile *symfile = mono_debugger_symbol_table->symbol_files [i];
+               MonoType *type;
+               guint32 offset;
+
+               type = mono_reflection_type_from_name (type_name, symfile->image);
+               if (!type)
+                       continue;
+
+               offset = write_type (mono_debugger_symbol_table, type);
+
+               mono_debugger_unlock ();
+               return offset;
+       }
+
+       mono_debugger_unlock ();
+       return 0;
+}