mirror of
https://github.com/86Box/86Box.git
synced 2026-02-25 04:45:31 -07:00
More newline and whitespace cleanups
This commit is contained in:
@@ -31,7 +31,7 @@ static struct
|
||||
int codegen_get_instruction_uop(codeblock_t *block, uint32_t pc, int *first_instruction, int *TOP)
|
||||
{
|
||||
int c;
|
||||
|
||||
|
||||
for (c = 0; c <= block->ins; c++)
|
||||
{
|
||||
if (codegen_instructions[c].pc == pc)
|
||||
@@ -41,7 +41,7 @@ int codegen_get_instruction_uop(codeblock_t *block, uint32_t pc, int *first_inst
|
||||
return codegen_instructions[c].first_uop;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
*first_instruction = block->ins;
|
||||
return -1;
|
||||
}
|
||||
@@ -185,7 +185,7 @@ static x86seg *codegen_generate_ea_16_long(ir_data_t *ir, x86seg *op_ea_seg, uin
|
||||
op_ea_seg = &cpu_state.seg_ss;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
codegen_mark_code_present(ir->block, cs+old_pc, ((*op_pc)+1)-old_pc);
|
||||
return op_ea_seg;
|
||||
}
|
||||
@@ -290,7 +290,7 @@ static x86seg *codegen_generate_ea_32_long(ir_data_t *ir, x86seg *op_ea_seg, uin
|
||||
uop_MOV_IMM(ir, IREG_eaaddr, new_eaaddr);
|
||||
extra_bytes = 4;
|
||||
}
|
||||
|
||||
|
||||
(*op_pc) += 4;
|
||||
}
|
||||
else
|
||||
@@ -327,7 +327,7 @@ static x86seg *codegen_generate_ea_32_long(ir_data_t *ir, x86seg *op_ea_seg, uin
|
||||
|
||||
if (extra_bytes)
|
||||
codegen_mark_code_present(ir->block, cs+old_pc, extra_bytes);
|
||||
|
||||
|
||||
return op_ea_seg;
|
||||
}
|
||||
|
||||
@@ -617,7 +617,7 @@ generate_call:
|
||||
|
||||
if (codegen_timing_jump_cycles)
|
||||
codegen_timing_jump_cycles();
|
||||
|
||||
|
||||
if (jump_cycles)
|
||||
codegen_accumulate(ir, ACCREG_cycles, -jump_cycles);
|
||||
codegen_accumulate_flush(ir);
|
||||
@@ -673,7 +673,7 @@ generate_call:
|
||||
if (recomp_opcodes_3DNOW[opcode_3dnow])
|
||||
{
|
||||
next_pc = opcode_pc + 1;
|
||||
|
||||
|
||||
op_table = (OpFn *) x86_dynarec_opcodes_3DNOW;
|
||||
recomp_op_table = recomp_opcodes_3DNOW;
|
||||
opcode = opcode_3dnow;
|
||||
@@ -765,14 +765,14 @@ generate_call:
|
||||
last_op_ea_seg = op_ea_seg;
|
||||
last_op_ssegs = op_ssegs;
|
||||
//codegen_block_ins++;
|
||||
|
||||
|
||||
block->ins++;
|
||||
|
||||
if (block->ins >= MAX_INSTRUCTION_COUNT)
|
||||
CPU_BLOCK_END();
|
||||
|
||||
codegen_endpc = (cs + cpu_state.pc) + 8;
|
||||
|
||||
|
||||
// if (has_ea)
|
||||
// fatal("Has EA\n");
|
||||
}
|
||||
|
||||
@@ -13,18 +13,18 @@
|
||||
added to the page_lookup for this purpose. When in the page_lookup, each write
|
||||
will go through the mem_write_ram*_page() functions and set the dirty mask
|
||||
appropriately.
|
||||
|
||||
|
||||
Each codeblock also contains a code mask (actually two masks, one for each
|
||||
page the block is/may be in), again with each bit representing 64 bytes.
|
||||
|
||||
|
||||
Each page has a list of codeblocks present in it. As each codeblock can span
|
||||
up to two pages, two lists are present.
|
||||
|
||||
|
||||
When a codeblock is about to be executed, the code masks are compared with the
|
||||
dirty masks for the relevant pages. If either intersect, then
|
||||
codegen_check_flush() is called on the affected page(s), and all affected
|
||||
blocks are evicted.
|
||||
|
||||
|
||||
The 64 byte granularity appears to work reasonably well for most cases,
|
||||
avoiding most unnecessary evictions (eg when code & data are stored in the
|
||||
same page).
|
||||
@@ -45,7 +45,7 @@ typedef struct codeblock_t
|
||||
uint16_t parent, left, right;
|
||||
|
||||
uint8_t *data;
|
||||
|
||||
|
||||
uint64_t page_mask, page_mask2;
|
||||
uint64_t *dirty_mask, *dirty_mask2;
|
||||
|
||||
@@ -96,10 +96,10 @@ static inline codeblock_t *codeblock_tree_find(uint32_t phys, uint32_t _cs)
|
||||
{
|
||||
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)
|
||||
{
|
||||
@@ -115,7 +115,7 @@ static inline codeblock_t *codeblock_tree_find(uint32_t phys, uint32_t _cs)
|
||||
else
|
||||
block = block->right ? &codeblock[block->right] : NULL;
|
||||
}
|
||||
|
||||
|
||||
return block;
|
||||
}
|
||||
|
||||
@@ -133,23 +133,23 @@ static inline void codeblock_tree_add(codeblock_t *new_block)
|
||||
{
|
||||
codeblock_t *old_block = NULL;
|
||||
uint64_t old_block_cmp = 0;
|
||||
|
||||
|
||||
while (block)
|
||||
{
|
||||
old_block = block;
|
||||
old_block_cmp = old_block->_cs | ((uint64_t)old_block->phys << 32);
|
||||
|
||||
|
||||
if (a < old_block_cmp)
|
||||
block = block->left ? &codeblock[block->left] : NULL;
|
||||
else
|
||||
block = block->right ? &codeblock[block->right] : NULL;
|
||||
}
|
||||
|
||||
|
||||
if (a < old_block_cmp)
|
||||
old_block->left = get_block_nr(new_block);
|
||||
else
|
||||
old_block->right = get_block_nr(new_block);
|
||||
|
||||
|
||||
new_block->parent = get_block_nr(old_block);
|
||||
new_block->left = new_block->right = BLOCK_INVALID;
|
||||
}
|
||||
@@ -173,7 +173,7 @@ static inline void codeblock_tree_delete(codeblock_t *block)
|
||||
else
|
||||
{
|
||||
uint16_t block_nr = get_block_nr(block);
|
||||
|
||||
|
||||
if (parent->left == block_nr)
|
||||
parent->left = BLOCK_INVALID;
|
||||
if (parent->right == block_nr)
|
||||
@@ -237,11 +237,11 @@ static inline void codeblock_tree_delete(codeblock_t *block)
|
||||
codeblock_t *lowest = &codeblock[block->right], *highest;
|
||||
codeblock_t *old_parent;
|
||||
uint16_t lowest_nr;
|
||||
|
||||
|
||||
while (lowest->left)
|
||||
lowest = &codeblock[lowest->left];
|
||||
lowest_nr = get_block_nr(lowest);
|
||||
|
||||
|
||||
old_parent = &codeblock[lowest->parent];
|
||||
|
||||
/*Replace deleted node with lowest node*/
|
||||
@@ -263,7 +263,7 @@ static inline void codeblock_tree_delete(codeblock_t *block)
|
||||
codeblock[lowest->left].parent = lowest_nr;
|
||||
|
||||
old_parent->left = BLOCK_INVALID;
|
||||
|
||||
|
||||
highest = &codeblock[lowest->right];
|
||||
if (!lowest->right)
|
||||
{
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
enum
|
||||
{
|
||||
ACCREG_cycles = 0,
|
||||
|
||||
|
||||
ACCREG_COUNT
|
||||
};
|
||||
|
||||
|
||||
@@ -60,13 +60,13 @@ mem_block_t *codegen_allocator_allocate(mem_block_t *parent, int code_block)
|
||||
{
|
||||
mem_block_t *block;
|
||||
uint32_t block_nr;
|
||||
|
||||
|
||||
while (!mem_block_free_list)
|
||||
{
|
||||
/*Pick a random memory block and free the owning code block*/
|
||||
block_nr = rand() & MEM_BLOCK_MASK;
|
||||
block = &mem_blocks[block_nr];
|
||||
|
||||
|
||||
if (block->code_block && block->code_block != code_block)
|
||||
codegen_delete_block(&codeblock[block->code_block]);
|
||||
}
|
||||
@@ -75,7 +75,7 @@ mem_block_t *codegen_allocator_allocate(mem_block_t *parent, int code_block)
|
||||
block_nr = mem_block_free_list;
|
||||
block = &mem_blocks[block_nr-1];
|
||||
mem_block_free_list = block->next;
|
||||
|
||||
|
||||
block->code_block = code_block;
|
||||
if (parent)
|
||||
{
|
||||
@@ -97,12 +97,12 @@ void codegen_allocator_free(mem_block_t *block)
|
||||
{
|
||||
int next_block_nr = block->next;
|
||||
codegen_allocator_usage--;
|
||||
|
||||
|
||||
block->next = mem_block_free_list;
|
||||
block->code_block = BLOCK_INVALID;
|
||||
mem_block_free_list = block_nr;
|
||||
block_nr = next_block_nr;
|
||||
|
||||
|
||||
if (block_nr)
|
||||
block = &mem_blocks[block_nr - 1];
|
||||
else
|
||||
|
||||
@@ -4,12 +4,12 @@
|
||||
/*The allocator handles all allocation of executable memory. Since the two-pass
|
||||
recompiler design makes applying hard limits to codeblock size difficult, the
|
||||
allocator allows memory to be provided as and when required.
|
||||
|
||||
|
||||
The allocator provides a block size of a little under 1 kB (slightly lower to
|
||||
limit cache aliasing). Each generated codeblock is allocated one block by default,
|
||||
and will allocate additional block(s) once the existing memory is sorted. Blocks
|
||||
are chained together by jump instructions.
|
||||
|
||||
|
||||
Due to the chaining, the total memory size is limited by the range of a jump
|
||||
instruction. ARMv7 is restricted to +/- 32 MB, ARMv8 to +/- 128 MB, x86 to
|
||||
+/- 2GB. As a result, total memory size is limited to 32 MB on ARMv7*/
|
||||
|
||||
@@ -283,7 +283,7 @@ static void build_fp_round_routine(codeblock_t *block)
|
||||
host_arm_VCVTR_IS_D(block, REG_D_TEMP, REG_D_TEMP);
|
||||
host_arm_VMSR_FPSCR(block, REG_TEMP);
|
||||
host_arm_MOV_REG(block, REG_PC, REG_LR);
|
||||
|
||||
|
||||
jump_table[X87_ROUNDING_CHOP] = (uint64_t)(uintptr_t)&block_write_data[block_pos]; //zero
|
||||
host_arm_VCVT_IS_D(block, REG_D_TEMP, REG_D_TEMP);
|
||||
host_arm_MOV_REG(block, REG_PC, REG_LR);
|
||||
|
||||
@@ -270,7 +270,7 @@ static void build_fp_round_routine(codeblock_t *block, int is_quad)
|
||||
else
|
||||
host_arm64_FCVTMS_W_D(block, REG_TEMP, REG_V_TEMP);
|
||||
host_arm64_RET(block, REG_X30);
|
||||
|
||||
|
||||
jump_table[X87_ROUNDING_CHOP] = (uint64_t)(uintptr_t)&block_write_data[block_pos]; //zero
|
||||
if (is_quad)
|
||||
host_arm64_FCVTZS_X_D(block, REG_TEMP, REG_V_TEMP);
|
||||
|
||||
@@ -1410,7 +1410,7 @@ static int codegen_MOV_INT_DOUBLE_64(codeblock_t *block, uop_t *uop)
|
||||
host_arm64_FMOV_D_D(block, REG_V_TEMP, src_reg);
|
||||
host_arm64_call(block, codegen_fp_round_quad);
|
||||
host_arm64_FMOV_D_Q(block, dest_reg, REG_TEMP);
|
||||
|
||||
|
||||
host_arm64_branch_set_offset(branch_offset, &block_write_data[block_pos]);
|
||||
}
|
||||
else
|
||||
|
||||
@@ -416,7 +416,7 @@ static int codegen_CMP_JNBE(codeblock_t *block, uop_t *uop)
|
||||
|
||||
jump_p = host_arm_BHI_(block);
|
||||
*jump_p |= ((((uintptr_t)uop->p - (uintptr_t)jump_p) - 8) & 0x3fffffc) >> 2;
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1488,7 +1488,7 @@ static int codegen_MOV_INT_DOUBLE(codeblock_t *block, uop_t *uop)
|
||||
static int64_t x87_fround64(double b)
|
||||
{
|
||||
int64_t a, c;
|
||||
|
||||
|
||||
switch ((cpu_state.npxc >> 10) & 3)
|
||||
{
|
||||
case 0: /*Nearest*/
|
||||
@@ -1507,7 +1507,7 @@ static int64_t x87_fround64(double b)
|
||||
case 3: /*Chop*/
|
||||
return (int64_t)b;
|
||||
}
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
static int codegen_MOV_INT_DOUBLE_64(codeblock_t *block, uop_t *uop)
|
||||
@@ -1529,7 +1529,7 @@ static int codegen_MOV_INT_DOUBLE_64(codeblock_t *block, uop_t *uop)
|
||||
host_arm_VMOV_D_D(block, REG_D0, src_reg);
|
||||
host_arm_call(block, x87_fround64);
|
||||
host_arm_VMOV_D_64(block, REG_D_TEMP, REG_R0, REG_R1);
|
||||
|
||||
|
||||
*branch_offset |= ((((uintptr_t)&block_write_data[block_pos] - (uintptr_t)branch_offset) - 8) & 0x3fffffc) >> 2;
|
||||
}
|
||||
else
|
||||
|
||||
@@ -701,7 +701,7 @@ void host_x86_MOV8_REG_ABS(codeblock_t *block, int dst_reg, void *p)
|
||||
{
|
||||
int64_t offset = (uintptr_t)p - (((uintptr_t)&cpu_state) + 128);
|
||||
int64_t ram_offset = (uintptr_t)p - (uintptr_t)ram;
|
||||
|
||||
|
||||
if (dst_reg & 8)
|
||||
fatal("host_x86_MOV8_REG_ABS reg & 8\n");
|
||||
|
||||
@@ -767,7 +767,7 @@ void host_x86_MOV32_REG_ABS(codeblock_t *block, int dst_reg, void *p)
|
||||
{
|
||||
int64_t offset = (uintptr_t)p - (((uintptr_t)&cpu_state) + 128);
|
||||
int64_t ram_offset = (uintptr_t)p - (uintptr_t)ram;
|
||||
|
||||
|
||||
if (dst_reg & 8)
|
||||
fatal("host_x86_MOV32_REG_ABS reg & 8\n");
|
||||
|
||||
@@ -1139,7 +1139,7 @@ void host_x86_MOVZX_REG_ABS_16_8(codeblock_t *block, int dst_reg, void *p)
|
||||
{
|
||||
int64_t offset = (uintptr_t)p - (((uintptr_t)&cpu_state) + 128);
|
||||
int64_t ram_offset = (uintptr_t)p - (uintptr_t)ram;
|
||||
|
||||
|
||||
if (dst_reg & 8)
|
||||
fatal("host_x86_MOVZX_REG_ABS_16_8 - bad reg\n");
|
||||
|
||||
@@ -1170,7 +1170,7 @@ void host_x86_MOVZX_REG_ABS_32_8(codeblock_t *block, int dst_reg, void *p)
|
||||
{
|
||||
int64_t offset = (uintptr_t)p - (((uintptr_t)&cpu_state) + 128);
|
||||
int64_t ram_offset = (uintptr_t)p - (uintptr_t)ram;
|
||||
|
||||
|
||||
// if (dst_reg & 8)
|
||||
// fatal("host_x86_MOVZX_REG_ABS_32_8 - bad reg\n");
|
||||
|
||||
@@ -1214,7 +1214,7 @@ void host_x86_MOVZX_REG_ABS_32_16(codeblock_t *block, int dst_reg, void *p)
|
||||
{
|
||||
int64_t offset = (uintptr_t)p - (((uintptr_t)&cpu_state) + 128);
|
||||
int64_t ram_offset = (uintptr_t)p - (uintptr_t)ram;
|
||||
|
||||
|
||||
if (dst_reg & 8)
|
||||
fatal("host_x86_MOVZX_REG_ABS_32_16 - bad reg\n");
|
||||
|
||||
|
||||
@@ -1449,7 +1449,7 @@ static int codegen_MOV_INT_DOUBLE_64(codeblock_t *block, uop_t *uop)
|
||||
host_x86_CVTSD2SI_REG64_XREG(block, REG_RCX, src_reg);
|
||||
host_x86_LDMXCSR(block, &cpu_state.old_fp_control);
|
||||
host_x86_MOVQ_XREG_REG(block, dest_reg, REG_RCX);
|
||||
|
||||
|
||||
*branch_offset = (uint32_t)((uintptr_t)&block_write_data[block_pos] - (uintptr_t)branch_offset) - 4;
|
||||
}
|
||||
#ifdef RECOMPILER_DEBUG
|
||||
|
||||
@@ -66,7 +66,7 @@ static void build_load_routine(codeblock_t *block, int size, int is_float)
|
||||
{
|
||||
uint8_t *branch_offset;
|
||||
uint8_t *misaligned_offset = NULL;
|
||||
|
||||
|
||||
/*In - ESI = address
|
||||
Out - ECX = data, ESI = abrt*/
|
||||
/*MOV ECX, ESI
|
||||
@@ -111,7 +111,7 @@ static void build_load_routine(codeblock_t *block, int size, int is_float)
|
||||
fatal("build_load_routine: size=%i\n", size);
|
||||
host_x86_XOR32_REG_REG(block, REG_ESI, REG_ESI);
|
||||
host_x86_RET(block);
|
||||
|
||||
|
||||
*branch_offset = (uint8_t)((uintptr_t)&block_write_data[block_pos] - (uintptr_t)branch_offset) - 1;
|
||||
if (size != 1)
|
||||
*misaligned_offset = (uint8_t)((uintptr_t)&block_write_data[block_pos] - (uintptr_t)misaligned_offset) - 1;
|
||||
@@ -155,7 +155,7 @@ static void build_store_routine(codeblock_t *block, int size, int is_float)
|
||||
{
|
||||
uint8_t *branch_offset;
|
||||
uint8_t *misaligned_offset = NULL;
|
||||
|
||||
|
||||
/*In - ECX = data, ESI = address
|
||||
Out - ESI = abrt
|
||||
Corrupts EDI*/
|
||||
@@ -290,7 +290,7 @@ void codegen_backend_init()
|
||||
block->data = codeblock_allocator_get_ptr(block->head_mem_block);
|
||||
block_write_data = block->data;
|
||||
build_loadstore_routines(block);
|
||||
|
||||
|
||||
codegen_gpf_rout = &codeblock[block_current].data[block_pos];
|
||||
host_x86_MOV32_STACK_IMM(block, STACK_ARG0, 0);
|
||||
host_x86_MOV32_STACK_IMM(block, STACK_ARG1, 0);
|
||||
|
||||
@@ -66,7 +66,7 @@ static int codegen_ADD_IMM(codeblock_t *block, uop_t *uop)
|
||||
{
|
||||
int dest_reg = HOST_REG_GET(uop->dest_reg_a_real), src_reg = HOST_REG_GET(uop->src_reg_a_real);
|
||||
int dest_size = IREG_GET_SIZE(uop->dest_reg_a_real), src_size = IREG_GET_SIZE(uop->src_reg_a_real);
|
||||
|
||||
|
||||
if (REG_IS_L(dest_size) && REG_IS_L(src_size))
|
||||
{
|
||||
if (uop->dest_reg_a_real != uop->src_reg_a_real)
|
||||
@@ -280,7 +280,7 @@ static int codegen_CMP_IMM_JZ_DEST(codeblock_t *block, uop_t *uop)
|
||||
fatal("CMP_IMM_JZ_DEST %02x\n", uop->src_reg_a_real);
|
||||
#endif
|
||||
uop->p = host_x86_JZ_long(block);
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -319,7 +319,7 @@ static int codegen_CMP_JNBE(codeblock_t *block, uop_t *uop)
|
||||
#endif
|
||||
jump_p = host_x86_JNBE_long(block);
|
||||
*jump_p = (uintptr_t)uop->p - ((uintptr_t)jump_p + 4);
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -801,7 +801,7 @@ static int codegen_FSUB(codeblock_t *block, uop_t *uop)
|
||||
static int codegen_FP_ENTER(codeblock_t *block, uop_t *uop)
|
||||
{
|
||||
uint32_t *branch_offset;
|
||||
|
||||
|
||||
host_x86_MOV32_REG_ABS(block, REG_ECX, &cr0);
|
||||
host_x86_TEST32_REG_IMM(block, REG_ECX, 0xc);
|
||||
branch_offset = host_x86_JZ_long(block);
|
||||
@@ -830,7 +830,7 @@ static int codegen_MMX_ENTER(codeblock_t *block, uop_t *uop)
|
||||
host_x86_MOV32_ABS_IMM(block, &cpu_state.tag[4], 0x01010101);
|
||||
host_x86_MOV32_ABS_IMM(block, &cpu_state.TOP, 0);
|
||||
host_x86_MOV8_ABS_IMM(block, &cpu_state.ismmx, 1);
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1047,7 +1047,7 @@ static int codegen_MEM_LOAD_DOUBLE(codeblock_t *block, uop_t *uop)
|
||||
host_x86_TEST32_REG(block, REG_ESI, REG_ESI);
|
||||
host_x86_JNZ(block, codegen_exit_rout);
|
||||
host_x86_MOVQ_XREG_XREG(block, dest_reg, REG_XMM_TEMP);
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1266,7 +1266,7 @@ static int codegen_MOV_REG_PTR(codeblock_t *block, uop_t *uop)
|
||||
}
|
||||
else
|
||||
fatal("MOV_REG_PTR %02x\n", uop->dest_reg_a_real);
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
static int codegen_MOVZX_REG_PTR_8(codeblock_t *block, uop_t *uop)
|
||||
@@ -2830,7 +2830,7 @@ const uOpFn uop_handlers[UOP_MAX] =
|
||||
[UOP_JMP_DEST & UOP_MASK] = codegen_JMP_DEST,
|
||||
|
||||
[UOP_LOAD_SEG & UOP_MASK] = codegen_LOAD_SEG,
|
||||
|
||||
|
||||
[UOP_LOAD_FUNC_ARG_0 & UOP_MASK] = codegen_LOAD_FUNC_ARG0,
|
||||
[UOP_LOAD_FUNC_ARG_1 & UOP_MASK] = codegen_LOAD_FUNC_ARG1,
|
||||
[UOP_LOAD_FUNC_ARG_2 & UOP_MASK] = codegen_LOAD_FUNC_ARG2,
|
||||
@@ -2844,12 +2844,12 @@ const uOpFn uop_handlers[UOP_MAX] =
|
||||
[UOP_STORE_P_IMM & UOP_MASK] = codegen_STORE_PTR_IMM,
|
||||
[UOP_STORE_P_IMM_8 & UOP_MASK] = codegen_STORE_PTR_IMM_8,
|
||||
[UOP_STORE_P_IMM_16 & UOP_MASK] = codegen_STORE_PTR_IMM_16,
|
||||
|
||||
|
||||
[UOP_MEM_LOAD_ABS & UOP_MASK] = codegen_MEM_LOAD_ABS,
|
||||
[UOP_MEM_LOAD_REG & UOP_MASK] = codegen_MEM_LOAD_REG,
|
||||
[UOP_MEM_LOAD_SINGLE & UOP_MASK] = codegen_MEM_LOAD_SINGLE,
|
||||
[UOP_MEM_LOAD_DOUBLE & UOP_MASK] = codegen_MEM_LOAD_DOUBLE,
|
||||
|
||||
|
||||
[UOP_MEM_STORE_ABS & UOP_MASK] = codegen_MEM_STORE_ABS,
|
||||
[UOP_MEM_STORE_REG & UOP_MASK] = codegen_MEM_STORE_REG,
|
||||
[UOP_MEM_STORE_IMM_8 & UOP_MASK] = codegen_MEM_STORE_IMM_8,
|
||||
@@ -2857,7 +2857,7 @@ const uOpFn uop_handlers[UOP_MAX] =
|
||||
[UOP_MEM_STORE_IMM_32 & UOP_MASK] = codegen_MEM_STORE_IMM_32,
|
||||
[UOP_MEM_STORE_SINGLE & UOP_MASK] = codegen_MEM_STORE_SINGLE,
|
||||
[UOP_MEM_STORE_DOUBLE & UOP_MASK] = codegen_MEM_STORE_DOUBLE,
|
||||
|
||||
|
||||
[UOP_MOV & UOP_MASK] = codegen_MOV,
|
||||
[UOP_MOV_PTR & UOP_MASK] = codegen_MOV_PTR,
|
||||
[UOP_MOV_IMM & UOP_MASK] = codegen_MOV_IMM,
|
||||
@@ -2917,16 +2917,16 @@ const uOpFn uop_handlers[UOP_MAX] =
|
||||
|
||||
[UOP_TEST_JNS_DEST & UOP_MASK] = codegen_TEST_JNS_DEST,
|
||||
[UOP_TEST_JS_DEST & UOP_MASK] = codegen_TEST_JS_DEST,
|
||||
|
||||
|
||||
[UOP_FP_ENTER & UOP_MASK] = codegen_FP_ENTER,
|
||||
[UOP_MMX_ENTER & UOP_MASK] = codegen_MMX_ENTER,
|
||||
|
||||
|
||||
[UOP_FADD & UOP_MASK] = codegen_FADD,
|
||||
[UOP_FDIV & UOP_MASK] = codegen_FDIV,
|
||||
[UOP_FMUL & UOP_MASK] = codegen_FMUL,
|
||||
[UOP_FSUB & UOP_MASK] = codegen_FSUB,
|
||||
[UOP_FCOM & UOP_MASK] = codegen_FCOM,
|
||||
|
||||
|
||||
[UOP_FABS & UOP_MASK] = codegen_FABS,
|
||||
[UOP_FCHS & UOP_MASK] = codegen_FCHS,
|
||||
[UOP_FSQRT & UOP_MASK] = codegen_FSQRT,
|
||||
@@ -2963,11 +2963,11 @@ const uOpFn uop_handlers[UOP_MAX] =
|
||||
[UOP_PFRSQRT & UOP_MASK] = codegen_PFRSQRT,
|
||||
[UOP_PFSUB & UOP_MASK] = codegen_PFSUB,
|
||||
[UOP_PI2FD & UOP_MASK] = codegen_PI2FD,
|
||||
|
||||
|
||||
[UOP_PMADDWD & UOP_MASK] = codegen_PMADDWD,
|
||||
[UOP_PMULHW & UOP_MASK] = codegen_PMULHW,
|
||||
[UOP_PMULLW & UOP_MASK] = codegen_PMULLW,
|
||||
|
||||
|
||||
[UOP_PSLLW_IMM & UOP_MASK] = codegen_PSLLW_IMM,
|
||||
[UOP_PSLLD_IMM & UOP_MASK] = codegen_PSLLD_IMM,
|
||||
[UOP_PSLLQ_IMM & UOP_MASK] = codegen_PSLLQ_IMM,
|
||||
@@ -2977,7 +2977,7 @@ const uOpFn uop_handlers[UOP_MAX] =
|
||||
[UOP_PSRLW_IMM & UOP_MASK] = codegen_PSRLW_IMM,
|
||||
[UOP_PSRLD_IMM & UOP_MASK] = codegen_PSRLD_IMM,
|
||||
[UOP_PSRLQ_IMM & UOP_MASK] = codegen_PSRLQ_IMM,
|
||||
|
||||
|
||||
[UOP_PSUBB & UOP_MASK] = codegen_PSUBB,
|
||||
[UOP_PSUBW & UOP_MASK] = codegen_PSUBW,
|
||||
[UOP_PSUBD & UOP_MASK] = codegen_PSUBD,
|
||||
@@ -2985,7 +2985,7 @@ const uOpFn uop_handlers[UOP_MAX] =
|
||||
[UOP_PSUBSW & UOP_MASK] = codegen_PSUBSW,
|
||||
[UOP_PSUBUSB & UOP_MASK] = codegen_PSUBUSB,
|
||||
[UOP_PSUBUSW & UOP_MASK] = codegen_PSUBUSW,
|
||||
|
||||
|
||||
[UOP_PUNPCKHBW & UOP_MASK] = codegen_PUNPCKHBW,
|
||||
[UOP_PUNPCKHWD & UOP_MASK] = codegen_PUNPCKHWD,
|
||||
[UOP_PUNPCKHDQ & UOP_MASK] = codegen_PUNPCKHDQ,
|
||||
@@ -2994,7 +2994,7 @@ const uOpFn uop_handlers[UOP_MAX] =
|
||||
[UOP_PUNPCKLDQ & UOP_MASK] = codegen_PUNPCKLDQ,
|
||||
|
||||
[UOP_NOP_BARRIER & UOP_MASK] = codegen_NOP,
|
||||
|
||||
|
||||
#ifdef DEBUG_EXTRA
|
||||
[UOP_LOG_INSTR & UOP_MASK] = codegen_LOG_INSTR
|
||||
#endif
|
||||
|
||||
@@ -58,7 +58,7 @@ static void delete_dirty_block(codeblock_t *block);
|
||||
/*Temporary list of code blocks that have recently been evicted. This allows for
|
||||
some historical state to be kept when a block is the target of self-modifying
|
||||
code.
|
||||
|
||||
|
||||
The size of this list is limited to DIRTY_LIST_MAX_SIZE blocks. When this is
|
||||
exceeded the oldest entry will be moved to the free list.*/
|
||||
static uint16_t block_dirty_list_head, block_dirty_list_tail;
|
||||
@@ -88,7 +88,7 @@ static void block_dirty_list_add(codeblock_t *block)
|
||||
if (block_dirty_list_head != BLOCK_INVALID)
|
||||
{
|
||||
codeblock_t *old_head = &codeblock[block_dirty_list_head];
|
||||
|
||||
|
||||
block->next = block_dirty_list_head;
|
||||
block->prev = BLOCK_INVALID;
|
||||
block_dirty_list_head = old_head->prev = get_block_nr(block);
|
||||
@@ -213,9 +213,9 @@ static codeblock_t *block_free_list_get()
|
||||
void codegen_init()
|
||||
{
|
||||
int c;
|
||||
|
||||
|
||||
codegen_allocator_init();
|
||||
|
||||
|
||||
codegen_backend_init();
|
||||
block_free_list = 0;
|
||||
for (c = 0; c < BLOCK_SIZE; c++)
|
||||
@@ -235,7 +235,7 @@ void codegen_close()
|
||||
{
|
||||
int c;
|
||||
uint32_t highest_num = 0, highest_idx = 0;
|
||||
|
||||
|
||||
for (c = 0; c < 256*256; c++)
|
||||
{
|
||||
if (instr_counts[c] > highest_num)
|
||||
@@ -263,7 +263,7 @@ void codegen_reset()
|
||||
for (c = 1; c < BLOCK_SIZE; c++)
|
||||
{
|
||||
codeblock_t *block = &codeblock[c];
|
||||
|
||||
|
||||
if (block->pc != BLOCK_PC_INVALID)
|
||||
{
|
||||
block->phys = 0;
|
||||
@@ -296,7 +296,7 @@ void dump_block()
|
||||
pclog(" %p : %08x-%08x %08x-%08x %p %p\n", (void *)block, start_pc, end_pc, block->pc, block->endpc, (void *)block->prev, (void *)block->next);
|
||||
if (!block->pc)
|
||||
fatal("Dead PC=0\n");
|
||||
|
||||
|
||||
block = block->next;
|
||||
}
|
||||
pclog("dump_block done\n");*/
|
||||
@@ -331,11 +331,11 @@ static void add_to_block_list(codeblock_t *block)
|
||||
fatal("block->next->pc=BLOCK_PC_INVALID %p %p %x %x\n", (void *)&codeblock[block->next], (void *)codeblock, block_current, block_pos);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
if (block->page_mask2)
|
||||
{
|
||||
block->flags |= CODEBLOCK_HAS_PAGE2;
|
||||
|
||||
|
||||
block_prev_nr = pages[block->phys_2 >> 12].block_2;
|
||||
|
||||
if (block_prev_nr)
|
||||
@@ -466,7 +466,7 @@ void codegen_delete_block(codeblock_t *block)
|
||||
void codegen_delete_random_block(int required_mem_block)
|
||||
{
|
||||
int block_nr = rand() & BLOCK_MASK;
|
||||
|
||||
|
||||
while (1)
|
||||
{
|
||||
if (block_nr && block_nr != block_current)
|
||||
@@ -493,7 +493,7 @@ void codegen_check_flush(page_t *page, uint64_t mask, uint32_t phys_addr)
|
||||
{
|
||||
codeblock_t *block = &codeblock[block_nr];
|
||||
uint16_t next_block = block->next;
|
||||
|
||||
|
||||
if (*block->dirty_mask & block->page_mask)
|
||||
{
|
||||
invalidate_block(block);
|
||||
@@ -506,7 +506,7 @@ void codegen_check_flush(page_t *page, uint64_t mask, uint32_t phys_addr)
|
||||
}
|
||||
|
||||
block_nr = page->block_2;
|
||||
|
||||
|
||||
while (block_nr)
|
||||
{
|
||||
codeblock_t *block = &codeblock[block_nr];
|
||||
@@ -522,12 +522,12 @@ void codegen_check_flush(page_t *page, uint64_t mask, uint32_t phys_addr)
|
||||
#endif
|
||||
block_nr = next_block;
|
||||
}
|
||||
|
||||
|
||||
if (page->code_present_mask & page->dirty_mask)
|
||||
remove_from_evict_list = 1;
|
||||
page->code_present_mask &= ~page->dirty_mask;
|
||||
page->dirty_mask = 0;
|
||||
|
||||
|
||||
for (c = 0; c < 64; c++)
|
||||
{
|
||||
if (page->byte_code_present_mask[c] & page->byte_dirty_mask[c])
|
||||
@@ -567,7 +567,7 @@ void codegen_block_init(uint32_t phys_addr)
|
||||
block->page_mask = block->page_mask2 = 0;
|
||||
block->flags = CODEBLOCK_STATIC_TOP;
|
||||
block->status = cpu_cur_status;
|
||||
|
||||
|
||||
recomp_page = block->phys & ~0xfff;
|
||||
codeblock_tree_add(block);
|
||||
}
|
||||
@@ -598,7 +598,7 @@ void codegen_block_start_recompile(codeblock_t *block)
|
||||
block->data = codeblock_allocator_get_ptr(block->head_mem_block);
|
||||
|
||||
block->status = cpu_cur_status;
|
||||
|
||||
|
||||
block->page_mask = block->page_mask2 = 0;
|
||||
block->ins = 0;
|
||||
|
||||
@@ -607,30 +607,30 @@ void codegen_block_start_recompile(codeblock_t *block)
|
||||
last_op32 = -1;
|
||||
last_ea_seg = NULL;
|
||||
last_ssegs = -1;
|
||||
|
||||
|
||||
codegen_block_cycles = 0;
|
||||
codegen_timing_block_start();
|
||||
|
||||
|
||||
codegen_block_ins = 0;
|
||||
codegen_block_full_ins = 0;
|
||||
|
||||
recomp_page = block->phys & ~0xfff;
|
||||
|
||||
|
||||
codegen_flags_changed = 0;
|
||||
codegen_fpu_entered = 0;
|
||||
codegen_mmx_entered = 0;
|
||||
|
||||
codegen_fpu_loaded_iq[0] = codegen_fpu_loaded_iq[1] = codegen_fpu_loaded_iq[2] = codegen_fpu_loaded_iq[3] =
|
||||
codegen_fpu_loaded_iq[4] = codegen_fpu_loaded_iq[5] = codegen_fpu_loaded_iq[6] = codegen_fpu_loaded_iq[7] = 0;
|
||||
|
||||
|
||||
cpu_state.seg_ds.checked = cpu_state.seg_es.checked = cpu_state.seg_fs.checked = cpu_state.seg_gs.checked = (cr0 & 1) ? 0 : 1;
|
||||
|
||||
block->TOP = cpu_state.TOP & 7;
|
||||
block->flags |= CODEBLOCK_WAS_RECOMPILED;
|
||||
|
||||
codegen_flat_ds = !(cpu_cur_status & CPU_STATUS_NOTFLATDS);
|
||||
codegen_flat_ss = !(cpu_cur_status & CPU_STATUS_NOTFLATSS);
|
||||
|
||||
codegen_flat_ss = !(cpu_cur_status & CPU_STATUS_NOTFLATSS);
|
||||
|
||||
if (block->flags & CODEBLOCK_BYTE_MASK)
|
||||
{
|
||||
block->dirty_mask = &page->byte_dirty_mask[(block->phys >> PAGE_BYTE_MASK_SHIFT) & PAGE_BYTE_MASK_OFFSET_MASK];
|
||||
@@ -684,7 +684,7 @@ void codegen_block_generate_end_mask_recompile()
|
||||
if (block->flags & CODEBLOCK_BYTE_MASK)
|
||||
{
|
||||
int offset = (block->phys_2 >> PAGE_BYTE_MASK_SHIFT) & PAGE_BYTE_MASK_OFFSET_MASK;
|
||||
|
||||
|
||||
page_2->byte_code_present_mask[offset] |= block->page_mask2;
|
||||
block->dirty_mask2 = &page_2->byte_dirty_mask[offset];
|
||||
}
|
||||
|
||||
@@ -48,7 +48,7 @@ static void duplicate_uop(ir_data_t *ir, uop_t *uop, int offset)
|
||||
new_uop->imm_data = uop->imm_data;
|
||||
new_uop->p = uop->p;
|
||||
new_uop->pc = uop->pc;
|
||||
|
||||
|
||||
if (uop->jump_dest_uop != -1)
|
||||
{
|
||||
new_uop->jump_dest_uop = uop->jump_dest_uop + offset;
|
||||
@@ -64,10 +64,10 @@ void codegen_ir_compile(ir_data_t *ir, codeblock_t *block)
|
||||
{
|
||||
int unroll_count;
|
||||
int unroll_end;
|
||||
|
||||
|
||||
codegen_set_loop_start(ir, codegen_unroll_first_instruction);
|
||||
unroll_end = ir->wr_pos;
|
||||
|
||||
|
||||
for (unroll_count = 1; unroll_count < codegen_unroll_count; unroll_count++)
|
||||
{
|
||||
int offset = ir->wr_pos - codegen_unroll_start;
|
||||
@@ -89,7 +89,7 @@ void codegen_ir_compile(ir_data_t *ir, codeblock_t *block)
|
||||
for (c = 0; c < ir->wr_pos; c++)
|
||||
{
|
||||
uop_t *uop = &ir->uops[c];
|
||||
|
||||
|
||||
// pclog("uOP %i : %08x\n", c, uop->type);
|
||||
|
||||
if (uop->type & UOP_TYPE_BARRIER)
|
||||
@@ -184,7 +184,7 @@ void codegen_ir_compile(ir_data_t *ir, codeblock_t *block)
|
||||
else
|
||||
{
|
||||
uop_t *uop_dest = &ir->uops[uop->jump_dest_uop];
|
||||
|
||||
|
||||
while (uop_dest->jump_list_next != -1)
|
||||
uop_dest = &ir->uops[uop_dest->jump_list_next];
|
||||
|
||||
@@ -195,7 +195,7 @@ void codegen_ir_compile(ir_data_t *ir, codeblock_t *block)
|
||||
}
|
||||
|
||||
codegen_reg_flush_invalidate(ir, block);
|
||||
|
||||
|
||||
if (jump_target_at_end != -1)
|
||||
{
|
||||
uop_t *uop_dest = &ir->uops[jump_target_at_end];
|
||||
|
||||
@@ -361,19 +361,19 @@ typedef struct ir_data_t
|
||||
static inline uop_t *uop_alloc(ir_data_t *ir, uint32_t uop_type)
|
||||
{
|
||||
uop_t *uop;
|
||||
|
||||
|
||||
if (ir->wr_pos >= UOP_NR_MAX)
|
||||
fatal("Exceeded uOP max\n");
|
||||
|
||||
|
||||
uop = &ir->uops[ir->wr_pos++];
|
||||
|
||||
|
||||
uop->dest_reg_a = invalid_ir_reg;
|
||||
uop->src_reg_a = invalid_ir_reg;
|
||||
uop->src_reg_b = invalid_ir_reg;
|
||||
uop->src_reg_c = invalid_ir_reg;
|
||||
|
||||
|
||||
uop->pc = cpu_state.oldpc;
|
||||
|
||||
|
||||
uop->jump_dest_uop = -1;
|
||||
uop->jump_list_next = -1;
|
||||
|
||||
@@ -386,7 +386,7 @@ static inline uop_t *uop_alloc(ir_data_t *ir, uint32_t uop_type)
|
||||
static inline void uop_set_jump_dest(ir_data_t *ir, int jump_uop)
|
||||
{
|
||||
uop_t *uop = &ir->uops[jump_uop];
|
||||
|
||||
|
||||
uop->jump_dest_uop = ir->wr_pos;
|
||||
}
|
||||
|
||||
@@ -402,7 +402,7 @@ static inline int uop_gen(uint32_t uop_type, ir_data_t *ir)
|
||||
static inline int uop_gen_reg_src1(uint32_t uop_type, ir_data_t *ir, int src_reg_a)
|
||||
{
|
||||
uop_t *uop = uop_alloc(ir, uop_type);
|
||||
|
||||
|
||||
uop->type = uop_type;
|
||||
uop->src_reg_a = codegen_reg_read(src_reg_a);
|
||||
|
||||
@@ -424,7 +424,7 @@ static inline int uop_gen_reg_src1_imm(uint32_t uop_type, ir_data_t *ir, int src
|
||||
uop->type = uop_type;
|
||||
uop->src_reg_a = codegen_reg_read(src_reg);
|
||||
uop->imm_data = imm;
|
||||
|
||||
|
||||
return ir->wr_pos-1;
|
||||
}
|
||||
|
||||
@@ -514,7 +514,7 @@ static inline int uop_gen_reg_src2(uint32_t uop_type, ir_data_t *ir, int src_reg
|
||||
uop->type = uop_type;
|
||||
uop->src_reg_a = codegen_reg_read(src_reg_a);
|
||||
uop->src_reg_b = codegen_reg_read(src_reg_b);
|
||||
|
||||
|
||||
return ir->wr_pos-1;
|
||||
}
|
||||
|
||||
@@ -552,7 +552,7 @@ static inline void uop_gen_reg_src3_imm(uint32_t uop_type, ir_data_t *ir, int sr
|
||||
static inline void uop_gen_imm(uint32_t uop_type, ir_data_t *ir, uint32_t imm)
|
||||
{
|
||||
uop_t *uop = uop_alloc(ir, uop_type);
|
||||
|
||||
|
||||
uop->type = uop_type;
|
||||
uop->imm_data = imm;
|
||||
}
|
||||
@@ -560,7 +560,7 @@ static inline void uop_gen_imm(uint32_t uop_type, ir_data_t *ir, uint32_t imm)
|
||||
static inline void uop_gen_pointer(uint32_t uop_type, ir_data_t *ir, void *p)
|
||||
{
|
||||
uop_t *uop = uop_alloc(ir, uop_type);
|
||||
|
||||
|
||||
uop->type = uop_type;
|
||||
uop->p = p;
|
||||
}
|
||||
@@ -568,7 +568,7 @@ static inline void uop_gen_pointer(uint32_t uop_type, ir_data_t *ir, void *p)
|
||||
static inline void uop_gen_pointer_imm(uint32_t uop_type, ir_data_t *ir, void *p, uint32_t imm)
|
||||
{
|
||||
uop_t *uop = uop_alloc(ir, uop_type);
|
||||
|
||||
|
||||
uop->type = uop_type;
|
||||
uop->p = p;
|
||||
uop->imm_data = imm;
|
||||
|
||||
@@ -309,7 +309,7 @@ uint32_t ropADD_AX_imm(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32
|
||||
uint32_t ropADD_EAX_imm(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
{
|
||||
uop_MOV(ir, IREG_flags_op1, IREG_EAX);
|
||||
|
||||
|
||||
if (block->flags & CODEBLOCK_NO_IMMEDIATES)
|
||||
{
|
||||
LOAD_IMMEDIATE_FROM_RAM_32(block, ir, IREG_temp0, cs + op_pc);
|
||||
@@ -337,7 +337,7 @@ uint32_t ropADD_b_rm(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t
|
||||
if ((fetchdat & 0xc0) == 0xc0)
|
||||
{
|
||||
int src_reg = fetchdat & 7;
|
||||
|
||||
|
||||
uop_MOVZX(ir, IREG_flags_op1, IREG_8(dest_reg));
|
||||
uop_MOVZX(ir, IREG_flags_op2, IREG_8(src_reg));
|
||||
uop_ADD(ir, IREG_8(dest_reg), IREG_8(dest_reg), IREG_8(src_reg));
|
||||
@@ -1283,7 +1283,7 @@ uint32_t rop80(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetch
|
||||
{
|
||||
int dest_reg = fetchdat & 7;
|
||||
uint8_t imm = fastreadb(cs + op_pc + 1);
|
||||
|
||||
|
||||
if (block->flags & CODEBLOCK_NO_IMMEDIATES)
|
||||
{
|
||||
skip_immediate = 1;
|
||||
@@ -1779,7 +1779,7 @@ uint32_t rop81_w(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
uint32_t rop81_l(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
{
|
||||
int skip_immediate = 0;
|
||||
|
||||
|
||||
codegen_mark_code_present(block, cs+op_pc, 1);
|
||||
if ((fetchdat & 0xc0) == 0xc0)
|
||||
{
|
||||
@@ -1836,7 +1836,7 @@ uint32_t rop81_l(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
uop_MOV_IMM(ir, IREG_flags_op, FLAGS_ADC32);
|
||||
uop_MOV(ir, IREG_flags_res, IREG_32(dest_reg));
|
||||
break;
|
||||
|
||||
|
||||
case 0x18: /*SBB*/
|
||||
get_cf(ir, IREG_temp1);
|
||||
uop_MOV(ir, IREG_flags_op1, IREG_32(dest_reg));
|
||||
@@ -1954,7 +1954,7 @@ uint32_t rop81_l(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
uop_MOV(ir, IREG_flags_res, IREG_temp0);
|
||||
uop_MOV_IMM(ir, IREG_flags_op, FLAGS_ZN32);
|
||||
break;
|
||||
|
||||
|
||||
case 0x10: /*ADC*/
|
||||
get_cf(ir, IREG_temp3);
|
||||
if (block->flags & CODEBLOCK_NO_IMMEDIATES)
|
||||
@@ -2157,7 +2157,7 @@ uint32_t rop83_w(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
uop_MOVZX(ir, IREG_flags_res, IREG_temp0_W);
|
||||
uop_MOV_IMM(ir, IREG_flags_op, FLAGS_ZN16);
|
||||
break;
|
||||
|
||||
|
||||
case 0x10: /*ADC*/
|
||||
get_cf(ir, IREG_temp2);
|
||||
uop_ADD_IMM(ir, IREG_temp1_W, IREG_temp0_W, imm);
|
||||
@@ -2227,7 +2227,7 @@ uint32_t rop83_l(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
{
|
||||
int dest_reg = fetchdat & 7;
|
||||
uint32_t imm = (int32_t)(int8_t)fastreadb(cs + op_pc + 1);
|
||||
|
||||
|
||||
switch (fetchdat & 0x38)
|
||||
{
|
||||
case 0x00: /*ADD*/
|
||||
@@ -2243,7 +2243,7 @@ uint32_t rop83_l(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
uop_MOV_IMM(ir, IREG_flags_op, FLAGS_ZN32);
|
||||
uop_MOV(ir, IREG_flags_res, IREG_32(dest_reg));
|
||||
break;
|
||||
|
||||
|
||||
case 0x10: /*ADC*/
|
||||
get_cf(ir, IREG_temp1);
|
||||
uop_MOV(ir, IREG_flags_op1, IREG_32(dest_reg));
|
||||
@@ -2299,7 +2299,7 @@ uint32_t rop83_l(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
{
|
||||
x86seg *target_seg;
|
||||
uint32_t imm;
|
||||
|
||||
|
||||
uop_MOV_IMM(ir, IREG_oldpc, cpu_state.oldpc);
|
||||
target_seg = codegen_generate_ea(ir, op_ea_seg, fetchdat, op_ssegs, &op_pc, op_32, 0);
|
||||
if ((fetchdat & 0x38) == 0x38) /*CMP*/
|
||||
@@ -2326,7 +2326,7 @@ uint32_t rop83_l(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
uop_MOV(ir, IREG_flags_res, IREG_temp0);
|
||||
uop_MOV_IMM(ir, IREG_flags_op, FLAGS_ZN32);
|
||||
break;
|
||||
|
||||
|
||||
case 0x10: /*ADC*/
|
||||
get_cf(ir, IREG_temp2);
|
||||
uop_ADD_IMM(ir, IREG_temp1, IREG_temp0, imm);
|
||||
@@ -2392,7 +2392,7 @@ uint32_t rop83_l(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
static void rebuild_c(ir_data_t *ir)
|
||||
{
|
||||
int needs_rebuild = 1;
|
||||
|
||||
|
||||
if (codegen_flags_changed)
|
||||
{
|
||||
switch (cpu_state.flags_op)
|
||||
@@ -2403,7 +2403,7 @@ static void rebuild_c(ir_data_t *ir)
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (needs_rebuild)
|
||||
{
|
||||
uop_CALL_FUNC(ir, flags_rebuild_c);
|
||||
@@ -2426,7 +2426,7 @@ uint32_t ropINC_r16(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t
|
||||
uint32_t ropINC_r32(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
{
|
||||
rebuild_c(ir);
|
||||
|
||||
|
||||
uop_MOV(ir, IREG_flags_op1, IREG_32(opcode & 7));
|
||||
uop_ADD_IMM(ir, IREG_32(opcode & 7), IREG_32(opcode & 7), 1);
|
||||
uop_MOV(ir, IREG_flags_res, IREG_32(opcode & 7));
|
||||
@@ -2468,7 +2468,7 @@ uint32_t ropINCDEC(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t f
|
||||
{
|
||||
codegen_mark_code_present(block, cs+op_pc, 1);
|
||||
rebuild_c(ir);
|
||||
|
||||
|
||||
if ((fetchdat & 0xc0) == 0xc0)
|
||||
{
|
||||
uop_MOVZX(ir, IREG_flags_op1, IREG_8(fetchdat & 7));
|
||||
|
||||
@@ -622,7 +622,7 @@ static int ropJNL_common(codeblock_t *block, ir_data_t *ir, uint32_t dest_addr,
|
||||
{
|
||||
int jump_uop;
|
||||
int do_unroll = ((NF_SET() ? 1 : 0) == (VF_SET() ? 1 : 0) && codegen_can_unroll(block, ir, next_pc, dest_addr));
|
||||
|
||||
|
||||
switch (codegen_flags_changed ? cpu_state.flags_op : FLAGS_UNKNOWN)
|
||||
{
|
||||
case FLAGS_ZN8:
|
||||
|
||||
@@ -21,7 +21,7 @@ uint32_t ropFADD(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
uop_FP_ENTER(ir);
|
||||
uop_FADD(ir, IREG_ST(0), IREG_ST(0), IREG_ST(src_reg));
|
||||
uop_MOV_IMM(ir, IREG_tag(0), TAG_VALID);
|
||||
|
||||
|
||||
return op_pc;
|
||||
}
|
||||
uint32_t ropFADDr(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
@@ -42,7 +42,7 @@ uint32_t ropFADDP(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fe
|
||||
uop_FADD(ir, IREG_ST(dest_reg), IREG_ST(dest_reg), IREG_ST(0));
|
||||
uop_MOV_IMM(ir, IREG_tag(dest_reg), TAG_VALID);
|
||||
fpu_POP(block, ir);
|
||||
|
||||
|
||||
return op_pc;
|
||||
}
|
||||
|
||||
@@ -128,7 +128,7 @@ uint32_t ropFDIVP(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fe
|
||||
uop_FDIV(ir, IREG_ST(dest_reg), IREG_ST(dest_reg), IREG_ST(0));
|
||||
uop_MOV_IMM(ir, IREG_tag(dest_reg), TAG_VALID);
|
||||
fpu_POP(block, ir);
|
||||
|
||||
|
||||
return op_pc;
|
||||
}
|
||||
uint32_t ropFDIVRP(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
@@ -234,7 +234,7 @@ uint32_t ropFSUBRP(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t f
|
||||
uop_FSUB(ir, IREG_ST(dest_reg), IREG_ST(0), IREG_ST(dest_reg));
|
||||
uop_MOV_IMM(ir, IREG_tag(dest_reg), TAG_VALID);
|
||||
fpu_POP(block, ir);
|
||||
|
||||
|
||||
return op_pc;
|
||||
}
|
||||
|
||||
|
||||
@@ -31,6 +31,6 @@ uint32_t ropFLDZ(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
uop_MOV_DOUBLE_INT(ir, IREG_ST(-1), IREG_temp0);
|
||||
uop_MOV_IMM(ir, IREG_tag(-1), TAG_VALID);
|
||||
fpu_PUSH(block, ir);
|
||||
|
||||
|
||||
return op_pc;
|
||||
}
|
||||
|
||||
@@ -91,7 +91,7 @@ uint32_t ropFSTSW_AX(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t
|
||||
{
|
||||
uop_FP_ENTER(ir);
|
||||
uop_MOV(ir, IREG_AX, IREG_NPXS);
|
||||
|
||||
|
||||
return op_pc;
|
||||
}
|
||||
|
||||
|
||||
@@ -57,7 +57,7 @@ int codegen_can_unroll_full(codeblock_t *block, ir_data_t *ir, uint32_t next_pc,
|
||||
TOP = cpu_state.TOP;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (TOP != cpu_state.TOP)
|
||||
return 0;
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ uint32_t ropJMP_r16(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t
|
||||
{
|
||||
uint32_t offset = (int32_t)(int16_t)fastreadw(cs + op_pc);
|
||||
uint32_t dest_addr = op_pc+2+offset;
|
||||
|
||||
|
||||
dest_addr &= 0xffff;
|
||||
|
||||
if (offset < 0)
|
||||
@@ -40,7 +40,7 @@ uint32_t ropJMP_r32(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t
|
||||
{
|
||||
uint32_t offset = fastreadl(cs + op_pc);
|
||||
uint32_t dest_addr = op_pc+4+offset;
|
||||
|
||||
|
||||
if (offset < 0)
|
||||
codegen_can_unroll(block, ir, op_pc+1, dest_addr);
|
||||
codegen_mark_code_present(block, cs+op_pc, 4);
|
||||
@@ -100,13 +100,13 @@ uint32_t ropCALL_r32(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t
|
||||
uint32_t ret_addr = op_pc + 4;
|
||||
uint32_t dest_addr = ret_addr + offset;
|
||||
int sp_reg;
|
||||
|
||||
|
||||
uop_MOV_IMM(ir, IREG_oldpc, cpu_state.oldpc);
|
||||
sp_reg = LOAD_SP_WITH_OFFSET(ir, -4);
|
||||
uop_MEM_STORE_IMM_32(ir, IREG_SS_base, sp_reg, ret_addr);
|
||||
SUB_SP(ir, 4);
|
||||
uop_MOV_IMM(ir, IREG_pc, dest_addr);
|
||||
|
||||
|
||||
codegen_mark_code_present(block, cs+op_pc, 4);
|
||||
return -1;
|
||||
}
|
||||
@@ -114,7 +114,7 @@ uint32_t ropCALL_r32(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t
|
||||
uint32_t ropRET_16(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
{
|
||||
uop_MOV_IMM(ir, IREG_oldpc, cpu_state.oldpc);
|
||||
|
||||
|
||||
if (stack32)
|
||||
uop_MEM_LOAD_REG(ir, IREG_temp0_W, IREG_SS_base, IREG_ESP);
|
||||
else
|
||||
@@ -130,7 +130,7 @@ uint32_t ropRET_16(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t f
|
||||
uint32_t ropRET_32(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
{
|
||||
uop_MOV_IMM(ir, IREG_oldpc, cpu_state.oldpc);
|
||||
|
||||
|
||||
if (stack32)
|
||||
uop_MEM_LOAD_REG(ir, IREG_pc, IREG_SS_base, IREG_ESP);
|
||||
else
|
||||
@@ -146,7 +146,7 @@ uint32_t ropRET_32(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t f
|
||||
uint32_t ropRET_imm_16(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
{
|
||||
uint16_t offset = fastreadw(cs + op_pc);
|
||||
|
||||
|
||||
uop_MOV_IMM(ir, IREG_oldpc, cpu_state.oldpc);
|
||||
|
||||
if (stack32)
|
||||
@@ -267,7 +267,7 @@ uint32_t ropRETF_imm_32(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint3
|
||||
|
||||
if ((msw&1) && !(cpu_state.eflags&VM_FLAG))
|
||||
return 0;
|
||||
|
||||
|
||||
offset = fastreadw(cs + op_pc);
|
||||
uop_MOV_IMM(ir, IREG_oldpc, cpu_state.oldpc);
|
||||
|
||||
|
||||
@@ -64,7 +64,7 @@ uint32_t ropAND_b_rm(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t
|
||||
if ((fetchdat & 0xc0) == 0xc0)
|
||||
{
|
||||
int src_reg = fetchdat & 7;
|
||||
|
||||
|
||||
uop_AND(ir, IREG_8(dest_reg), IREG_8(dest_reg), IREG_8(src_reg));
|
||||
}
|
||||
else
|
||||
|
||||
@@ -22,13 +22,13 @@ uint32_t ropLEA_16(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t f
|
||||
codegen_mark_code_present(block, cs+op_pc, 1);
|
||||
codegen_generate_ea(ir, op_ea_seg, fetchdat, op_ssegs, &op_pc, op_32, 0);
|
||||
uop_MOV(ir, IREG_16(dest_reg), IREG_eaaddr_W);
|
||||
|
||||
|
||||
return op_pc + 1;
|
||||
}
|
||||
uint32_t ropLEA_32(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
{
|
||||
int dest_reg = (fetchdat >> 3) & 7;
|
||||
|
||||
|
||||
if ((fetchdat & 0xc0) == 0xc0)
|
||||
return 0;
|
||||
|
||||
@@ -44,7 +44,7 @@ uint32_t ropF6(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetch
|
||||
x86seg *target_seg = NULL;
|
||||
uint8_t imm_data;
|
||||
int reg;
|
||||
|
||||
|
||||
if (fetchdat & 0x20)
|
||||
return 0;
|
||||
|
||||
@@ -67,7 +67,7 @@ uint32_t ropF6(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetch
|
||||
{
|
||||
case 0x00: case 0x08: /*TEST*/
|
||||
imm_data = fastreadb(cs + op_pc + 1);
|
||||
|
||||
|
||||
uop_AND_IMM(ir, IREG_flags_res_B, reg, imm_data);
|
||||
uop_MOVZX(ir, IREG_flags_res, IREG_flags_res_B);
|
||||
uop_MOV_IMM(ir, IREG_flags_op, FLAGS_ZN8);
|
||||
@@ -75,7 +75,7 @@ uint32_t ropF6(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetch
|
||||
codegen_flags_changed = 1;
|
||||
codegen_mark_code_present(block, cs+op_pc+1, 1);
|
||||
return op_pc+2;
|
||||
|
||||
|
||||
case 0x10: /*NOT*/
|
||||
uop_XOR_IMM(ir, reg, reg, 0xff);
|
||||
if ((fetchdat & 0xc0) != 0xc0)
|
||||
@@ -321,7 +321,7 @@ uint32_t ropFF_16(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fe
|
||||
uop_MOV_IMM(ir, IREG_flags_op, FLAGS_INC16);
|
||||
}
|
||||
return op_pc+1;
|
||||
|
||||
|
||||
case 0x08: /*DEC*/
|
||||
rebuild_c(ir);
|
||||
codegen_flags_changed = 1;
|
||||
@@ -357,7 +357,7 @@ uint32_t ropFF_16(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fe
|
||||
case 0x20: /*JMP*/
|
||||
uop_MOVZX(ir, IREG_pc, src_reg);
|
||||
return -1;
|
||||
|
||||
|
||||
case 0x28: /*JMP far*/
|
||||
uop_MOVZX(ir, IREG_pc, src_reg);
|
||||
uop_MEM_LOAD_REG_OFFSET(ir, IREG_temp1_W, ireg_seg_base(target_seg), IREG_eaaddr, 2);
|
||||
|
||||
@@ -242,7 +242,7 @@ uint32_t ropMOV_EAX_abs(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint3
|
||||
uop_MEM_LOAD_REG(ir, IREG_EAX, ireg_seg_base(op_ea_seg), IREG_eaaddr);
|
||||
else
|
||||
uop_MEM_LOAD_ABS(ir, IREG_EAX, ireg_seg_base(op_ea_seg), addr);
|
||||
|
||||
|
||||
return op_pc + ((op_32 & 0x200) ? 4 : 2);
|
||||
}
|
||||
|
||||
@@ -421,7 +421,7 @@ uint32_t ropMOV_w_seg(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_
|
||||
uint32_t ropMOV_l_seg(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
{
|
||||
int src_reg;
|
||||
|
||||
|
||||
codegen_mark_code_present(block, cs+op_pc, 1);
|
||||
switch (fetchdat & 0x38)
|
||||
{
|
||||
@@ -490,7 +490,7 @@ uint32_t ropMOV_seg_w(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_
|
||||
}
|
||||
|
||||
uop_MOV_IMM(ir, IREG_oldpc, cpu_state.oldpc);
|
||||
|
||||
|
||||
if ((fetchdat & 0xc0) == 0xc0)
|
||||
{
|
||||
uop_MOV(ir, IREG_temp0_W, IREG_16(fetchdat & 7));
|
||||
@@ -655,11 +655,11 @@ uint32_t ropMOVZX_32_16(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint3
|
||||
uint32_t ropXCHG_AX(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
{
|
||||
int reg2 = IREG_16(opcode & 7);
|
||||
|
||||
|
||||
uop_MOV(ir, IREG_temp0_W, IREG_AX);
|
||||
uop_MOV(ir, IREG_AX, reg2);
|
||||
uop_MOV(ir, reg2, IREG_temp0_W);
|
||||
|
||||
|
||||
return op_pc;
|
||||
}
|
||||
uint32_t ropXCHG_EAX(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
@@ -681,7 +681,7 @@ uint32_t ropXCHG_8(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t f
|
||||
if ((fetchdat & 0xc0) == 0xc0)
|
||||
{
|
||||
int reg2 = IREG_8(fetchdat & 7);
|
||||
|
||||
|
||||
uop_MOV(ir, IREG_temp0_B, reg1);
|
||||
uop_MOV(ir, reg1, reg2);
|
||||
uop_MOV(ir, reg2, IREG_temp0_B);
|
||||
@@ -693,7 +693,7 @@ uint32_t ropXCHG_8(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t f
|
||||
uop_MOV_IMM(ir, IREG_oldpc, cpu_state.oldpc);
|
||||
target_seg = codegen_generate_ea(ir, op_ea_seg, fetchdat, op_ssegs, &op_pc, op_32, 0);
|
||||
codegen_check_seg_write(block, ir, target_seg);
|
||||
|
||||
|
||||
uop_MEM_LOAD_REG(ir, IREG_temp0_B, ireg_seg_base(target_seg), IREG_eaaddr);
|
||||
uop_MEM_STORE_REG(ir, ireg_seg_base(target_seg), IREG_eaaddr, reg1);
|
||||
uop_MOV(ir, reg1, IREG_temp0_B);
|
||||
@@ -761,7 +761,7 @@ uint32_t ropXCHG_32(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t
|
||||
uint32_t ropXLAT(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
{
|
||||
uop_MOV_IMM(ir, IREG_oldpc, cpu_state.oldpc);
|
||||
|
||||
|
||||
uop_MOVZX(ir, IREG_eaaddr, IREG_AL);
|
||||
uop_ADD(ir, IREG_eaaddr, IREG_eaaddr, IREG_EBX);
|
||||
if (!(op_32 & 0x200))
|
||||
|
||||
@@ -58,7 +58,7 @@ static uint32_t shift_common_8(ir_data_t *ir, uint32_t fetchdat, uint32_t op_pc,
|
||||
uop_MOV_IMM(ir, IREG_flags_op, FLAGS_SAR8);
|
||||
uop_MOVZX(ir, IREG_flags_res, IREG_8(dest_reg));
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
@@ -454,7 +454,7 @@ uint32_t ropC0(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetch
|
||||
}
|
||||
imm = fastreadb(cs + op_pc + 1) & 0x1f;
|
||||
codegen_mark_code_present(block, cs+op_pc+1, 1);
|
||||
|
||||
|
||||
if (imm)
|
||||
return shift_common_8(ir, fetchdat, op_pc, target_seg, imm) + 1;
|
||||
return op_pc+1;
|
||||
@@ -477,7 +477,7 @@ uint32_t ropC1_w(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
}
|
||||
imm = fastreadb(cs + op_pc + 1) & 0x1f;
|
||||
codegen_mark_code_present(block, cs+op_pc+1, 1);
|
||||
|
||||
|
||||
if (imm)
|
||||
return shift_common_16(ir, fetchdat, op_pc, target_seg, imm) + 1;
|
||||
return op_pc+1;
|
||||
@@ -501,7 +501,7 @@ uint32_t ropC1_l(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
{
|
||||
uint32_t new_pc;
|
||||
int jump_uop;
|
||||
|
||||
|
||||
LOAD_IMMEDIATE_FROM_RAM_8(block, ir, IREG_temp2, cs + op_pc + 1);
|
||||
uop_AND_IMM(ir, IREG_temp2, IREG_temp2, 0x1f);
|
||||
jump_uop = uop_CMP_IMM_JZ_DEST(ir, IREG_temp2, 0);
|
||||
@@ -515,7 +515,7 @@ uint32_t ropC1_l(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
{
|
||||
uint8_t imm = fastreadb(cs + op_pc + 1) & 0x1f;
|
||||
codegen_mark_code_present(block, cs+op_pc+1, 1);
|
||||
|
||||
|
||||
if (imm)
|
||||
return shift_common_32(ir, fetchdat, op_pc, target_seg, imm) + 1;
|
||||
}
|
||||
@@ -584,7 +584,7 @@ uint32_t ropD2(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetch
|
||||
|
||||
if (!(CL & 0x1f) || !block->ins)
|
||||
return 0;
|
||||
|
||||
|
||||
uop_AND_IMM(ir, IREG_temp2, REG_ECX, 0x1f);
|
||||
uop_CMP_IMM_JZ(ir, IREG_temp2, 0, codegen_exit_rout);
|
||||
|
||||
@@ -706,7 +706,7 @@ uint32_t ropD3_w(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fet
|
||||
|
||||
if (!(CL & 0x1f) || !block->ins)
|
||||
return 0;
|
||||
|
||||
|
||||
uop_AND_IMM(ir, IREG_temp2, REG_ECX, 0x1f);
|
||||
uop_CMP_IMM_JZ(ir, IREG_temp2, 0, codegen_exit_rout);
|
||||
|
||||
@@ -958,7 +958,7 @@ uint32_t ropSHLD_16_imm(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint3
|
||||
}
|
||||
imm = fastreadb(cs + op_pc + 1) & 0x1f;
|
||||
codegen_mark_code_present(block, cs+op_pc+1, 1);
|
||||
|
||||
|
||||
if (!imm)
|
||||
return op_pc+2;
|
||||
|
||||
@@ -1006,7 +1006,7 @@ uint32_t ropSHLD_32_imm(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint3
|
||||
}
|
||||
imm = fastreadb(cs + op_pc + 1) & 0x1f;
|
||||
codegen_mark_code_present(block, cs+op_pc+1, 1);
|
||||
|
||||
|
||||
if (!imm)
|
||||
return op_pc+2;
|
||||
|
||||
@@ -1054,7 +1054,7 @@ uint32_t ropSHRD_16_imm(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint3
|
||||
}
|
||||
imm = fastreadb(cs + op_pc + 1) & 0x1f;
|
||||
codegen_mark_code_present(block, cs+op_pc+1, 1);
|
||||
|
||||
|
||||
if (!imm)
|
||||
return op_pc+2;
|
||||
|
||||
@@ -1102,7 +1102,7 @@ uint32_t ropSHRD_32_imm(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint3
|
||||
}
|
||||
imm = fastreadb(cs + op_pc + 1) & 0x1f;
|
||||
codegen_mark_code_present(block, cs+op_pc+1, 1);
|
||||
|
||||
|
||||
if (!imm)
|
||||
return op_pc+2;
|
||||
|
||||
|
||||
@@ -141,7 +141,7 @@ uint32_t ropPOP_W(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fe
|
||||
{
|
||||
x86seg *target_seg = codegen_generate_ea(ir, op_ea_seg, fetchdat, op_ssegs, &op_pc, op_32, 2);
|
||||
codegen_check_seg_write(block, ir, target_seg);
|
||||
|
||||
|
||||
if (stack32)
|
||||
uop_MEM_LOAD_REG(ir, IREG_temp0_W, IREG_SS_base, IREG_ESP);
|
||||
else
|
||||
@@ -340,7 +340,7 @@ uint32_t ropPUSHA_32(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t
|
||||
uint32_t ropPOPA_16(codeblock_t *block, ir_data_t *ir, uint8_t opcode, uint32_t fetchdat, uint32_t op_32, uint32_t op_pc)
|
||||
{
|
||||
int sp_reg;
|
||||
|
||||
|
||||
uop_MOV_IMM(ir, IREG_oldpc, cpu_state.oldpc);
|
||||
sp_reg = LOAD_SP(ir);
|
||||
uop_MEM_LOAD_REG(ir, IREG_DI, IREG_SS_base, sp_reg);
|
||||
|
||||
@@ -92,14 +92,14 @@ struct
|
||||
|
||||
[IREG_op32] = {REG_DWORD, &cpu_state.op32, REG_INTEGER, REG_PERMANENT},
|
||||
[IREG_ssegsx] = {REG_BYTE, &cpu_state.ssegs, REG_INTEGER, REG_PERMANENT},
|
||||
|
||||
|
||||
[IREG_rm_mod_reg] = {REG_DWORD, &cpu_state.rm_data.rm_mod_reg_data, REG_INTEGER, REG_PERMANENT},
|
||||
|
||||
#ifdef USE_ACYCS
|
||||
[IREG_acycs] = {REG_DWORD, &acycs, REG_INTEGER, REG_PERMANENT},
|
||||
#endif
|
||||
[IREG_cycles] = {REG_DWORD, &cpu_state._cycles, REG_INTEGER, REG_PERMANENT},
|
||||
|
||||
|
||||
[IREG_CS_base] = {REG_DWORD, &cpu_state.seg_cs.base, REG_INTEGER, REG_PERMANENT},
|
||||
[IREG_DS_base] = {REG_DWORD, &cpu_state.seg_ds.base, REG_INTEGER, REG_PERMANENT},
|
||||
[IREG_ES_base] = {REG_DWORD, &cpu_state.seg_es.base, REG_INTEGER, REG_PERMANENT},
|
||||
@@ -113,7 +113,7 @@ struct
|
||||
[IREG_FS_seg] = {REG_WORD, &cpu_state.seg_fs.seg, REG_INTEGER, REG_PERMANENT},
|
||||
[IREG_GS_seg] = {REG_WORD, &cpu_state.seg_gs.seg, REG_INTEGER, REG_PERMANENT},
|
||||
[IREG_SS_seg] = {REG_WORD, &cpu_state.seg_ss.seg, REG_INTEGER, REG_PERMANENT},
|
||||
|
||||
|
||||
[IREG_FPU_TOP] = {REG_DWORD, &cpu_state.TOP, REG_INTEGER, REG_PERMANENT},
|
||||
|
||||
[IREG_ST0] = {REG_FPU_ST_DOUBLE, &cpu_state.ST[0], REG_FP, REG_PERMANENT},
|
||||
@@ -124,7 +124,7 @@ struct
|
||||
[IREG_ST5] = {REG_FPU_ST_DOUBLE, &cpu_state.ST[0], REG_FP, REG_PERMANENT},
|
||||
[IREG_ST6] = {REG_FPU_ST_DOUBLE, &cpu_state.ST[0], REG_FP, REG_PERMANENT},
|
||||
[IREG_ST7] = {REG_FPU_ST_DOUBLE, &cpu_state.ST[0], REG_FP, REG_PERMANENT},
|
||||
|
||||
|
||||
[IREG_tag0] = {REG_FPU_ST_BYTE, &cpu_state.tag[0], REG_INTEGER, REG_PERMANENT},
|
||||
[IREG_tag1] = {REG_FPU_ST_BYTE, &cpu_state.tag[0], REG_INTEGER, REG_PERMANENT},
|
||||
[IREG_tag2] = {REG_FPU_ST_BYTE, &cpu_state.tag[0], REG_INTEGER, REG_PERMANENT},
|
||||
@@ -151,7 +151,7 @@ struct
|
||||
[IREG_MM5x] = {REG_QWORD, &cpu_state.MM[5], REG_FP, REG_PERMANENT},
|
||||
[IREG_MM6x] = {REG_QWORD, &cpu_state.MM[6], REG_FP, REG_PERMANENT},
|
||||
[IREG_MM7x] = {REG_QWORD, &cpu_state.MM[7], REG_FP, REG_PERMANENT},
|
||||
|
||||
|
||||
[IREG_NPXCx] = {REG_WORD, &cpu_state.npxc, REG_INTEGER, REG_PERMANENT},
|
||||
[IREG_NPXSx] = {REG_WORD, &cpu_state.npxs, REG_INTEGER, REG_PERMANENT},
|
||||
|
||||
@@ -179,7 +179,7 @@ struct
|
||||
[IREG_temp1] = {REG_DWORD, (void *)20, REG_INTEGER, REG_VOLATILE},
|
||||
[IREG_temp2] = {REG_DWORD, (void *)24, REG_INTEGER, REG_VOLATILE},
|
||||
[IREG_temp3] = {REG_DWORD, (void *)28, REG_INTEGER, REG_VOLATILE},
|
||||
|
||||
|
||||
[IREG_temp0d] = {REG_DOUBLE, (void *)40, REG_FP, REG_VOLATILE},
|
||||
[IREG_temp1d] = {REG_DOUBLE, (void *)48, REG_FP, REG_VOLATILE},
|
||||
};
|
||||
@@ -187,11 +187,11 @@ struct
|
||||
void codegen_reg_mark_as_required()
|
||||
{
|
||||
int reg;
|
||||
|
||||
|
||||
for (reg = 0; reg < IREG_COUNT; reg++)
|
||||
{
|
||||
int last_version = reg_last_version[reg];
|
||||
|
||||
|
||||
if (last_version > 0 && ireg_data[reg].is_volatile == REG_PERMANENT)
|
||||
reg_version[reg][last_version].flags |= REG_FLAGS_REQUIRED;
|
||||
}
|
||||
@@ -201,7 +201,7 @@ int reg_is_native_size(ir_reg_t ir_reg)
|
||||
{
|
||||
int native_size = ireg_data[IREG_GET_REG(ir_reg.reg)].native_size;
|
||||
int requested_size = IREG_GET_SIZE(ir_reg.reg);
|
||||
|
||||
|
||||
switch (native_size)
|
||||
{
|
||||
case REG_BYTE: case REG_FPU_ST_BYTE:
|
||||
@@ -216,11 +216,11 @@ int reg_is_native_size(ir_reg_t ir_reg)
|
||||
if (sizeof(void *) == 4)
|
||||
return (requested_size == IREG_SIZE_L);
|
||||
return (requested_size == IREG_SIZE_Q);
|
||||
|
||||
|
||||
default:
|
||||
fatal("get_reg_is_native_size: unknown native size %i\n", native_size);
|
||||
}
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -254,7 +254,7 @@ void codegen_reg_reset()
|
||||
host_fp_reg_set.regs[c] = invalid_ir_reg;
|
||||
host_fp_reg_set.dirty[c] = 0;
|
||||
}
|
||||
|
||||
|
||||
reg_dead_list = 0;
|
||||
max_version_refcount = 0;
|
||||
}
|
||||
@@ -308,7 +308,7 @@ static void codegen_reg_load(host_reg_set_t *reg_set, codeblock_t *block, int c,
|
||||
else
|
||||
codegen_direct_read_64(block, reg_set->reg_list[c].reg, ireg_data[IREG_GET_REG(ir_reg.reg)].p);
|
||||
break;
|
||||
|
||||
|
||||
case REG_POINTER:
|
||||
#ifndef RELEASE_BUILD
|
||||
if (ireg_data[IREG_GET_REG(ir_reg.reg)].type != REG_INTEGER)
|
||||
@@ -330,7 +330,7 @@ static void codegen_reg_load(host_reg_set_t *reg_set, codeblock_t *block, int c,
|
||||
else
|
||||
codegen_direct_read_double(block, reg_set->reg_list[c].reg, ireg_data[IREG_GET_REG(ir_reg.reg)].p);
|
||||
break;
|
||||
|
||||
|
||||
case REG_FPU_ST_BYTE:
|
||||
#ifndef RELEASE_BUILD
|
||||
if (ireg_data[IREG_GET_REG(ir_reg.reg)].type != REG_INTEGER)
|
||||
@@ -535,7 +535,7 @@ static void alloc_reg(ir_reg_t ir_reg)
|
||||
host_reg_set_t *reg_set = get_reg_set(ir_reg);
|
||||
int nr_regs = (reg_set == &host_reg_set) ? CODEGEN_HOST_REGS : CODEGEN_HOST_FP_REGS;
|
||||
int c;
|
||||
|
||||
|
||||
for (c = 0; c < nr_regs; c++)
|
||||
{
|
||||
if (IREG_GET_REG(reg_set->regs[c].reg) == IREG_GET_REG(ir_reg.reg))
|
||||
@@ -591,7 +591,7 @@ static void alloc_dest_reg(ir_reg_t ir_reg, int dest_reference)
|
||||
void codegen_reg_alloc_register(ir_reg_t dest_reg_a, ir_reg_t src_reg_a, ir_reg_t src_reg_b, ir_reg_t src_reg_c)
|
||||
{
|
||||
int dest_reference = 0;
|
||||
|
||||
|
||||
host_reg_set.locked = 0;
|
||||
host_fp_reg_set.locked = 0;
|
||||
|
||||
@@ -680,16 +680,16 @@ ir_host_reg_t codegen_reg_alloc_write_reg(codeblock_t *block, ir_reg_t ir_reg)
|
||||
{
|
||||
host_reg_set_t *reg_set = get_reg_set(ir_reg);
|
||||
int c;
|
||||
|
||||
|
||||
if (!reg_is_native_size(ir_reg))
|
||||
{
|
||||
/*Read in parent register so we can do partial accesses to it*/
|
||||
ir_reg_t parent_reg;
|
||||
|
||||
|
||||
parent_reg.reg = IREG_GET_REG(ir_reg.reg) | IREG_SIZE_L;
|
||||
parent_reg.version = ir_reg.version - 1;
|
||||
reg_version[IREG_GET_REG(ir_reg.reg)][ir_reg.version - 1].refcount++;
|
||||
|
||||
|
||||
codegen_reg_alloc_read_reg(block, parent_reg, &c);
|
||||
|
||||
#ifndef RELEASE_BUILD
|
||||
@@ -704,7 +704,7 @@ ir_host_reg_t codegen_reg_alloc_write_reg(codeblock_t *block, ir_reg_t ir_reg)
|
||||
reg_set->dirty[c] = 1;
|
||||
return reg_set->reg_list[c].reg | IREG_GET_SIZE(ir_reg.reg);
|
||||
}
|
||||
|
||||
|
||||
/*Search for previous version in host register*/
|
||||
for (c = 0; c < reg_set->nr_regs; c++)
|
||||
{
|
||||
@@ -720,7 +720,7 @@ ir_host_reg_t codegen_reg_alloc_write_reg(codeblock_t *block, ir_reg_t ir_reg)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (c == reg_set->nr_regs)
|
||||
{
|
||||
/*Search for unused registers*/
|
||||
@@ -729,7 +729,7 @@ ir_host_reg_t codegen_reg_alloc_write_reg(codeblock_t *block, ir_reg_t ir_reg)
|
||||
if (ir_reg_is_invalid(reg_set->regs[c]))
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
if (c == reg_set->nr_regs)
|
||||
{
|
||||
/*No unused registers. Search for an unlocked register*/
|
||||
@@ -746,7 +746,7 @@ ir_host_reg_t codegen_reg_alloc_write_reg(codeblock_t *block, ir_reg_t ir_reg)
|
||||
codegen_reg_writeback(reg_set, block, c, 1);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
reg_set->regs[c].reg = ir_reg.reg;
|
||||
reg_set->regs[c].version = ir_reg.version;
|
||||
reg_set->dirty[c] = 1;
|
||||
@@ -819,7 +819,7 @@ void codegen_reg_flush(ir_data_t *ir, codeblock_t *block)
|
||||
{
|
||||
host_reg_set_t *reg_set;
|
||||
int c;
|
||||
|
||||
|
||||
reg_set = &host_reg_set;
|
||||
for (c = 0; c < reg_set->nr_regs; c++)
|
||||
{
|
||||
@@ -853,7 +853,7 @@ void codegen_reg_flush_invalidate(ir_data_t *ir, codeblock_t *block)
|
||||
{
|
||||
host_reg_set_t *reg_set;
|
||||
int c;
|
||||
|
||||
|
||||
reg_set = &host_reg_set;
|
||||
for (c = 0; c < reg_set->nr_regs; c++)
|
||||
{
|
||||
|
||||
@@ -38,9 +38,9 @@ enum
|
||||
IREG_ea_seg = 15,
|
||||
IREG_op32 = 16,
|
||||
IREG_ssegsx = 17,
|
||||
|
||||
|
||||
IREG_rm_mod_reg = 18,
|
||||
|
||||
|
||||
IREG_acycs = 19,
|
||||
IREG_cycles = 20,
|
||||
|
||||
@@ -70,7 +70,7 @@ enum
|
||||
|
||||
IREG_temp0d = 38,
|
||||
IREG_temp1d = 39,
|
||||
|
||||
|
||||
/*FPU stack registers are physical registers. Use IREG_ST() / IREG_tag()
|
||||
to access.
|
||||
When CODEBLOCK_STATIC_TOP is set, the physical register number will be
|
||||
@@ -85,7 +85,7 @@ enum
|
||||
IREG_ST5 = 45,
|
||||
IREG_ST6 = 46,
|
||||
IREG_ST7 = 47,
|
||||
|
||||
|
||||
IREG_tag0 = 48,
|
||||
IREG_tag1 = 49,
|
||||
IREG_tag2 = 50,
|
||||
@@ -103,7 +103,7 @@ enum
|
||||
IREG_ST5_i64 = 61,
|
||||
IREG_ST6_i64 = 62,
|
||||
IREG_ST7_i64 = 63,
|
||||
|
||||
|
||||
IREG_MM0x = 64,
|
||||
IREG_MM1x = 65,
|
||||
IREG_MM2x = 66,
|
||||
@@ -112,13 +112,13 @@ enum
|
||||
IREG_MM5x = 69,
|
||||
IREG_MM6x = 70,
|
||||
IREG_MM7x = 71,
|
||||
|
||||
|
||||
IREG_NPXCx = 72,
|
||||
IREG_NPXSx = 73,
|
||||
|
||||
|
||||
IREG_flagsx = 74,
|
||||
IREG_eflagsx = 75,
|
||||
|
||||
|
||||
IREG_CS_limit_low = 76,
|
||||
IREG_DS_limit_low = 77,
|
||||
IREG_ES_limit_low = 78,
|
||||
@@ -134,9 +134,9 @@ enum
|
||||
IREG_SS_limit_high = 87,
|
||||
|
||||
IREG_COUNT = 88,
|
||||
|
||||
|
||||
IREG_INVALID = 255,
|
||||
|
||||
|
||||
IREG_AX = IREG_EAX + IREG_SIZE_W,
|
||||
IREG_CX = IREG_ECX + IREG_SIZE_W,
|
||||
IREG_DX = IREG_EDX + IREG_SIZE_W,
|
||||
@@ -155,7 +155,7 @@ enum
|
||||
IREG_CH = IREG_ECX + IREG_SIZE_BH,
|
||||
IREG_DH = IREG_EDX + IREG_SIZE_BH,
|
||||
IREG_BH = IREG_EBX + IREG_SIZE_BH,
|
||||
|
||||
|
||||
IREG_flags_res_W = IREG_flags_res + IREG_SIZE_W,
|
||||
IREG_flags_op1_W = IREG_flags_op1 + IREG_SIZE_W,
|
||||
IREG_flags_op2_W = IREG_flags_op2 + IREG_SIZE_W,
|
||||
@@ -168,7 +168,7 @@ enum
|
||||
IREG_temp1_W = IREG_temp1 + IREG_SIZE_W,
|
||||
IREG_temp2_W = IREG_temp2 + IREG_SIZE_W,
|
||||
IREG_temp3_W = IREG_temp3 + IREG_SIZE_W,
|
||||
|
||||
|
||||
IREG_temp0_B = IREG_temp0 + IREG_SIZE_B,
|
||||
IREG_temp1_B = IREG_temp1 + IREG_SIZE_B,
|
||||
IREG_temp2_B = IREG_temp2 + IREG_SIZE_B,
|
||||
@@ -181,14 +181,14 @@ enum
|
||||
IREG_temp1_Q = IREG_temp1d + IREG_SIZE_Q,
|
||||
|
||||
IREG_eaaddr_W = IREG_eaaddr + IREG_SIZE_W,
|
||||
|
||||
|
||||
IREG_CS_seg_W = IREG_CS_seg + IREG_SIZE_W,
|
||||
IREG_DS_seg_W = IREG_DS_seg + IREG_SIZE_W,
|
||||
IREG_ES_seg_W = IREG_ES_seg + IREG_SIZE_W,
|
||||
IREG_FS_seg_W = IREG_FS_seg + IREG_SIZE_W,
|
||||
IREG_GS_seg_W = IREG_GS_seg + IREG_SIZE_W,
|
||||
IREG_SS_seg_W = IREG_SS_seg + IREG_SIZE_W,
|
||||
|
||||
|
||||
IREG_MM0 = IREG_MM0x + IREG_SIZE_Q,
|
||||
IREG_MM1 = IREG_MM1x + IREG_SIZE_Q,
|
||||
IREG_MM2 = IREG_MM2x + IREG_SIZE_Q,
|
||||
@@ -197,12 +197,12 @@ enum
|
||||
IREG_MM5 = IREG_MM5x + IREG_SIZE_Q,
|
||||
IREG_MM6 = IREG_MM6x + IREG_SIZE_Q,
|
||||
IREG_MM7 = IREG_MM7x + IREG_SIZE_Q,
|
||||
|
||||
|
||||
IREG_NPXC = IREG_NPXCx + IREG_SIZE_W,
|
||||
IREG_NPXS = IREG_NPXSx + IREG_SIZE_W,
|
||||
|
||||
|
||||
IREG_ssegs = IREG_ssegsx + IREG_SIZE_B,
|
||||
|
||||
|
||||
IREG_flags = IREG_flagsx + IREG_SIZE_W,
|
||||
IREG_eflags = IREG_eflagsx + IREG_SIZE_W
|
||||
};
|
||||
@@ -324,7 +324,7 @@ static inline ir_reg_t codegen_reg_read(int reg)
|
||||
{
|
||||
ir_reg_t ireg;
|
||||
reg_version_t *version;
|
||||
|
||||
|
||||
#ifndef RELEASE_BUILD
|
||||
if (IREG_GET_REG(reg) == IREG_INVALID)
|
||||
fatal("codegen_reg_read - IREG_INVALID\n");
|
||||
@@ -354,21 +354,21 @@ static inline ir_reg_t codegen_reg_write(int reg, int uop_nr)
|
||||
ir_reg_t ireg;
|
||||
int last_version = reg_last_version[IREG_GET_REG(reg)];
|
||||
reg_version_t *version;
|
||||
|
||||
|
||||
#ifndef RELEASE_BUILD
|
||||
if (IREG_GET_REG(reg) == IREG_INVALID)
|
||||
fatal("codegen_reg_write - IREG_INVALID\n");
|
||||
#endif
|
||||
ireg.reg = reg;
|
||||
ireg.version = last_version + 1;
|
||||
|
||||
|
||||
if (IREG_GET_REG(reg) > IREG_EBX && last_version && !reg_version[IREG_GET_REG(reg)][last_version].refcount &&
|
||||
!(reg_version[IREG_GET_REG(reg)][last_version].flags & REG_FLAGS_REQUIRED))
|
||||
{
|
||||
if (reg_is_native_size(ireg)) /*Non-native size registers have an implicit dependency on the previous version, so don't add to dead list*/
|
||||
add_to_dead_list(®_version[IREG_GET_REG(reg)][last_version], IREG_GET_REG(reg), last_version);
|
||||
}
|
||||
|
||||
|
||||
reg_last_version[IREG_GET_REG(reg)]++;
|
||||
#ifndef RELEASE_BUILD
|
||||
if (!reg_last_version[IREG_GET_REG(reg)])
|
||||
|
||||
Reference in New Issue
Block a user