static int bbAdd(Sdb *db, ut64 from, ut64 to, ut64 jump, ut64 fail) { ut64 block_start = getCrossingBlock (db, "bbs", from, to); int add = 1; if (block_start == UT64_MAX) { // add = 1; } else if (block_start == from) { // check if size is the same, add = 0; } else { /* from = start address of new basic block to = end address of new basic block jump = destination basic block fail = fallback jump of basic block addr = previous closer basic block start address addr_end = previous closer basic block start address */ // found a possible block if (from > block_start) { // from inside // RESIZE this sdb_num_set (db, Fbb(block_start), from, 0); sdb_num_set (db, FbbTo(block_start), from, 0); sdb_array_set_num (db, FbbTo(block_start), 0, from, 0); sdb_array_set_num (db, FbbTo(block_start), 1, UT64_MAX, 0); } else { // < the current runs into a known block to = block_start; jump = block_start; fail = UT64_MAX; } } if (add) { sdb_array_add_num (db, "bbs", from, 0); sdb_num_set (db, Fbb(from), to, 0); sdb_array_set_num (db, FbbTo(from), 0, jump, 0); sdb_array_set_num (db, FbbTo(from), 1, fail, 0); sdb_num_min (db, "min", from, 0); sdb_num_max (db, "max", to, 0); } return 0; }
static int bbAdd (Sdb *db, ut64 from, ut64 to, ut64 jump, ut64 fail) { ut64 addr_end, addr = sdb_array_get_closer_num (db, "bbs", from); int add = 1; if (addr == UT64_MAX) { // add = 1; } else if (addr == from) { // check if size is the same, eprintf ("basic block already analyzed\n"); add = 0; } else { /* from = start address of new basic block to = end address of new basic block jump = destination basic block fail = fallback jump of basic block addr = previous closer basic block start address addr_end = previous closer basic block start address */ addr_end = sdb_num_get (db, Fbb(addr), NULL); if (addr_end) { if (from >= addr && from < addr_end) { eprintf ("OVERLAPS MUST SPLIT\n"); /* reduce current basic block to from */ eprintf ("Shrink basic block 0x%08"PFMT64x" to %d\n", addr, (int)(from-addr)); sdb_num_set (db, Fbb(addr), addr + from-addr, 0); sdb_num_set (db, FbbTo(addr), from, 0); //to = addr_end; // ??? } } } if (add) { sdb_array_add_num (db, "bbs", from, 0); sdb_num_set (db, Fbb(from), to, 0); if (jump != UT64_MAX) sdb_array_set_num (db, FbbTo(from), 0, jump, 0); if (fail != UT64_MAX) sdb_array_set_num (db, FbbTo(from), 1, fail, 0); sdb_num_min (db, "min", from, 0); sdb_num_max (db, "max", to, 0); } return 0; }
static ut64 getFunctionSize(Sdb *db) { ut64 min = UT64_MAX, max = 0; char *c, *bbs = sdb_get (db, "bbs", NULL); bool first = true; sdb_aforeach (c, bbs) { ut64 addr = sdb_atoi (c); ut64 addr_end = sdb_num_get (db, Fbb (addr), NULL); if (first) { min = addr; max = addr_end; first = false; } else { if (addr < min) { min = addr; } if (addr_end > max) { max = addr_end; } } sdb_aforeach_next (c); }
static ut64 getFunctionSize(Sdb *db) { #if 1 ut64 min = sdb_num_get (db, Fmin (addr), NULL); ut64 max = sdb_num_get (db, Fmax (addr), NULL); #else ut64 min, max; char *c, *bbs = sdb_get (db, "bbs", NULL); int first = 1; sdb_aforeach (c, bbs) { ut64 addr = sdb_atoi (c); ut64 addr_end = sdb_num_get (db, Fbb(addr), NULL); if (first) { min = addr; max = addr_end; first = 0; } else { if (addr<min) min = addr; if (addr_end>max) max = addr_end; } sdb_aforeach_next (c); }
static ut64 getCrossingBlock(Sdb *db, const char *key, ut64 start, ut64 end) { ut64 block_start, block_end; ut64 nearest_start = UT64_MAX; const char *s = sdb_const_get (db, key, NULL); const char *next = NULL; const char *ptr = NULL; if (!s) { return UT64_MAX; } ptr = s; do { const char *str = sdb_const_anext (ptr, &next); block_start = sdb_atoi (str); if (start == block_start) { // case 5 return start; } block_end = sdb_num_get (db, Fbb(block_start), NULL); if (block_end) { if (start > block_start && start < block_end) { // case 2 // start is inside the block return block_start; } if (start < block_start && end >= block_end) { // crossing the start of the block if (nearest_start > block_start) { nearest_start = block_start; } } } ptr = next; } while (next); return nearest_start; }