[runtime] Fix reading past the end of a string when setting the native thread name.
[mono.git] / mono / dis / get.c
old mode 100644 (file)
new mode 100755 (executable)
index 6c4d158..34f87b0
@@ -5,6 +5,7 @@
  *   Miguel de Icaza (miguel@ximian.com)
  *
  * (C) 2001 Ximian, Inc.
+ * Copyright 2012 Xamarin Inc
  */
 #include <config.h>
 #include <stdio.h>
@@ -1276,7 +1277,11 @@ get_type (MonoImage *m, const char *ptr, char **result, gboolean is_def, MonoGen
        case MONO_TYPE_CLASS: {
                guint32 token = mono_metadata_parse_typedef_or_ref (m, ptr, &ptr);
                MonoClass *klass = mono_class_get (m, token);
-               char *temp = dis_stringify_object_with_class (m, klass, TRUE, FALSE);
+               char *temp;
+               if (klass)
+                       temp = dis_stringify_object_with_class (m, klass, TRUE, FALSE);
+               else
+                       temp = g_strdup_printf ("<BROKEN CLASS token_%8x>", token);
 
                if (show_tokens) {
                        *result = g_strdup_printf ("%s/*%08x*/", temp, token);
@@ -1618,7 +1623,15 @@ static dis_map_t field_flags_map [] = {
        { FIELD_ATTRIBUTE_SPECIAL_NAME,        "specialname " },
        { FIELD_ATTRIBUTE_PINVOKE_IMPL,        "FIXME:pinvokeimpl " },
        { FIELD_ATTRIBUTE_RT_SPECIAL_NAME,        "rtspecialname " },
-       /*{ FIELD_ATTRIBUTE_HAS_FIELD_MARSHAL,        "hasfieldmarshal " },*/
+
+       /* This is set when a MarshalAs attribute is seen. FIXME: round-trip?  */
+       { FIELD_ATTRIBUTE_HAS_FIELD_MARSHAL,        "" },
+
+       /* This seems to be set if LITERAL is set. FIXME: round-trip? */
+       { FIELD_ATTRIBUTE_HAS_DEFAULT,          "" },
+
+       /* This seems to be set on compiler-generated array initializer fields. FIXME: round-trip? */
+       { FIELD_ATTRIBUTE_HAS_FIELD_RVA,                "" },
        { 0, NULL }
 };
 
@@ -1632,11 +1645,12 @@ field_flags (guint32 f)
 {
        char buffer [1024];
        int access = f & FIELD_ATTRIBUTE_FIELD_ACCESS_MASK;
+       int rest = f & ~access;
        
        buffer [0] = 0;
 
        strcat (buffer, map (access, field_access_map));
-       strcat (buffer, flags (f, field_flags_map));
+       strcat (buffer, flags (rest, field_flags_map));
        return g_strdup (buffer);
 }
 
@@ -2293,10 +2307,10 @@ get_constant (MonoImage *m, MonoTypeEnum t, guint32 blob_index)
                readr4 (ptr, &r);
 
                /* Crazy solaris systems doesn't have isnormal */
-#ifdef HAVE_FINITE
-               normal = finite (r);
+#ifdef HAVE_ISFINITE
+               normal = isfinite (r);
 #else
-               normal = isnormal (r);
+               normal = !dis_isinf (r) && !dis_isnan (r);
 #endif
                if (!normal) {
                        return g_strdup_printf ("float32(0x%08x)", read32 (ptr));
@@ -2313,8 +2327,8 @@ get_constant (MonoImage *m, MonoTypeEnum t, guint32 blob_index)
                readr8 (ptr, &r);
 
                /* Crazy solaris systems doesn't have isnormal */
-#ifdef HAVE_FINITE
-               normal = finite (r);
+#ifdef HAVE_ISFINITE
+               normal = isfinite (r);
 #else
                normal = isnormal (r);
 #endif
@@ -2890,6 +2904,7 @@ init_key_table (void)
        g_hash_table_insert (key_table, (char *) "ldvirtftn", GINT_TO_POINTER (TRUE));
        g_hash_table_insert (key_table, (char *) "leave", GINT_TO_POINTER (TRUE));
        g_hash_table_insert (key_table, (char *) "leave.s", GINT_TO_POINTER (TRUE));
+       g_hash_table_insert (key_table, (char *) "legacy", GINT_TO_POINTER (TRUE));
        g_hash_table_insert (key_table, (char *) "linkcheck", GINT_TO_POINTER (TRUE));
        g_hash_table_insert (key_table, (char *) "literal", GINT_TO_POINTER (TRUE));
        g_hash_table_insert (key_table, (char *) "localloc", GINT_TO_POINTER (TRUE));
@@ -3157,3 +3172,46 @@ cant_print_generic_param_name (MonoGenericParam *gparam)
 }
 
 
+static dis_map_t method_impl_map [] = {
+       { METHOD_IMPL_ATTRIBUTE_IL,              "cil " },
+       { METHOD_IMPL_ATTRIBUTE_NATIVE,          "native " },
+       { METHOD_IMPL_ATTRIBUTE_OPTIL,           "optil " },
+       { METHOD_IMPL_ATTRIBUTE_RUNTIME,         "runtime " },
+       { 0, NULL }
+};
+
+static dis_map_t managed_type_map [] = {
+       { METHOD_IMPL_ATTRIBUTE_UNMANAGED,       "unmanaged " },
+       { METHOD_IMPL_ATTRIBUTE_MANAGED,         "managed " },
+       { 0, NULL }
+};
+
+static dis_map_t managed_impl_flags [] = {
+       { METHOD_IMPL_ATTRIBUTE_FORWARD_REF,     "fwdref " },
+       { METHOD_IMPL_ATTRIBUTE_PRESERVE_SIG,    "preservesig " },
+       { METHOD_IMPL_ATTRIBUTE_INTERNAL_CALL,   "internalcall " },
+       { METHOD_IMPL_ATTRIBUTE_SYNCHRONIZED,    "synchronized " },
+       { METHOD_IMPL_ATTRIBUTE_NOINLINING,      "noinlining " },
+       { METHOD_IMPL_ATTRIBUTE_NOOPTIMIZATION,  "nooptimization " },
+       { METHOD_IMPL_ATTRIBUTE_AGGRESSIVE_INLINING,  "agressive-inlining" },
+       { 0, NULL }
+};
+
+char *
+get_method_impl_flags (guint32 f)
+{
+       GString *str = g_string_new ("");
+       char *s;
+       int code_type = f & METHOD_IMPL_ATTRIBUTE_CODE_TYPE_MASK;
+       int managed_type = f & METHOD_IMPL_ATTRIBUTE_MANAGED_MASK;
+       int rest = f & ~(code_type | managed_type);
+
+       g_string_append (str, map (code_type, method_impl_map));
+       g_string_append (str, map (managed_type, managed_type_map));
+       g_string_append (str, flags (rest, managed_impl_flags));
+       
+       s = str->str;
+       g_string_free (str, FALSE);
+       return s;
+}
+