[runtime] Fix monitor exception throwing
[mono.git] / mono / metadata / class-accessors.c
1 /*
2  * Copyright 2016 Microsoft
3  * Licensed under the MIT license. See LICENSE file in the project root for full license information.
4  */
5 #include <mono/metadata/class-internals.h>
6 #include <mono/metadata/tabledefs.h>
7
8
9 /* Accessors based on class kind*/
10
11 /*
12 * mono_class_get_generic_class:
13 *
14 *   Return the MonoGenericClass of @klass, which MUST be a generic instance.
15 */
16 MonoGenericClass*
17 mono_class_get_generic_class (MonoClass *klass)
18 {
19         g_assert (mono_class_is_ginst (klass));
20         return ((MonoClassGenericInst*)klass)->generic_class;
21 }
22
23 /*
24 * mono_class_try_get_generic_class:
25 *
26 *   Return the MonoGenericClass if @klass is a ginst, NULL otherwise
27 */
28 MonoGenericClass*
29 mono_class_try_get_generic_class (MonoClass *klass)
30 {
31         if (mono_class_is_ginst (klass))
32                 return ((MonoClassGenericInst*)klass)->generic_class;
33         return NULL;
34 }
35
36 /**
37  * mono_class_get_flags:
38  * @klass: the MonoClass to act on
39  *
40  * Return the TypeAttributes flags of @klass.
41  * See the TYPE_ATTRIBUTE_* definitions on tabledefs.h for the different values.
42  *
43  * Returns: The type flags
44  */
45 guint32
46 mono_class_get_flags (MonoClass *klass)
47 {
48         switch (klass->class_kind) {
49         case MONO_CLASS_DEF:
50         case MONO_CLASS_GTD:
51                 return ((MonoClassDef*)klass)->flags;
52         case MONO_CLASS_GINST:
53                 return mono_class_get_flags (((MonoClassGenericInst*)klass)->generic_class->container_class);
54         case MONO_CLASS_GPARAM:
55                 return TYPE_ATTRIBUTE_PUBLIC;
56         case MONO_CLASS_ARRAY:
57                 /* all arrays are marked serializable and sealed, bug #42779 */
58                 return TYPE_ATTRIBUTE_CLASS | TYPE_ATTRIBUTE_SERIALIZABLE | TYPE_ATTRIBUTE_SEALED | TYPE_ATTRIBUTE_PUBLIC;
59         case MONO_CLASS_POINTER:
60                 return TYPE_ATTRIBUTE_CLASS | (mono_class_get_flags (klass->element_class) & TYPE_ATTRIBUTE_VISIBILITY_MASK);
61         }
62         g_assert_not_reached ();
63 }
64
65 void
66 mono_class_set_flags (MonoClass *klass, guint32 flags)
67 {
68         g_assert (klass->class_kind == MONO_CLASS_DEF || klass->class_kind == MONO_CLASS_GTD);
69         ((MonoClassDef*)klass)->flags = flags;
70 }
71
72 /*
73  * mono_class_get_generic_container:
74  *
75  *   Return the generic container of KLASS which should be a generic type definition.
76  */
77 MonoGenericContainer*
78 mono_class_get_generic_container (MonoClass *klass)
79 {
80         g_assert (mono_class_is_gtd (klass));
81
82         return ((MonoClassGtd*)klass)->generic_container;
83 }
84
85 MonoGenericContainer*
86 mono_class_try_get_generic_container (MonoClass *klass)
87 {
88         if (mono_class_is_gtd (klass))
89                 return ((MonoClassGtd*)klass)->generic_container;
90         return NULL;
91 }
92
93
94 void
95 mono_class_set_generic_container (MonoClass *klass, MonoGenericContainer *container)
96 {
97         g_assert (mono_class_is_gtd (klass));
98
99         ((MonoClassGtd*)klass)->generic_container = container;
100 }
101
102 /*
103  * mono_class_get_first_method_idx:
104  *
105  *   Return the table index of the first method for metadata classes.
106  */
107 guint32
108 mono_class_get_first_method_idx (MonoClass *klass)
109 {
110         g_assert (mono_class_has_static_metadata (klass));
111
112         return ((MonoClassDef*)klass)->first_method_idx;
113 }
114
115 void
116 mono_class_set_first_method_idx (MonoClass *klass, guint32 idx)
117 {
118         g_assert (mono_class_has_static_metadata (klass));
119
120         ((MonoClassDef*)klass)->first_method_idx = idx;
121 }
122
123 guint32
124 mono_class_get_first_field_idx (MonoClass *klass)
125 {
126         if (mono_class_is_ginst (klass))
127                 return mono_class_get_first_field_idx (mono_class_get_generic_class (klass)->container_class);
128
129         g_assert (mono_class_has_static_metadata (klass));
130
131         return ((MonoClassDef*)klass)->first_field_idx;
132 }
133
134 void
135 mono_class_set_first_field_idx (MonoClass *klass, guint32 idx)
136 {
137         g_assert (mono_class_has_static_metadata (klass));
138
139         ((MonoClassDef*)klass)->first_field_idx = idx;
140 }
141
142 guint32
143 mono_class_get_method_count (MonoClass *klass)
144 {
145         switch (klass->class_kind) {
146         case MONO_CLASS_DEF:
147         case MONO_CLASS_GTD:
148                 return ((MonoClassDef*)klass)->method_count;
149         case MONO_CLASS_GINST:
150                 return mono_class_get_method_count (((MonoClassGenericInst*)klass)->generic_class->container_class);
151         case MONO_CLASS_GPARAM:
152                 return 0;
153         case MONO_CLASS_ARRAY:
154                 return ((MonoClassArray*)klass)->method_count;
155         case MONO_CLASS_POINTER:
156                 return 0;
157         default:
158                 g_assert_not_reached ();
159                 return 0;
160         }
161 }
162
163 void
164 mono_class_set_method_count (MonoClass *klass, guint32 count)
165 {
166         switch (klass->class_kind) {
167         case MONO_CLASS_DEF:
168         case MONO_CLASS_GTD:
169                 ((MonoClassDef*)klass)->method_count = count;
170                 break;
171         case MONO_CLASS_GINST:
172                 break;
173         case MONO_CLASS_GPARAM:
174         case MONO_CLASS_POINTER:
175                 g_assert (count == 0);
176                 break;
177         case MONO_CLASS_ARRAY:
178                 ((MonoClassArray*)klass)->method_count = count;
179                 break;
180         default:
181                 g_assert_not_reached ();
182                 break;
183         }
184 }
185
186 guint32
187 mono_class_get_field_count (MonoClass *klass)
188 {
189         switch (klass->class_kind) {
190         case MONO_CLASS_DEF:
191         case MONO_CLASS_GTD:
192                 return ((MonoClassDef*)klass)->field_count;
193         case MONO_CLASS_GINST:
194                 return mono_class_get_field_count (((MonoClassGenericInst*)klass)->generic_class->container_class);
195         case MONO_CLASS_GPARAM:
196         case MONO_CLASS_ARRAY:
197         case MONO_CLASS_POINTER:
198                 return 0;
199         default:
200                 g_assert_not_reached ();
201                 return 0;
202         }
203 }
204
205 void
206 mono_class_set_field_count (MonoClass *klass, guint32 count)
207 {
208         switch (klass->class_kind) {
209         case MONO_CLASS_DEF:
210         case MONO_CLASS_GTD:
211                 ((MonoClassDef*)klass)->field_count = count;
212                 break;
213         case MONO_CLASS_GINST:
214                 break;
215         case MONO_CLASS_GPARAM:
216         case MONO_CLASS_ARRAY:
217         case MONO_CLASS_POINTER:
218                 g_assert (count == 0);
219                 break;
220         default:
221                 g_assert_not_reached ();
222                 break;
223         }
224 }