ACPI AML decompiler w/ CFG recovery and structured pseudocode
29

Configure Feed

Select the types of activity you want to include in your feed.

Add stable IR node identifiers and parent indexes for deterministic cross references

+59
+1
src/cf.c
··· 61 61 62 62 int tobi_cf_recover(tobi_ir *root, tobi_diag_list *diag) { 63 63 walk(root, diag, 0); 64 + tobi_ir_assign_ids(root); 64 65 return !tobi_diag_has_error(diag); 65 66 } 66 67
+34
src/ir.c
··· 3 3 #include "mem.h" 4 4 5 5 #include <stdlib.h> 6 + #include <stdint.h> 6 7 7 8 tobi_ir *tobi_ir_new(tobi_ir_kind kind, size_t off, size_t len) { 8 9 tobi_ir *n = tobi_xcalloc(1, sizeof(*n)); 9 10 n->kind = kind; 10 11 n->off = off; 11 12 n->len = len; 13 + n->parent_index = SIZE_MAX; 12 14 return n; 13 15 } 14 16 ··· 35 37 parent->child_cap = parent->child_cap ? parent->child_cap * 2 : 4; 36 38 parent->child = tobi_xrealloc(parent->child, parent->child_cap * sizeof(parent->child[0])); 37 39 } 40 + child->parent_id = parent->id; 41 + child->parent_index = parent->child_len; 38 42 parent->child[parent->child_len++] = child; 43 + } 44 + 45 + void tobi_ir_assign_ids(tobi_ir *root) { 46 + if (!root) { 47 + return; 48 + } 49 + typedef struct frame { 50 + tobi_ir *node; 51 + size_t parent_id; 52 + size_t parent_index; 53 + } frame; 54 + size_t cap = 64; 55 + size_t len = 0; 56 + frame *stack = tobi_xcalloc(cap, sizeof(stack[0])); 57 + stack[len++] = (frame){root, 0, SIZE_MAX}; 58 + size_t next_id = 1; 59 + while (len > 0) { 60 + frame cur = stack[--len]; 61 + cur.node->id = next_id++; 62 + cur.node->parent_id = cur.parent_id; 63 + cur.node->parent_index = cur.parent_index; 64 + for (size_t i = cur.node->child_len; i > 0; i--) { 65 + if (len == cap) { 66 + cap *= 2u; 67 + stack = tobi_xrealloc(stack, cap * sizeof(stack[0])); 68 + } 69 + stack[len++] = (frame){cur.node->child[i - 1u], cur.node->id, i - 1u}; 70 + } 71 + } 72 + free(stack); 39 73 } 40 74 41 75 void tobi_ir_set_name(tobi_ir *node, const char *s) {
+5
src/ir.h
··· 38 38 39 39 typedef struct tobi_ir { 40 40 tobi_ir_kind kind; 41 + size_t id; 42 + size_t parent_id; 43 + size_t parent_index; 41 44 size_t off; 42 45 size_t len; 43 46 char *name; ··· 64 67 void tobi_ir_free(tobi_ir *node); 65 68 66 69 void tobi_ir_add(tobi_ir *parent, tobi_ir *child); 70 + 71 + void tobi_ir_assign_ids(tobi_ir *root); 67 72 68 73 void tobi_ir_set_name(tobi_ir *node, const char *s); 69 74
+8
src/js.c
··· 17 17 tobi_sb_add(sb, "\"kind\":"); 18 18 tobi_json_string(sb, tobi_ir_kind_name(n->kind)); 19 19 comma(sb, &first); 20 + tobi_sb_printf(sb, "\"id\":%zu", n->id); 21 + if (n->parent_id != 0) { 22 + comma(sb, &first); 23 + tobi_sb_printf(sb, "\"parent_id\":%zu", n->parent_id); 24 + comma(sb, &first); 25 + tobi_sb_printf(sb, "\"parent_index\":%zu", n->parent_index); 26 + } 27 + comma(sb, &first); 20 28 tobi_sb_printf(sb, "\"offset\":%zu", n->off); 21 29 comma(sb, &first); 22 30 tobi_sb_printf(sb, "\"length\":%zu", n->len);
+2
src/p.c
··· 1959 1959 (void)parse_term_list(&p, &rd, out->root, 0); 1960 1960 } 1961 1961 semantic_validate(&p, out->root); 1962 + tobi_ir_assign_ids(out->root); 1962 1963 parser_free(&p); 1963 1964 return !(strict && tobi_diag_has_error(&out->diag)); 1964 1965 } ··· 2009 2010 } 2010 2011 } 2011 2012 semantic_validate(&p, out->root); 2013 + tobi_ir_assign_ids(out->root); 2012 2014 parser_free(&p); 2013 2015 free(metas); 2014 2016 return ok && !(strict && tobi_diag_has_error(&out->diag));
+9
test/t_ir.c
··· 8 8 tobi_ir_set_name(m, "MTH0"); 9 9 tobi_ir_add(root, m); 10 10 tobi_ir_add(m, tobi_ir_new(TOBI_IR_BLOCK, 7, 3)); 11 + tobi_ir_assign_ids(root); 11 12 T_CHECK(root->kind == TOBI_IR_ROOT); 13 + T_CHECK(root->id == 1 && root->parent_id == 0); 12 14 T_CHECK(root->child_len == 1); 13 15 T_CHECK(root->child[0]->off == 2 && root->child[0]->len == 8); 16 + T_CHECK(root->child[0]->id == 2 && root->child[0]->parent_id == root->id); 17 + T_CHECK(root->child[0]->parent_index == 0); 18 + T_CHECK(m->child[0]->id == 3 && m->child[0]->parent_id == m->id); 14 19 T_CHECK(tobi_ir_find_child(root, TOBI_IR_METHOD) == m); 15 20 T_CHECK(tobi_ir_count_kind(root, TOBI_IR_METHOD) == 1); 16 21 tobi_ir *u = tobi_ir_new(TOBI_IR_UNKNOWN, 4, 1); 17 22 u->raw_op = 0xfe; 18 23 tobi_ir_add(m->child[0], u); 24 + tobi_ir_assign_ids(root); 19 25 T_CHECK(m->child[0]->child[0]->raw_op == 0xfe); 26 + T_CHECK(m->child[0]->child[0]->id == 4); 27 + T_CHECK(m->child[0]->child[0]->parent_id == m->child[0]->id); 28 + T_CHECK(m->child[0]->child[0]->parent_index == 0); 20 29 tobi_ir_free(root); 21 30 return 0; 22 31 }