2 * aot-dump.c: mono Ahead of Time compiler JSON dumping
5 * Joao Matos (joao.matos@xamarin.com)
7 * Copyright 2015 Xamarin Inc (http://www.xamarin.com)
10 #ifndef MONO_SMALL_CONFIG
12 #define JSON_INDENT_VALUE 2
14 typedef struct JsonWriter {
19 static void json_writer_init (JsonWriter* writer) MONO_INTERNAL;
20 static void json_writer_destroy (JsonWriter* writer);
21 static void json_writer_indent(JsonWriter* writer);
22 static void json_writer_indent_push(JsonWriter* writer);
23 static void json_writer_indent_pop(JsonWriter* writer);
24 static void json_writer_vprintf(JsonWriter* writer, const gchar *format, va_list args);
25 static void json_writer_printf(JsonWriter* writer, const gchar *format, ...);
26 static void json_writer_array_begin(JsonWriter* writer);
27 static void json_writer_array_end(JsonWriter* writer);
28 static void json_writer_object_begin(JsonWriter* writer);
29 static void json_writer_object_end(JsonWriter* writer);
30 static void json_writer_object_key(JsonWriter* writer, const gchar* format, ...);
32 static void json_writer_init (JsonWriter* writer)
34 g_assert (writer && "Expected a valid JSON writer instance");
36 writer->text = g_string_new ("");
40 static void json_writer_destroy (JsonWriter* writer)
42 g_assert (writer && "Expected a valid JSON writer instance");
43 g_string_free (writer->text, /*free_segment=*/TRUE);
46 static void json_writer_indent_push(JsonWriter* writer)
48 g_assert (writer && "Expected a valid JSON writer instance");
49 writer->indent += JSON_INDENT_VALUE;
52 static void json_writer_indent_pop(JsonWriter* writer)
54 g_assert (writer && "Expected a valid JSON writer instance");
55 writer->indent -= JSON_INDENT_VALUE;
58 static void json_writer_indent(JsonWriter* writer)
60 g_assert (writer && "Expected a valid JSON writer instance");
63 for (i = 0; i < writer->indent; ++i)
64 g_string_append_c (writer->text, ' ');
67 static void json_writer_vprintf(JsonWriter* writer, const gchar *format, va_list args)
69 g_assert (writer && "Expected a valid JSON writer instance");
70 g_string_append_vprintf (writer->text, format, args);
73 static void json_writer_printf(JsonWriter* writer, const gchar *format, ...)
75 g_assert (writer && "Expected a valid JSON writer instance");
78 va_start (args, format);
80 g_string_append_vprintf (writer->text, format, args);
85 static void json_writer_array_begin(JsonWriter* writer)
87 g_assert (writer && "Expected a valid JSON writer instance");
88 g_string_append_printf (writer->text, "[\n");
89 writer->indent += JSON_INDENT_VALUE;
92 static void json_writer_array_end(JsonWriter* writer)
94 g_assert (writer && "Expected a valid JSON writer instance");
95 g_string_append_printf (writer->text, "]");
96 writer->indent -= JSON_INDENT_VALUE;
99 static void json_writer_object_begin(JsonWriter* writer)
101 g_assert (writer && "Expected a valid JSON writer instance");
102 json_writer_printf (writer, "{\n");
103 writer->indent += JSON_INDENT_VALUE;
106 static void json_writer_object_end(JsonWriter* writer)
108 g_assert (writer && "Expected a valid JSON writer instance");
109 json_writer_printf (writer, "}");
112 static void json_writer_object_key(JsonWriter* writer, const gchar* format, ...)
114 g_assert (writer && "Expected a valid JSON writer instance");
117 va_start (args, format);
119 g_string_append_printf (writer->text, "\"");
120 json_writer_vprintf (writer, format, args);
121 g_string_append_printf (writer->text, "\" : ");
126 #define WRAPPER(e,n) n,
127 static const char* const
128 wrapper_type_names [MONO_WRAPPER_NUM + 1] = {
129 #include "mono/metadata/wrapper-types.h"
133 static G_GNUC_UNUSED const char*
134 get_wrapper_type_name (int type)
136 return wrapper_type_names [type];
142 static void aot_dump (MonoAotCompile *acfg)
148 json_writer_init (&writer);
150 json_writer_object_begin(&writer);
153 json_writer_indent (&writer);
154 json_writer_object_key(&writer, "methods");
155 json_writer_array_begin (&writer);
158 for (i = 0; i < acfg->nmethods; ++i) {
164 cfg = acfg->cfgs [i];
168 method = cfg->orig_method;
170 json_writer_indent (&writer);
171 json_writer_object_begin(&writer);
173 json_writer_indent (&writer);
174 json_writer_object_key(&writer, "name");
175 json_writer_printf (&writer, "\"%s\",\n", method->name);
177 json_writer_indent (&writer);
178 json_writer_object_key(&writer, "signature");
179 json_writer_printf (&writer, "\"%s\",\n", mono_method_full_name (method,
180 /*signature=*/TRUE));
182 json_writer_indent (&writer);
183 json_writer_object_key(&writer, "code_size");
184 json_writer_printf (&writer, "\"%d\",\n", cfg->code_size);
186 klass = method->klass;
188 json_writer_indent (&writer);
189 json_writer_object_key(&writer, "class");
190 json_writer_printf (&writer, "\"%s\",\n", klass->name);
192 json_writer_indent (&writer);
193 json_writer_object_key(&writer, "namespace");
194 json_writer_printf (&writer, "\"%s\",\n", klass->name_space);
196 json_writer_indent (&writer);
197 json_writer_object_key(&writer, "wrapper_type");
198 json_writer_printf (&writer, "\"%s\",\n", get_wrapper_type_name(method->wrapper_type));
200 json_writer_indent_pop (&writer);
201 json_writer_indent (&writer);
202 json_writer_object_end (&writer);
203 json_writer_printf (&writer, ",\n");
206 json_writer_indent_pop (&writer);
207 json_writer_indent (&writer);
208 json_writer_array_end (&writer);
209 json_writer_printf (&writer, ",\n");
213 json_writer_indent_push (&writer);
214 json_writer_indent (&writer);
215 json_writer_object_key(&writer, "plt");
216 json_writer_array_begin (&writer);
218 for (i = 0; i < acfg->plt_offset; ++i) {
219 MonoPltEntry *plt_entry = NULL;
224 * The first plt entry is unused.
228 plt_entry = g_hash_table_lookup (acfg->plt_offset_to_entry, GUINT_TO_POINTER (i));
231 json_writer_indent (&writer);
232 json_writer_printf (&writer, "{ ");
233 json_writer_object_key(&writer, "symbol");
234 json_writer_printf (&writer, "\"%s\" },\n", plt_entry->symbol);
237 json_writer_indent_pop (&writer);
238 json_writer_indent (&writer);
239 json_writer_array_end (&writer);
240 json_writer_printf (&writer, ",\n");
245 json_writer_indent_push (&writer);
246 json_writer_indent (&writer);
247 json_writer_object_key(&writer, "got");
248 json_writer_array_begin (&writer);
250 json_writer_indent_push (&writer);
251 for (i = 0; i < acfg->got_info.got_patches->len; ++i) {
252 MonoJumpInfo *ji = g_ptr_array_index (acfg->got_info.got_patches, i);
254 json_writer_indent (&writer);
255 json_writer_printf (&writer, "{ ");
256 json_writer_object_key(&writer, "patch_name");
257 json_writer_printf (&writer, "\"%s\" },\n", get_patch_name (ji->type));
260 json_writer_indent_pop (&writer);
261 json_writer_indent (&writer);
262 json_writer_array_end (&writer);
263 json_writer_printf (&writer, ",\n");
266 json_writer_indent_pop (&writer);
267 json_writer_indent (&writer);
268 json_writer_object_end (&writer);
270 dumpname = g_strdup_printf ("%s.json", g_path_get_basename (acfg->image->name));
271 dumpfile = fopen (dumpname, "w+");
274 fprintf (dumpfile, "%s", writer.text->str);
277 json_writer_destroy (&writer);
282 static void aot_dump (MonoAotCompile *acfg)