/* Dump a spesh graph into string form, for debugging purposes. */ char * MVM_spesh_dump(MVMThreadContext *tc, MVMSpeshGraph *g) { MVMSpeshBB *cur_bb; /* Allocate buffer. */ DumpStr ds; ds.alloc = 8192; ds.buffer = MVM_malloc(ds.alloc); ds.pos = 0; /* Dump name and CUID. */ append(&ds, "Spesh of '"); append_str(tc, &ds, g->sf->body.name); append(&ds, "' (cuid: "); append_str(tc, &ds, g->sf->body.cuuid); append(&ds, ", file: "); dump_fileinfo(tc, &ds, g); append(&ds, ")\n"); if (g->cs) dump_callsite(tc, &ds, g); if (g->num_arg_guards) dump_arg_guards(tc, &ds, g); if (!g->cs && !g->num_arg_guards) append(&ds, "\n"); /* Go over all the basic blocks and dump them. */ cur_bb = g->entry; while (cur_bb) { dump_bb(tc, &ds, g, cur_bb); cur_bb = cur_bb->linear_next; } /* Dump facts. */ append(&ds, "\nFacts:\n"); dump_facts(tc, &ds, g); if (g->num_spesh_slots || g->num_log_slots) { append(&ds, "\nStats:\n"); appendf(&ds, " %d spesh slots\n", g->num_spesh_slots); appendf(&ds, " %d log slots\n", g->num_log_slots); } if (g->num_log_slots) { dump_log_values(tc, &ds, g); } append(&ds, "\n"); append_null(&ds); return ds.buffer; }
/* Dump a spesh graph into string form, for debugging purposes. */ char * MVM_spesh_dump(MVMThreadContext *tc, MVMSpeshGraph *g) { MVMSpeshBB *cur_bb; SpeshGraphSizeStats stats; InlineIndexStack inline_stack; DumpStr ds; stats.total_size = 0; stats.inlined_size = 0; inline_stack.cur_depth = -1; /* Allocate buffer. */ ds.alloc = 8192; ds.buffer = MVM_malloc(ds.alloc); ds.pos = 0; /* Dump name and CUID. */ append(&ds, "Spesh of '"); append_str(tc, &ds, g->sf->body.name); append(&ds, "' (cuid: "); append_str(tc, &ds, g->sf->body.cuuid); append(&ds, ", file: "); dump_fileinfo(tc, &ds, g->sf); append(&ds, ")\n"); if (g->cs) dump_callsite(tc, &ds, g->cs); if (!g->cs) append(&ds, "\n"); /* Go over all the basic blocks and dump them. */ cur_bb = g->entry; while (cur_bb) { dump_bb(tc, &ds, g, cur_bb, &stats, &inline_stack); cur_bb = cur_bb->linear_next; } /* Dump facts. */ if (g->facts) { append(&ds, "\nFacts:\n"); dump_facts(tc, &ds, g); } /* Dump spesh slots. */ if (g->num_spesh_slots) { MVMuint32 i; append(&ds, "\nSpesh slots:\n"); for (i = 0; i < g->num_spesh_slots; i++) { MVMCollectable *value = g->spesh_slots[i]; if (value == NULL) appendf(&ds, " %d = NULL\n", i); else if (value->flags & MVM_CF_STABLE) appendf(&ds, " %d = STable (%s)\n", i, MVM_6model_get_stable_debug_name(tc, (MVMSTable *)value)); else if (value->flags & MVM_CF_TYPE_OBJECT) appendf(&ds, " %d = Type Object (%s)\n", i, MVM_6model_get_debug_name(tc, (MVMObject *)value)); else { MVMObject *obj = (MVMObject *)value; MVMuint32 repr_id = REPR(obj)->ID; appendf(&ds, " %d = Instance (%s)", i, MVM_6model_get_debug_name(tc, obj)); if (repr_id == MVM_REPR_ID_MVMStaticFrame || repr_id == MVM_REPR_ID_MVMCode) { MVMStaticFrameBody *body; char *name_str; char *cuuid_str; if (repr_id == MVM_REPR_ID_MVMCode) { MVMCodeBody *code_body = (MVMCodeBody *)OBJECT_BODY(obj); obj = (MVMObject *)code_body->sf; } body = (MVMStaticFrameBody *)OBJECT_BODY(obj); name_str = MVM_string_utf8_encode_C_string(tc, body->name); cuuid_str = MVM_string_utf8_encode_C_string(tc, body->cuuid); appendf(&ds, " - '%s' (%s)", name_str, cuuid_str); MVM_free(name_str); MVM_free(cuuid_str); } appendf(&ds, "\n"); } } } /* Dump materialization deopt into. */ dump_deopt_pea(tc, &ds, g); append(&ds, "\n"); /* Print out frame size */ if (stats.inlined_size) appendf(&ds, "Frame size: %u bytes (%u from inlined frames)\n", stats.total_size, stats.inlined_size); else appendf(&ds, "Frame size: %u bytes\n", stats.total_size); append_null(&ds); return ds.buffer; }