diff --git a/src/386_dynarec.c b/src/386_dynarec.c index eb727b0..8954538 100644 --- a/src/386_dynarec.c +++ b/src/386_dynarec.c @@ -651,7 +651,7 @@ void exec386_dynarec(int cycs) allow the first page to be interpreted and for the page fault to occur when the page boundary is actually crossed.*/ - uint32_t phys_addr_2 = get_phys_noabrt(block->endpc); + uint32_t phys_addr_2 = get_phys_noabrt(block->pc + 0x400); page_t *page_2 = &pages[phys_addr_2 >> 12]; if ((block->phys_2 ^ phys_addr_2) & ~0xfff) valid_block = 0; diff --git a/src/codegen.h b/src/codegen.h index f9d357c..72a3820 100644 --- a/src/codegen.h +++ b/src/codegen.h @@ -42,9 +42,13 @@ typedef struct codeblock_t uint32_t phys, phys_2; uint16_t status; uint16_t flags; - uint16_t ins; + uint8_t ins; uint8_t TOP; - uint32_t endpc; + + /*Pointers for codeblock tree, used to search for blocks when hash lookup + fails.*/ + uint16_t parent, left, right; + uint8_t *data; uint64_t page_mask, page_mask2; @@ -53,16 +57,16 @@ typedef struct codeblock_t /*Previous and next pointers, for the codeblock list associated with each physical page. Two sets of pointers, as a codeblock can be present in two pages.*/ - struct codeblock_t *prev, *next; - struct codeblock_t *prev_2, *next_2; - - /*Pointers for codeblock tree, used to search for blocks when hash lookup - fails.*/ - struct codeblock_t *parent, *left, *right; + uint16_t prev, next; + uint16_t prev_2, next_2; } codeblock_t; uint8_t *codeblock_data; +extern codeblock_t *codeblock; + +extern codeblock_t **codeblock_hash; + /*Code block uses FPU*/ #define CODEBLOCK_HAS_FPU 1 /*Code block is always entered with the same FPU top-of-stack*/ @@ -72,11 +76,22 @@ uint8_t *codeblock_data; #define BLOCK_PC_INVALID 0xffffffff +#define BLOCK_INVALID 0 + +static inline int get_block_nr(codeblock_t *block) +{ + return ((uintptr_t)block - (uintptr_t)codeblock) / sizeof(codeblock_t); +} + static inline codeblock_t *codeblock_tree_find(uint32_t phys, uint32_t _cs) { - codeblock_t *block = pages[phys >> 12].head; + codeblock_t *block; uint64_t a = _cs | ((uint64_t)phys << 32); + if (!pages[phys >> 12].head) + return NULL; + + block = &codeblock[pages[phys >> 12].head]; while (block) { uint64_t block_cmp = block->_cs | ((uint64_t)block->phys << 32); @@ -87,9 +102,9 @@ static inline codeblock_t *codeblock_tree_find(uint32_t phys, uint32_t _cs) break; } if (a < block_cmp) - block = block->left; + block = block->left ? &codeblock[block->left] : NULL; else - block = block->right; + block = block->right ? &codeblock[block->right] : NULL; } return block; @@ -97,18 +112,18 @@ static inline codeblock_t *codeblock_tree_find(uint32_t phys, uint32_t _cs) static inline void codeblock_tree_add(codeblock_t *new_block) { - codeblock_t *block = pages[new_block->phys >> 12].head; + codeblock_t *block = &codeblock[pages[new_block->phys >> 12].head]; uint64_t a = new_block->_cs | ((uint64_t)new_block->phys << 32); - if (!block) + if (!pages[new_block->phys >> 12].head) { - pages[new_block->phys >> 12].head = new_block; - new_block->parent = new_block->left = new_block->right = NULL; + pages[new_block->phys >> 12].head = get_block_nr(new_block); + new_block->parent = new_block->left = new_block->right = BLOCK_INVALID; } else { codeblock_t *old_block = NULL; - uint64_t old_block_cmp; + uint64_t old_block_cmp = 0; while (block) { @@ -116,58 +131,68 @@ static inline void codeblock_tree_add(codeblock_t *new_block) old_block_cmp = old_block->_cs | ((uint64_t)old_block->phys << 32); if (a < old_block_cmp) - block = block->left; + block = block->left ? &codeblock[block->left] : NULL; else - block = block->right; + block = block->right ? &codeblock[block->right] : NULL; } if (a < old_block_cmp) - old_block->left = new_block; + old_block->left = get_block_nr(new_block); else - old_block->right = new_block; + old_block->right = get_block_nr(new_block); - new_block->parent = old_block; - new_block->left = new_block->right = NULL; + new_block->parent = get_block_nr(old_block); + new_block->left = new_block->right = BLOCK_INVALID; } } static inline void codeblock_tree_delete(codeblock_t *block) { - codeblock_t *parent = block->parent; + uint16_t parent_nr = block->parent; + codeblock_t *parent; + + if (block->parent) + parent = &codeblock[block->parent]; + else + parent = NULL; if (!block->left && !block->right) { /*Easy case - remove from parent*/ if (!parent) - pages[block->phys >> 12].head = NULL; + pages[block->phys >> 12].head = BLOCK_INVALID; else { - if (parent->left == block) - parent->left = NULL; - if (parent->right == block) - parent->right = NULL; + uint16_t block_nr = get_block_nr(block); + + if (parent->left == block_nr) + parent->left = BLOCK_INVALID; + if (parent->right == block_nr) + parent->right = BLOCK_INVALID; } return; } else if (!block->left) { /*Only right node*/ - if (!parent) + if (!parent_nr) { pages[block->phys >> 12].head = block->right; - pages[block->phys >> 12].head->parent = NULL; + codeblock[pages[block->phys >> 12].head].parent = BLOCK_INVALID; } else { - if (parent->left == block) + uint16_t block_nr = get_block_nr(block); + + if (parent->left == block_nr) { parent->left = block->right; - parent->left->parent = parent; + codeblock[parent->left].parent = parent_nr; } - if (parent->right == block) + if (parent->right == block_nr) { parent->right = block->right; - parent->right->parent = parent; + codeblock[parent->right].parent = parent_nr; } } return; @@ -175,22 +200,24 @@ static inline void codeblock_tree_delete(codeblock_t *block) else if (!block->right) { /*Only left node*/ - if (!parent) + if (!parent_nr) { pages[block->phys >> 12].head = block->left; - pages[block->phys >> 12].head->parent = NULL; + codeblock[pages[block->phys >> 12].head].parent = BLOCK_INVALID; } else { - if (parent->left == block) + uint16_t block_nr = get_block_nr(block); + + if (parent->left == block_nr) { parent->left = block->left; - parent->left->parent = parent; + codeblock[parent->left].parent = parent_nr; } - if (parent->right == block) + if (parent->right == block_nr) { parent->right = block->left; - parent->right->parent = parent; + codeblock[parent->right].parent = parent_nr; } } return; @@ -198,50 +225,54 @@ static inline void codeblock_tree_delete(codeblock_t *block) else { /*Difficult case - node has two children. Walk right child to find lowest node*/ - codeblock_t *lowest = block->right, *highest; + codeblock_t *lowest = &codeblock[block->right], *highest; codeblock_t *old_parent; + uint16_t lowest_nr; while (lowest->left) - lowest = lowest->left; - - old_parent = lowest->parent; + lowest = &codeblock[lowest->left]; + lowest_nr = get_block_nr(lowest); + + old_parent = &codeblock[lowest->parent]; /*Replace deleted node with lowest node*/ - if (!parent) - pages[block->phys >> 12].head = lowest; + if (!parent_nr) + pages[block->phys >> 12].head = lowest_nr; else { - if (parent->left == block) - parent->left = lowest; - if (parent->right == block) - parent->right = lowest; + uint16_t block_nr = get_block_nr(block); + + if (parent->left == block_nr) + parent->left = lowest_nr; + if (parent->right == block_nr) + parent->right = lowest_nr; } - lowest->parent = parent; + lowest->parent = parent_nr; lowest->left = block->left; if (lowest->left) - lowest->left->parent = lowest; + codeblock[lowest->left].parent = lowest_nr; - old_parent->left = NULL; + old_parent->left = BLOCK_INVALID; - highest = lowest->right; - if (!highest) + highest = &codeblock[lowest->right]; + if (!lowest->right) { - if (lowest != block->right) + if (lowest_nr != block->right) { lowest->right = block->right; - block->right->parent = lowest; + codeblock[block->right].parent = lowest_nr; } return; } while (highest->right) - highest = highest->right; + highest = &codeblock[highest->right]; - if (block->right && block->right != lowest) + if (block->right && block->right != lowest_nr) { highest->right = block->right; - block->right->parent = highest; + codeblock[block->right].parent = get_block_nr(highest); } } } @@ -251,10 +282,6 @@ static inline void codeblock_tree_delete(codeblock_t *block) #define PAGE_MASK_MASK 63 #define PAGE_MASK_SHIFT 4 -extern codeblock_t *codeblock; - -extern codeblock_t **codeblock_hash; - void codegen_init(); void codegen_close(); void codegen_reset(); diff --git a/src/codegen_backend.c b/src/codegen_backend.c index a24b7a5..de292e3 100644 --- a/src/codegen_backend.c +++ b/src/codegen_backend.c @@ -122,43 +122,44 @@ void dump_block() static void add_to_block_list(codeblock_t *block) { - codeblock_t *block_prev = pages[block->phys >> 12].block[(block->phys >> 10) & 3]; + uint16_t block_prev_nr = pages[block->phys >> 12].block[(block->phys >> 10) & 3]; + uint16_t block_nr = get_block_nr(block); if (!block->page_mask) fatal("add_to_block_list - mask = 0\n"); - if (block_prev) + if (block_prev_nr) { - block->next = block_prev; - block_prev->prev = block; - pages[block->phys >> 12].block[(block->phys >> 10) & 3] = block; + block->next = block_prev_nr; + codeblock[block_prev_nr].prev = block_nr; + pages[block->phys >> 12].block[(block->phys >> 10) & 3] = block_nr; } else { - block->next = NULL; - pages[block->phys >> 12].block[(block->phys >> 10) & 3] = block; + block->next = BLOCK_INVALID; + pages[block->phys >> 12].block[(block->phys >> 10) & 3] = block_nr; } if (block->next) { - if (block->next->pc == BLOCK_PC_INVALID) - fatal("block->next->pc=BLOCK_PC_INVALID %p %p %x %x\n", (void *)block->next, (void *)codeblock, block_current, block_pos); + if (codeblock[block->next].pc == BLOCK_PC_INVALID) + fatal("block->next->pc=BLOCK_PC_INVALID %p %p %x %x\n", (void *)&codeblock[block->next], (void *)codeblock, block_current, block_pos); } if (block->page_mask2) { - block_prev = pages[block->phys_2 >> 12].block_2[(block->phys_2 >> 10) & 3]; + block_prev_nr = pages[block->phys_2 >> 12].block_2[(block->phys_2 >> 10) & 3]; - if (block_prev) + if (block_prev_nr) { - block->next_2 = block_prev; - block_prev->prev_2 = block; - pages[block->phys_2 >> 12].block_2[(block->phys_2 >> 10) & 3] = block; + block->next_2 = block_prev_nr; + codeblock[block_prev_nr].prev_2 = block_nr; + pages[block->phys_2 >> 12].block_2[(block->phys_2 >> 10) & 3] = block_nr; } else { - block->next_2 = NULL; - pages[block->phys_2 >> 12].block_2[(block->phys_2 >> 10) & 3] = block; + block->next_2 = BLOCK_INVALID; + pages[block->phys_2 >> 12].block_2[(block->phys_2 >> 10) & 3] = block_nr; } } } @@ -170,15 +171,15 @@ static void remove_from_block_list(codeblock_t *block, uint32_t pc) if (block->prev) { - block->prev->next = block->next; + codeblock[block->prev].next = block->next; if (block->next) - block->next->prev = block->prev; + codeblock[block->next].prev = block->prev; } else { pages[block->phys >> 12].block[(block->phys >> 10) & 3] = block->next; if (block->next) - block->next->prev = NULL; + codeblock[block->next].prev = BLOCK_INVALID; else mem_flush_write_page(block->phys, 0); } @@ -191,16 +192,16 @@ static void remove_from_block_list(codeblock_t *block, uint32_t pc) if (block->prev_2) { - block->prev_2->next_2 = block->next_2; + codeblock[block->prev_2].next_2 = block->next_2; if (block->next_2) - block->next_2->prev_2 = block->prev_2; + codeblock[block->next_2].prev_2 = block->prev_2; } else { // pclog(" pages.block_2=%p 3 %p %p\n", (void *)block->next_2, (void *)block, (void *)pages[block->phys_2 >> 12].block_2); pages[block->phys_2 >> 12].block_2[(block->phys_2 >> 10) & 3] = block->next_2; if (block->next_2) - block->next_2->prev_2 = NULL; + codeblock[block->next_2].prev_2 = BLOCK_INVALID; else mem_flush_write_page(block->phys_2, 0); } @@ -223,32 +224,36 @@ static void delete_block(codeblock_t *block) void codegen_check_flush(page_t *page, uint64_t mask, uint32_t phys_addr) { - struct codeblock_t *block = page->block[(phys_addr >> 10) & 3]; + uint16_t block_nr = page->block[(phys_addr >> 10) & 3]; - while (block) + while (block_nr) { + codeblock_t *block = &codeblock[block_nr]; + if (mask & block->page_mask) { delete_block(block); cpu_recomp_evicted++; } - if (block == block->next) + if (block == &codeblock[block->next]) fatal("Broken 1\n"); - block = block->next; + block_nr = block->next; } - block = page->block_2[(phys_addr >> 10) & 3]; + block_nr = page->block_2[(phys_addr >> 10) & 3]; - while (block) + while (block_nr) { + codeblock_t *block = &codeblock[block_nr]; + if (mask & block->page_mask2) { delete_block(block); cpu_recomp_evicted++; } - if (block == block->next_2) + if (block == &codeblock[block->next_2]) fatal("Broken 2\n"); - block = block->next_2; + block_nr = block->next_2; } } @@ -261,6 +266,8 @@ void codegen_block_init(uint32_t phys_addr) mem_flush_write_page(phys_addr, cs+cpu_state.pc); block_current = (block_current + 1) & BLOCK_MASK; + if (!block_current) + block_current++; block = &codeblock[block_current]; // if (block->pc == 0xb00b4ff5) @@ -280,8 +287,8 @@ void codegen_block_init(uint32_t phys_addr) block->phys = phys_addr; block->dirty_mask = &page->dirty_mask[(phys_addr >> PAGE_MASK_INDEX_SHIFT) & PAGE_MASK_INDEX_MASK]; block->dirty_mask2 = NULL; - block->next = block->prev = NULL; - block->next_2 = block->prev_2 = NULL; + block->next = block->prev = BLOCK_INVALID; + block->next_2 = block->prev_2 = BLOCK_INVALID; block->page_mask = 0; block->flags = CODEBLOCK_STATIC_TOP; block->status = cpu_cur_status; @@ -298,11 +305,6 @@ ir_data_t *codegen_get_ir_data() return ir_data; } -static int get_block_nr(codeblock_t *block) -{ - return ((uintptr_t)block - (uintptr_t)codeblock) / sizeof(codeblock_t); -} - void codegen_block_start_recompile(codeblock_t *block) { page_t *page = &pages[block->phys >> 12]; @@ -372,14 +374,12 @@ void codegen_block_generate_end_mask() uint32_t start_pc; uint32_t end_pc; - block->endpc = codegen_endpc; - block->page_mask = 0; start_pc = (block->pc & 0x3ff) & ~15; - if ((block->pc ^ block->endpc) & ~0x3ff) + if ((block->pc ^ codegen_endpc) & ~0x3ff) end_pc = 0x3ff & ~15; else - end_pc = (block->endpc & 0x3ff) & ~15; + end_pc = (codegen_endpc & 0x3ff) & ~15; if (end_pc < start_pc) end_pc = 0x3ff; start_pc >>= PAGE_MASK_SHIFT; @@ -396,37 +396,37 @@ void codegen_block_generate_end_mask() block->phys_2 = -1; block->page_mask2 = 0; - block->next_2 = block->prev_2 = NULL; - if ((block->pc ^ block->endpc) & ~0x3ff) + block->next_2 = block->prev_2 = BLOCK_INVALID; + if ((block->pc ^ codegen_endpc) & ~0x3ff) { - block->phys_2 = get_phys_noabrt(block->endpc); + block->phys_2 = get_phys_noabrt(codegen_endpc); if (block->phys_2 != -1) { page_t *page_2 = &pages[block->phys_2 >> 12]; start_pc = 0; - end_pc = (block->endpc & 0x3ff) >> PAGE_MASK_SHIFT; + end_pc = (codegen_endpc & 0x3ff) >> PAGE_MASK_SHIFT; for (; start_pc <= end_pc; start_pc++) block->page_mask2 |= ((uint64_t)1 << start_pc); page_2->code_present_mask[(block->phys_2 >> 10) & 3] |= block->page_mask2; if (!pages[block->phys_2 >> 12].block_2[(block->phys_2 >> 10) & 3]) - mem_flush_write_page(block->phys_2, block->endpc); + mem_flush_write_page(block->phys_2, codegen_endpc); if (!block->page_mask2) fatal("!page_mask2\n"); if (block->next_2) { // pclog(" next_2->pc=%08x\n", block->next_2->pc); - if (block->next_2->pc == BLOCK_PC_INVALID) - fatal("block->next_2->pc=BLOCK_PC_INVALID %p\n", (void *)block->next_2); + if (codeblock[block->next_2].pc == BLOCK_PC_INVALID) + fatal("block->next_2->pc=BLOCK_PC_INVALID %p\n", (void *)&codeblock[block->next_2]); } block->dirty_mask2 = &page_2->dirty_mask[(block->phys_2 >> PAGE_MASK_INDEX_SHIFT) & PAGE_MASK_INDEX_MASK]; } } -// pclog("block_end: %08x %08x %016llx\n", block->pc, block->endpc, block->page_mask); +// pclog("block_end: %08x %08x %016llx\n", block->pc, codegen_endpc, block->page_mask); recomp_page = -1; } @@ -443,8 +443,8 @@ void codegen_block_end_recompile(codeblock_t *block) codegen_timing_block_end(); remove_from_block_list(block, block->pc); - block->next = block->prev = NULL; - block->next_2 = block->prev_2 = NULL; + block->next = block->prev = BLOCK_INVALID; + block->next_2 = block->prev_2 = BLOCK_INVALID; codegen_block_generate_end_mask(); add_to_block_list(block); // pclog("End block %i\n", block_num); diff --git a/src/codegen_backend_arm.c b/src/codegen_backend_arm.c index 00c2a17..d2b0fe4 100644 --- a/src/codegen_backend_arm.c +++ b/src/codegen_backend_arm.c @@ -294,19 +294,19 @@ void codegen_backend_init() #endif #if defined WIN32 || defined _WIN32 || defined _WIN32 - codeblock_data = VirtualAlloc(NULL, (BLOCK_SIZE+1) * BLOCK_DATA_SIZE, MEM_COMMIT, PAGE_EXECUTE_READWRITE); + codeblock_data = VirtualAlloc(NULL, BLOCK_SIZE * BLOCK_DATA_SIZE, MEM_COMMIT, PAGE_EXECUTE_READWRITE); #else - codeblock_data = malloc((BLOCK_SIZE+1) * BLOCK_DATA_SIZE); + codeblock_data = malloc(BLOCK_SIZE * BLOCK_DATA_SIZE); #endif if (!codeblock_data) fatal("codeblock_data failed to alloc - %i\n", (BLOCK_SIZE+1) * BLOCK_DATA_SIZE); - codeblock = malloc((BLOCK_SIZE+1) * sizeof(codeblock_t)); + codeblock = malloc(BLOCK_SIZE * sizeof(codeblock_t)); codeblock_hash = malloc(HASH_SIZE * sizeof(codeblock_t *)); - memset(codeblock, 0, (BLOCK_SIZE+1) * sizeof(codeblock_t)); + memset(codeblock, 0, BLOCK_SIZE * sizeof(codeblock_t)); memset(codeblock_hash, 0, HASH_SIZE * sizeof(codeblock_t *)); - for (c = 0; c < BLOCK_SIZE+1; c++) + for (c = 0; c < BLOCK_SIZE; c++) { codeblock[c].pc = BLOCK_PC_INVALID; codeblock[c].data = &codeblock_data[c * BLOCK_DATA_SIZE]; @@ -314,7 +314,7 @@ void codegen_backend_init() #if defined(__linux__) || defined(__APPLE__) start = (void *)((long)codeblock_data & pagemask); - len = (((BLOCK_SIZE+1) * BLOCK_DATA_SIZE) + pagesize) & pagemask; + len = ((BLOCK_SIZE * BLOCK_DATA_SIZE) + pagesize) & pagemask; if (mprotect(start, len, PROT_READ | PROT_WRITE | PROT_EXEC) != 0) { perror("mprotect"); @@ -323,7 +323,7 @@ void codegen_backend_init() #endif // pclog("Codegen is %p\n", (void *)pages[0xfab12 >> 12].block); - block_current = BLOCK_SIZE; + block_current = 0; block_pos = 0; build_loadstore_routines(&codeblock[block_current]); diff --git a/src/codegen_backend_arm64.c b/src/codegen_backend_arm64.c index 839f37e..534df5c 100644 --- a/src/codegen_backend_arm64.c +++ b/src/codegen_backend_arm64.c @@ -289,19 +289,19 @@ void codegen_backend_init() #endif #if defined WIN32 || defined _WIN32 || defined _WIN32 - codeblock_data = VirtualAlloc(NULL, (BLOCK_SIZE+1) * BLOCK_DATA_SIZE, MEM_COMMIT, PAGE_EXECUTE_READWRITE); + codeblock_data = VirtualAlloc(NULL, BLOCK_SIZE * BLOCK_DATA_SIZE, MEM_COMMIT, PAGE_EXECUTE_READWRITE); #else - codeblock_data = malloc((BLOCK_SIZE+1) * BLOCK_DATA_SIZE); + codeblock_data = malloc(BLOCK_SIZE * BLOCK_DATA_SIZE); #endif if (!codeblock_data) fatal("codeblock_data failed to alloc - %i\n", (BLOCK_SIZE+1) * BLOCK_DATA_SIZE); - codeblock = malloc((BLOCK_SIZE+1) * sizeof(codeblock_t)); + codeblock = malloc(BLOCK_SIZE * sizeof(codeblock_t)); codeblock_hash = malloc(HASH_SIZE * sizeof(codeblock_t *)); - memset(codeblock, 0, (BLOCK_SIZE+1) * sizeof(codeblock_t)); + memset(codeblock, 0, BLOCK_SIZE * sizeof(codeblock_t)); memset(codeblock_hash, 0, HASH_SIZE * sizeof(codeblock_t *)); - for (c = 0; c < BLOCK_SIZE+1; c++) + for (c = 0; c < BLOCK_SIZE; c++) { codeblock[c].pc = BLOCK_PC_INVALID; codeblock[c].data = &codeblock_data[c * BLOCK_SIZE]; @@ -309,7 +309,7 @@ void codegen_backend_init() #if defined(__linux__) || defined(__APPLE__) start = (void *)((long)codeblock_data & pagemask); - len = (((BLOCK_SIZE+1) * BLOCK_DATA_SIZE) + pagesize) & pagemask; + len = ((BLOCK_SIZE * BLOCK_DATA_SIZE) + pagesize) & pagemask; if (mprotect(start, len, PROT_READ | PROT_WRITE | PROT_EXEC) != 0) { perror("mprotect"); @@ -318,7 +318,7 @@ void codegen_backend_init() #endif // pclog("Codegen is %p\n", (void *)pages[0xfab12 >> 12].block); - block_current = BLOCK_SIZE; + block_current = 0; block_pos = 0; codegen_reset_literal_pool(&codeblock[block_current]); build_loadstore_routines(&codeblock[block_current]); diff --git a/src/codegen_backend_x86-64.c b/src/codegen_backend_x86-64.c index c509c04..631402a 100644 --- a/src/codegen_backend_x86-64.c +++ b/src/codegen_backend_x86-64.c @@ -276,17 +276,17 @@ void codegen_backend_init() #endif #if defined WIN32 || defined _WIN32 || defined _WIN32 - codeblock_data = VirtualAlloc(NULL, (BLOCK_SIZE+1) * BLOCK_DATA_SIZE, MEM_COMMIT, PAGE_EXECUTE_READWRITE); + codeblock_data = VirtualAlloc(NULL, BLOCK_SIZE * BLOCK_DATA_SIZE, MEM_COMMIT, PAGE_EXECUTE_READWRITE); #else - codeblock_data = malloc((BLOCK_SIZE+1) * BLOCK_DATA_SIZE); + codeblock_data = malloc(BLOCK_SIZE * BLOCK_DATA_SIZE); #endif - codeblock = malloc((BLOCK_SIZE+1) * sizeof(codeblock_t)); + codeblock = malloc(BLOCK_SIZE * sizeof(codeblock_t)); codeblock_hash = malloc(HASH_SIZE * sizeof(codeblock_t *)); - memset(codeblock, 0, (BLOCK_SIZE+1) * sizeof(codeblock_t)); + memset(codeblock, 0, BLOCK_SIZE * sizeof(codeblock_t)); memset(codeblock_hash, 0, HASH_SIZE * sizeof(codeblock_t *)); - for (c = 0; c < BLOCK_SIZE+1; c++) + for (c = 0; c < BLOCK_SIZE; c++) { codeblock[c].data = &codeblock_data[c * BLOCK_DATA_SIZE]; codeblock[c].pc = BLOCK_PC_INVALID; @@ -294,7 +294,7 @@ void codegen_backend_init() #if defined(__linux__) || defined(__APPLE__) start = (void *)((long)codeblock & pagemask); - len = (((BLOCK_SIZE+1) * sizeof(codeblock_t)) + pagesize) & pagemask; + len = ((BLOCK_SIZE * sizeof(codeblock_t)) + pagesize) & pagemask; if (mprotect(start, len, PROT_READ | PROT_WRITE | PROT_EXEC) != 0) { perror("mprotect"); @@ -303,7 +303,7 @@ void codegen_backend_init() #endif // pclog("Codegen is %p\n", (void *)pages[0xfab12 >> 12].block); - block_current = BLOCK_SIZE; + block_current = 0; block_pos = 0; build_loadstore_routines(&codeblock[block_current]); // fatal("Here\n"); diff --git a/src/codegen_backend_x86.c b/src/codegen_backend_x86.c index 0fd6104..4a43ff0 100644 --- a/src/codegen_backend_x86.c +++ b/src/codegen_backend_x86.c @@ -270,31 +270,30 @@ pclog(" offsetof(codeblock_t, status)=%i\n", offsetof(codeblock_t, status)); pclog(" offsetof(codeblock_t, flags)=%i\n", offsetof(codeblock_t, flags)); pclog(" offsetof(codeblock_t, ins)=%i\n", offsetof(codeblock_t, ins)); pclog(" offsetof(codeblock_t, TOP)=%i\n", offsetof(codeblock_t, TOP)); -pclog(" offsetof(codeblock_t, endpc)=%i\n", offsetof(codeblock_t, endpc)); +pclog(" offsetof(codeblock_t, parent)=%i\n", offsetof(codeblock_t, parent)); +pclog(" offsetof(codeblock_t, left)=%i\n", offsetof(codeblock_t, left)); +pclog(" offsetof(codeblock_t, right)=%i\n", offsetof(codeblock_t, right)); pclog(" offsetof(codeblock_t, data)=%i\n", offsetof(codeblock_t, data)); -pclog(" offsetof(codeblock_t, page_mask=%i\n", offsetof(codeblock_t, page_mask)); -pclog(" offsetof(codeblock_t, page_mask2=%i\n", offsetof(codeblock_t, page_mask2)); -pclog(" offsetof(codeblock_t, dirty_mask=%i\n", offsetof(codeblock_t, dirty_mask)); -pclog(" offsetof(codeblock_t, dirty_mask2=%i\n", offsetof(codeblock_t, dirty_mask2)); -pclog(" offsetof(codeblock_t, prev=%i\n", offsetof(codeblock_t, prev)); -pclog(" offsetof(codeblock_t, next=%i\n", offsetof(codeblock_t, next)); -pclog(" offsetof(codeblock_t, prev_2=%i\n", offsetof(codeblock_t, prev_2)); -pclog(" offsetof(codeblock_t, next_2=%i\n", offsetof(codeblock_t, next_2)); -pclog(" offsetof(codeblock_t, parent=%i\n", offsetof(codeblock_t, parent)); -pclog(" offsetof(codeblock_t, left=%i\n", offsetof(codeblock_t, left)); -pclog(" offsetof(codeblock_t, right=%i\n", offsetof(codeblock_t, right)); - codeblock = malloc((BLOCK_SIZE+1) * sizeof(codeblock_t)); +pclog(" offsetof(codeblock_t, page_mask)=%i\n", offsetof(codeblock_t, page_mask)); +pclog(" offsetof(codeblock_t, page_mask2)=%i\n", offsetof(codeblock_t, page_mask2)); +pclog(" offsetof(codeblock_t, dirty_mask)=%i\n", offsetof(codeblock_t, dirty_mask)); +pclog(" offsetof(codeblock_t, dirty_mask2)=%i\n", offsetof(codeblock_t, dirty_mask2)); +pclog(" offsetof(codeblock_t, prev)=%i\n", offsetof(codeblock_t, prev)); +pclog(" offsetof(codeblock_t, next)=%i\n", offsetof(codeblock_t, next)); +pclog(" offsetof(codeblock_t, prev_2)=%i\n", offsetof(codeblock_t, prev_2)); +pclog(" offsetof(codeblock_t, next_2)=%i\n", offsetof(codeblock_t, next_2)); + codeblock = malloc(BLOCK_SIZE * sizeof(codeblock_t)); #if defined WIN32 || defined _WIN32 || defined _WIN32 - codeblock_data = VirtualAlloc(NULL, (BLOCK_SIZE+1) * BLOCK_DATA_SIZE, MEM_COMMIT, PAGE_EXECUTE_READWRITE); + codeblock_data = VirtualAlloc(NULL, BLOCK_SIZE * BLOCK_DATA_SIZE, MEM_COMMIT, PAGE_EXECUTE_READWRITE); #else - codeblock_data = malloc((BLOCK_SIZE+1) * BLOCK_DATA_SIZE; + codeblock_data = malloc(BLOCK_SIZE * BLOCK_DATA_SIZE; #endif codeblock_hash = malloc(HASH_SIZE * sizeof(codeblock_t *)); - memset(codeblock, 0, (BLOCK_SIZE+1) * sizeof(codeblock_t)); + memset(codeblock, 0, BLOCK_SIZE * sizeof(codeblock_t)); memset(codeblock_hash, 0, HASH_SIZE * sizeof(codeblock_t *)); - for (c = 0; c < BLOCK_SIZE + 1; c++) + for (c = 0; c < BLOCK_SIZE; c++) { codeblock[c].data = &codeblock_data[c * BLOCK_DATA_SIZE]; codeblock[c].pc = BLOCK_PC_INVALID; @@ -302,7 +301,7 @@ pclog(" offsetof(codeblock_t, right=%i\n", offsetof(codeblock_t, right)); #if defined(__linux__) || defined(__APPLE__) start = (void *)((long)codeblock_data & pagemask); - len = (((BLOCK_SIZE+1) * BLOCK_DATA_SIZE) + pagesize) & pagemask; + len = ((BLOCK_SIZE * BLOCK_DATA_SIZE) + pagesize) & pagemask; if (mprotect(start, len, PROT_READ | PROT_WRITE | PROT_EXEC) != 0) { perror("mprotect"); @@ -311,7 +310,7 @@ pclog(" offsetof(codeblock_t, right=%i\n", offsetof(codeblock_t, right)); #endif // pclog("Codegen is %p\n", (void *)pages[0xfab12 >> 12].block); - block_current = BLOCK_SIZE; + block_current = 0; block_pos = 0; mem_abrt_rout = &codeblock[block_current].data[block_pos]; addbyte(0x83); /*ADDL $16+4,%esp*/ diff --git a/src/mem.c b/src/mem.c index 6fa3a69..ad095a3 100644 --- a/src/mem.c +++ b/src/mem.c @@ -1499,8 +1499,8 @@ void mem_reset_page_blocks() pages[c].write_b = mem_write_ramb_page; pages[c].write_w = mem_write_ramw_page; pages[c].write_l = mem_write_raml_page; - pages[c].block[0] = pages[c].block[1] = pages[c].block[2] = pages[c].block[3] = NULL; - pages[c].block_2[0] = pages[c].block_2[1] = pages[c].block_2[2] = pages[c].block_2[3] = NULL; + pages[c].block[0] = pages[c].block[1] = pages[c].block[2] = pages[c].block[3] = BLOCK_INVALID; + pages[c].block_2[0] = pages[c].block_2[1] = pages[c].block_2[2] = pages[c].block_2[3] = BLOCK_INVALID; } } diff --git a/src/mem.h b/src/mem.h index 2aabde9..a015acc 100644 --- a/src/mem.h +++ b/src/mem.h @@ -119,10 +119,10 @@ typedef struct page_t uint8_t *mem; - struct codeblock_t *block[4], *block_2[4]; + uint16_t block[4], block_2[4]; /*Head of codeblock tree associated with this page*/ - struct codeblock_t *head; + uint16_t head; uint64_t code_present_mask[4], dirty_mask[4]; } page_t;