include CS in flat_segments
This commit is contained in:
parent
23a6994a14
commit
eea5cb67b0
3 changed files with 30 additions and 15 deletions
|
|
@ -12,9 +12,11 @@ use regs;
|
||||||
use wasmgen::wasm_builder::{WasmBuilder, WasmLocal, WasmLocalI64};
|
use wasmgen::wasm_builder::{WasmBuilder, WasmLocal, WasmLocalI64};
|
||||||
|
|
||||||
pub fn gen_add_cs_offset(ctx: &mut JitContext) {
|
pub fn gen_add_cs_offset(ctx: &mut JitContext) {
|
||||||
ctx.builder
|
if !ctx.cpu.has_flat_segmentation() {
|
||||||
.load_fixed_i32(global_pointers::get_seg_offset(regs::CS));
|
ctx.builder
|
||||||
ctx.builder.add_i32();
|
.load_fixed_i32(global_pointers::get_seg_offset(regs::CS));
|
||||||
|
ctx.builder.add_i32();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn gen_get_eip(builder: &mut WasmBuilder) {
|
pub fn gen_get_eip(builder: &mut WasmBuilder) {
|
||||||
|
|
@ -1536,9 +1538,11 @@ pub fn gen_get_real_eip(ctx: &mut JitContext) {
|
||||||
ctx.builder.and_i32();
|
ctx.builder.and_i32();
|
||||||
ctx.builder.const_i32(ctx.cpu.eip as i32 & 0xFFF);
|
ctx.builder.const_i32(ctx.cpu.eip as i32 & 0xFFF);
|
||||||
ctx.builder.or_i32();
|
ctx.builder.or_i32();
|
||||||
ctx.builder
|
if !ctx.cpu.has_flat_segmentation() {
|
||||||
.load_fixed_i32(global_pointers::get_seg_offset(regs::CS));
|
ctx.builder
|
||||||
ctx.builder.sub_i32();
|
.load_fixed_i32(global_pointers::get_seg_offset(regs::CS));
|
||||||
|
ctx.builder.sub_i32();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn gen_set_last_op1(builder: &mut WasmBuilder, source: &WasmLocal) {
|
pub fn gen_set_last_op1(builder: &mut WasmBuilder, source: &WasmLocal) {
|
||||||
|
|
|
||||||
|
|
@ -547,6 +547,7 @@ pub unsafe fn iret(is_16: bool) {
|
||||||
cpl_changed();
|
cpl_changed();
|
||||||
|
|
||||||
update_cs_size(false);
|
update_cs_size(false);
|
||||||
|
update_state_flags();
|
||||||
|
|
||||||
// iret end
|
// iret end
|
||||||
return;
|
return;
|
||||||
|
|
@ -1020,6 +1021,8 @@ pub unsafe fn call_interrupt_vector(
|
||||||
handle_irqs();
|
handle_irqs();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
update_state_flags();
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
// call 4 byte cs:ip interrupt vector from ivt at cpu.memory 0
|
// call 4 byte cs:ip interrupt vector from ivt at cpu.memory 0
|
||||||
|
|
@ -1044,6 +1047,7 @@ pub unsafe fn call_interrupt_vector(
|
||||||
|
|
||||||
switch_cs_real_mode(new_cs);
|
switch_cs_real_mode(new_cs);
|
||||||
*instruction_pointer = get_seg_cs() + new_ip;
|
*instruction_pointer = get_seg_cs() + new_ip;
|
||||||
|
update_state_flags();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1070,6 +1074,7 @@ pub unsafe fn far_jump(eip: i32, selector: i32, is_call: bool, is_osize_32: bool
|
||||||
}
|
}
|
||||||
switch_cs_real_mode(selector);
|
switch_cs_real_mode(selector);
|
||||||
*instruction_pointer = get_seg_cs() + eip;
|
*instruction_pointer = get_seg_cs() + eip;
|
||||||
|
update_state_flags();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1309,6 +1314,8 @@ pub unsafe fn far_jump(eip: i32, selector: i32, is_call: bool, is_osize_32: bool
|
||||||
dbg_assert!(*sreg.offset(CS as isize) & 3 == *cpl as u16);
|
dbg_assert!(*sreg.offset(CS as isize) & 3 == *cpl as u16);
|
||||||
|
|
||||||
*instruction_pointer = get_seg_cs() + new_eip;
|
*instruction_pointer = get_seg_cs() + new_eip;
|
||||||
|
|
||||||
|
update_state_flags();
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
dbg_assert!(false);
|
dbg_assert!(false);
|
||||||
|
|
@ -1374,6 +1381,8 @@ pub unsafe fn far_jump(eip: i32, selector: i32, is_call: bool, is_osize_32: bool
|
||||||
*sreg.offset(CS as isize) = selector as u16 & !3 | *cpl as u16;
|
*sreg.offset(CS as isize) = selector as u16 & !3 | *cpl as u16;
|
||||||
|
|
||||||
*instruction_pointer = get_seg_cs() + eip;
|
*instruction_pointer = get_seg_cs() + eip;
|
||||||
|
|
||||||
|
update_state_flags();
|
||||||
}
|
}
|
||||||
|
|
||||||
//dbg_log!("far " + ["jump", "call"][+is_call] + " to:", LOG_CPU)
|
//dbg_log!("far " + ["jump", "call"][+is_call] + " to:", LOG_CPU)
|
||||||
|
|
@ -1395,6 +1404,7 @@ pub unsafe fn far_return(eip: i32, selector: i32, stack_adjust: i32, is_osize_32
|
||||||
switch_cs_real_mode(selector);
|
switch_cs_real_mode(selector);
|
||||||
*instruction_pointer = get_seg_cs() + eip;
|
*instruction_pointer = get_seg_cs() + eip;
|
||||||
adjust_stack_reg(2 * (if is_osize_32 { 4 } else { 2 }) + stack_adjust);
|
adjust_stack_reg(2 * (if is_osize_32 { 4 } else { 2 }) + stack_adjust);
|
||||||
|
update_state_flags();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1520,6 +1530,8 @@ pub unsafe fn far_return(eip: i32, selector: i32, stack_adjust: i32, is_osize_32
|
||||||
|
|
||||||
*instruction_pointer = get_seg_cs() + eip;
|
*instruction_pointer = get_seg_cs() + eip;
|
||||||
|
|
||||||
|
update_state_flags();
|
||||||
|
|
||||||
//dbg_log("far return to:", LOG_CPU)
|
//dbg_log("far return to:", LOG_CPU)
|
||||||
//CPU_LOG_VERBOSE && debug.dump_state("far ret end");
|
//CPU_LOG_VERBOSE && debug.dump_state("far ret end");
|
||||||
}
|
}
|
||||||
|
|
@ -1734,6 +1746,8 @@ pub unsafe fn do_task_switch(selector: i32, error_code: Option<i32>) {
|
||||||
push32(error_code).unwrap();
|
push32(error_code).unwrap();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
update_state_flags();
|
||||||
}
|
}
|
||||||
|
|
||||||
pub unsafe fn after_block_boundary() { jit_block_boundary = true; }
|
pub unsafe fn after_block_boundary() { jit_block_boundary = true; }
|
||||||
|
|
@ -2478,6 +2492,7 @@ pub unsafe fn switch_seg(reg: i32, selector_raw: i32) -> bool {
|
||||||
// es, ds, fs, gs
|
// es, ds, fs, gs
|
||||||
*sreg.offset(reg as isize) = selector_raw as u16;
|
*sreg.offset(reg as isize) = selector_raw as u16;
|
||||||
*segment_is_null.offset(reg as isize) = true;
|
*segment_is_null.offset(reg as isize) = true;
|
||||||
|
update_state_flags();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -2514,7 +2529,6 @@ pub unsafe fn switch_seg(reg: i32, selector_raw: i32) -> bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
*stack_size_32 = descriptor.is_32();
|
*stack_size_32 = descriptor.is_32();
|
||||||
update_state_flags();
|
|
||||||
}
|
}
|
||||||
else if reg == CS {
|
else if reg == CS {
|
||||||
// handled by switch_cs_real_mode, far_return or far_jump
|
// handled by switch_cs_real_mode, far_return or far_jump
|
||||||
|
|
@ -2736,15 +2750,11 @@ pub unsafe fn load_pdpte(cr3: i32) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub unsafe fn cpl_changed() {
|
pub unsafe fn cpl_changed() { *last_virt_eip = -1 }
|
||||||
*last_virt_eip = -1;
|
|
||||||
update_state_flags();
|
|
||||||
}
|
|
||||||
|
|
||||||
pub unsafe fn update_cs_size(new_size: bool) {
|
pub unsafe fn update_cs_size(new_size: bool) {
|
||||||
if *is_32 != new_size {
|
if *is_32 != new_size {
|
||||||
*is_32 = new_size;
|
*is_32 = new_size;
|
||||||
update_state_flags();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -3092,10 +3102,11 @@ pub fn update_state_flags() {
|
||||||
|
|
||||||
#[no_mangle]
|
#[no_mangle]
|
||||||
pub unsafe fn has_flat_segmentation() -> bool {
|
pub unsafe fn has_flat_segmentation() -> bool {
|
||||||
// ss can't be null
|
// cs/ss can't be null
|
||||||
return *segment_offsets.offset(SS as isize) == 0
|
return *segment_offsets.offset(SS as isize) == 0
|
||||||
&& !*segment_is_null.offset(DS as isize)
|
&& !*segment_is_null.offset(DS as isize)
|
||||||
&& *segment_offsets.offset(DS as isize) == 0;
|
&& *segment_offsets.offset(DS as isize) == 0
|
||||||
|
&& *segment_offsets.offset(CS as isize) == 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub unsafe fn run_prefix_instruction() {
|
pub unsafe fn run_prefix_instruction() {
|
||||||
|
|
|
||||||
|
|
@ -265,7 +265,7 @@ enum Imm32 {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn can_optimize_get_seg(ctx: &mut JitContext, segment: u32) -> bool {
|
fn can_optimize_get_seg(ctx: &mut JitContext, segment: u32) -> bool {
|
||||||
(segment == DS || segment == SS) && ctx.cpu.has_flat_segmentation()
|
(segment == DS || segment == SS || segment == CS) && ctx.cpu.has_flat_segmentation()
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn jit_add_seg_offset(ctx: &mut JitContext, default_segment: u32) {
|
pub fn jit_add_seg_offset(ctx: &mut JitContext, default_segment: u32) {
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue