cache state flags

This commit is contained in:
Fabian 2022-10-29 21:31:31 -05:00
parent 5839152328
commit c6ef3c4c68
6 changed files with 36 additions and 13 deletions

View file

@ -259,6 +259,7 @@ CPU.prototype.wasm_patch = function()
this.clear_tlb = get_import("clear_tlb");
this.full_clear_tlb = get_import("full_clear_tlb");
this.update_state_flags = get_import("update_state_flags");
this.set_tsc = get_import("set_tsc");
this.store_current_tsc = get_import("store_current_tsc");
@ -500,6 +501,8 @@ CPU.prototype.set_state = function(state)
const packed_memory = state[77];
this.unpack_memory(bitmap, packed_memory);
this.update_state_flags();
this.full_clear_tlb();
this.jit_clear_cache();
@ -1091,6 +1094,8 @@ CPU.prototype.load_multiboot = function(buffer)
});
}
this.update_state_flags();
dbg_log("Starting multiboot kernel at:", LOG_CPU);
this.debug.dump_state();
this.debug.dump_regs();

View file

@ -489,6 +489,7 @@ pub unsafe fn iret(is_16: bool) {
adjust_stack_reg(3 * 4);
}
update_state_flags();
handle_irqs();
return;
}
@ -715,6 +716,8 @@ pub unsafe fn iret(is_16: bool) {
*instruction_pointer = new_eip + get_seg_cs();
update_state_flags();
// iret end
handle_irqs();
@ -2438,6 +2441,7 @@ pub unsafe fn switch_seg(reg: i32, selector_raw: i32) -> bool {
if reg == SS {
*stack_size_32 = false;
}
update_state_flags();
return true;
}
@ -2493,6 +2497,7 @@ pub unsafe fn switch_seg(reg: i32, selector_raw: i32) -> bool {
}
*stack_size_32 = descriptor.is_32();
update_state_flags();
}
else if reg == CS {
// handled by switch_cs_real_mode, far_return or far_jump
@ -2529,6 +2534,8 @@ pub unsafe fn switch_seg(reg: i32, selector_raw: i32) -> bool {
*segment_offsets.offset(reg as isize) = descriptor.base();
*sreg.offset(reg as isize) = selector_raw as u16;
update_state_flags();
true
}
@ -2712,11 +2719,15 @@ pub unsafe fn load_pdpte(cr3: i32) {
}
}
pub unsafe fn cpl_changed() { *last_virt_eip = -1; }
pub unsafe fn cpl_changed() {
*last_virt_eip = -1;
update_state_flags();
}
pub unsafe fn update_cs_size(new_size: bool) {
if *is_32 != new_size {
*is_32 = new_size;
update_state_flags();
}
}
@ -2832,7 +2843,6 @@ pub unsafe fn run_instruction0f_32(opcode: i32) { ::gen::interpreter0f::run(opco
pub unsafe fn cycle_internal() {
profiler::stat_increment(CYCLE_INTERNAL);
if !::config::FORCE_DISABLE_JIT {
let state_flags = pack_current_state_flags();
let mut jit_entry = None;
let initial_eip = *instruction_pointer;
@ -2841,7 +2851,7 @@ pub unsafe fn cycle_internal() {
Some(c) => {
let c = c.as_ref();
if state_flags == c.state_flags {
if *state_flags == c.state_flags {
let state = c.state_table[initial_eip as usize & 0xFFF];
if state != u16::MAX {
jit_entry = Some((c.wasm_table_index.to_u16(), state));
@ -2866,7 +2876,7 @@ pub unsafe fn cycle_internal() {
match get_phys_eip() {
Err(()) => dbg_assert!(false),
Ok(phys_eip) => {
let entry = jit::jit_find_cache_entry(phys_eip, state_flags);
let entry = jit::jit_find_cache_entry(phys_eip, *state_flags);
dbg_assert!(entry.wasm_table_index.to_u16() == wasm_table_index);
dbg_assert!(entry.initial_state == initial_state);
},
@ -2934,7 +2944,7 @@ pub unsafe fn cycle_internal() {
Some(c) => {
let c = c.as_ref();
if state_flags == c.state_flags
if *state_flags == c.state_flags
&& c.state_table[initial_eip as usize & 0xFFF] != u16::MAX
{
profiler::stat_increment(RUN_INTERPRETED_PAGE_HAS_ENTRY_AFTER_PAGE_WALK);
@ -2945,7 +2955,7 @@ pub unsafe fn cycle_internal() {
#[cfg(feature = "profiler")]
{
if CHECK_MISSED_ENTRY_POINTS {
jit::check_missed_entry_points(phys_addr, state_flags);
jit::check_missed_entry_points(phys_addr, *state_flags);
}
}
@ -2956,7 +2966,7 @@ pub unsafe fn cycle_internal() {
initial_eip,
phys_addr,
get_seg_cs() as u32,
state_flags,
*state_flags,
*instruction_counter - initial_instruction_counter,
);
@ -3023,8 +3033,7 @@ unsafe fn jit_run_interpreted(phys_addr: u32) {
if CHECK_MISSED_ENTRY_POINTS {
let phys_addr = return_on_pagefault!(get_phys_eip()) as u32;
let state_flags = pack_current_state_flags();
let entry = jit::jit_find_cache_entry(phys_addr, state_flags);
let entry = jit::jit_find_cache_entry(phys_addr, *state_flags);
if entry != jit::CachedCode::NONE {
profiler::stat_increment(RUN_INTERPRETED_MISSED_COMPILED_ENTRY_RUN_INTERPRETED);
@ -3045,9 +3054,10 @@ unsafe fn jit_run_interpreted(phys_addr: u32) {
}
}
pub fn pack_current_state_flags() -> CachedStateFlags {
#[no_mangle]
pub fn update_state_flags() {
unsafe {
CachedStateFlags::of_u32(
*state_flags = CachedStateFlags::of_u32(
(*is_32 as u32) << 0
| (*stack_size_32 as u32) << 1
| ((*cpl == 3) as u32) << 2
@ -4271,6 +4281,8 @@ pub unsafe fn reset_cpu() {
switch_seg(SS, 0x30);
write_reg32(ESP, 0x100);
update_state_flags();
jit::jit_clear_cache(jit::get_jit_state());
}

View file

@ -2,6 +2,7 @@
use cpu::cpu::reg128;
use softfloat::F80;
use state_flags::CachedStateFlags;
pub const reg8: *mut u8 = 64 as *mut u8;
pub const reg16: *mut u16 = 64 as *mut u16;
@ -10,6 +11,7 @@ pub const reg32: *mut i32 = 64 as *mut i32;
pub const last_op1: *mut i32 = 96 as *mut i32;
pub const last_op_size: *mut i32 = 104 as *mut i32;
pub const state_flags: *mut CachedStateFlags = 108 as *mut CachedStateFlags;
pub const last_result: *mut i32 = 112 as *mut i32;
pub const flags_changed: *mut i32 = 116 as *mut i32;

View file

@ -1323,6 +1323,7 @@ pub unsafe fn instr_0F34() {
*segment_limits.offset(SS as isize) = -1i32 as u32;
*segment_offsets.offset(SS as isize) = 0;
*stack_size_32 = true;
update_state_flags();
return;
};
}
@ -1349,6 +1350,7 @@ pub unsafe fn instr_0F35() {
*segment_limits.offset(SS as isize) = -1i32 as u32;
*segment_offsets.offset(SS as isize) = 0;
*stack_size_32 = true;
update_state_flags();
return;
};
}

View file

@ -740,8 +740,9 @@ pub fn jit_force_generate_unsafe(virt_addr: i32) {
let phys_addr = cpu::translate_address_read(virt_addr).unwrap();
record_entry_point(phys_addr);
let cs_offset = cpu::get_seg_cs() as u32;
let state_flags = cpu::pack_current_state_flags();
jit_analyze_and_generate(ctx, virt_addr, phys_addr, cs_offset, state_flags);
jit_analyze_and_generate(ctx, virt_addr, phys_addr, cs_offset, unsafe {
*global_pointers::state_flags
});
}
#[inline(never)]

View file

@ -176,6 +176,7 @@ Hint: Use tests/expect/run.js --accept-all to accept all changes (use git diff t
const START_ADDRESS = 0x1000;
cpu.mem8.set(executable, START_ADDRESS);
cpu.update_state_flags();
cpu.jit_force_generate(START_ADDRESS);
});
}