add a procedural implementation of rename_execute_retire #12

Merged
programmerjake merged 24 commits from programmerjake/cpu:rename-execute-retire into master 2026-05-22 06:58:09 +00:00
4 changed files with 149283 additions and 135206 deletions
Showing only changes of commit 2363e65564 - Show all commits

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -3219,6 +3219,7 @@ struct MockLoadStoreOpDebugState<C: PhantomConstGet<CpuConfig>> {
is_speculative: Bool,
src_values: HdlOption<Array<TraceAsString<PRegValue>, { COMMON_MOP_SRC_LEN }>>,
dest_value: HdlOption<TraceAsString<PRegValue>>,
cycles_left: UInt<8>,
ran_nonspeculatively: Bool,
sent_cant_cause_cancel: Bool,
sent_output_ready: Bool,
@ -3231,6 +3232,7 @@ struct MockLoadStoreOp<C: PhantomConstCpuConfig> {
is_speculative: bool,
src_values: Option<[SimValue<TraceAsString<PRegValue>>; COMMON_MOP_SRC_LEN]>,
dest_value: Option<SimValue<TraceAsString<PRegValue>>>,
cycles_left: u8,
ran_nonspeculatively: bool,
sent_cant_cause_cancel: bool,
sent_output_ready: bool,
@ -3245,6 +3247,7 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreOp<C> {
is_speculative,
src_values,
dest_value,
cycles_left,
ran_nonspeculatively,
sent_cant_cause_cancel,
sent_output_ready,
@ -3256,6 +3259,7 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreOp<C> {
is_speculative,
src_values,
dest_value,
cycles_left,
ran_nonspeculatively,
sent_cant_cause_cancel,
sent_output_ready,
@ -3275,7 +3279,8 @@ struct MockLoadStoreUnitDebugState<C: PhantomConstGet<CpuConfig>> {
config: C,
}
struct MockLoadStoreUnitState<C: PhantomConstCpuConfig> {
struct MockLoadStoreUnitState<'a, C: PhantomConstCpuConfig> {
random_state: &'a RandomState,
ops: VecDeque<MockLoadStoreOp<C>>,
memory: MockMemory,
speculative_memory: MockMemory,
@ -3283,9 +3288,15 @@ struct MockLoadStoreUnitState<C: PhantomConstCpuConfig> {
unit_index: usize,
}
impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
fn new(config: C, unit_index: usize, memory: MockMemory) -> Self {
impl<'a, C: PhantomConstCpuConfig> MockLoadStoreUnitState<'a, C> {
fn new(
config: C,
unit_index: usize,
memory: MockMemory,
random_state: &'a RandomState,
) -> Self {
Self {
random_state,
ops: VecDeque::new(),
memory: memory.clone(),
speculative_memory: memory,
@ -3296,6 +3307,7 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
#[hdl]
fn debug_state(&self) -> SimValue<MockLoadStoreUnitDebugState<C>> {
let Self {
random_state: _,
ops,
memory,
speculative_memory,
@ -3346,6 +3358,7 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
is_speculative,
src_values,
dest_value,
cycles_left: _,
ran_nonspeculatively: _,
sent_cant_cause_cancel: _,
sent_output_ready: _,
@ -3394,12 +3407,29 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
}
}
}
for op in &mut self.ops {
let MockLoadStoreOp {
mop: _,
is_speculative: _,
src_values: _,
dest_value,
cycles_left,
ran_nonspeculatively: _,
sent_cant_cause_cancel: _,
sent_output_ready: _,
config: _,
} = op;
if dest_value.is_some() {
*cycles_left = cycles_left.saturating_sub(1);
}
}
for op in &mut self.ops {
let MockLoadStoreOp {
mop,
is_speculative,
src_values,
dest_value,
cycles_left: _,
ran_nonspeculatively,
sent_cant_cause_cancel: _,
sent_output_ready: _,
@ -3453,11 +3483,16 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
is_last_mop_in_insn,
mop: mop.into_trace_as_string(),
};
const CYCLE_COUNTS: &[u8; 16] = &[3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 5, 5, 10];
let cycles_left = CYCLE_COUNTS[self.random_state.random_u64(u32::from_le_bytes(*b"lshe"))
as usize
% CYCLE_COUNTS.len()];
self.ops.push_back(MockLoadStoreOp {
mop,
is_speculative: true,
src_values: None,
dest_value: None,
cycles_left,
ran_nonspeculatively: false,
sent_cant_cause_cancel: false,
sent_output_ready: false,
@ -3477,6 +3512,7 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
is_speculative: _,
src_values: op_src_values,
dest_value: _,
cycles_left: _,
ran_nonspeculatively: _,
sent_cant_cause_cancel: _,
sent_output_ready: _,
@ -3497,6 +3533,7 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
is_speculative,
src_values: _,
dest_value: _,
cycles_left: _,
ran_nonspeculatively: _,
sent_cant_cause_cancel: _,
sent_output_ready: _,
@ -3513,6 +3550,7 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
is_speculative: _,
src_values: _,
dest_value,
cycles_left,
ran_nonspeculatively: _,
sent_cant_cause_cancel,
sent_output_ready: _,
@ -3522,7 +3560,7 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
if *sent_cant_cause_cancel {
continue;
}
if dest_value.is_some() {
if dest_value.is_some() && *cycles_left == 0 {
return #[hdl(sim)]
ret_ty.HdlSome(
#[hdl(sim)]
@ -3555,6 +3593,7 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
is_speculative: _,
src_values: _,
dest_value,
cycles_left,
ran_nonspeculatively: _,
sent_cant_cause_cancel: _,
sent_output_ready,
@ -3564,7 +3603,9 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
if *sent_output_ready {
continue;
}
if let Some(dest_value) = dest_value {
if let Some(dest_value) = dest_value
&& *cycles_left == 0
{
return #[hdl(sim)]
ret_ty.HdlSome(
#[hdl(sim)]
@ -3606,13 +3647,14 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
is_speculative: _,
src_values: _,
dest_value: _,
cycles_left,
ran_nonspeculatively,
sent_cant_cause_cancel: _,
sent_output_ready: _,
config: _,
}) = self.ops.front()
{
if *ran_nonspeculatively {
if *ran_nonspeculatively && *cycles_left == 0 {
return #[hdl(sim)]
ret_ty.HdlSome(
#[hdl(sim)]
@ -3646,6 +3688,7 @@ impl<C: PhantomConstCpuConfig> MockLoadStoreUnitState<C> {
}
fn cancel_all(&mut self) {
let Self {
random_state: _,
ops,
memory,
speculative_memory,
@ -3699,6 +3742,10 @@ fn mock_load_store_unit<#[hdl(skip)] MI: MakeInsns>(
),
async |args, mut sim| {
let (cd, from_execute, debug_state, all_outputs_written, config, unit_index) = args;
// intentionally have a different sequence each time we're reset
let random_state = RandomState {
state: Cell::new(0),
};
sim.resettable(
cd,
async |mut sim| {
@ -3758,6 +3805,7 @@ fn mock_load_store_unit<#[hdl(skip)] MI: MakeInsns>(
state,
config,
unit_index,
&random_state,
sim,
)
},
@ -3774,9 +3822,10 @@ fn mock_load_store_unit<#[hdl(skip)] MI: MakeInsns>(
memory: MockMemory,
config: PhantomConst<CpuConfig>,
unit_index: usize,
random_state: &RandomState,
mut sim: ExternModuleSimulationState,
) {
let mut state = MockLoadStoreUnitState::new(config, unit_index, memory);
let mut state = MockLoadStoreUnitState::new(config, unit_index, memory, random_state);
loop {
{
#[hdl]
@ -4142,7 +4191,7 @@ fn test_rename_execute_retire_slow_loop() {
};
sim.write_clock(sim.io().cd.clk, false);
sim.write_reset(sim.io().cd.rst, true);
for cycle in 0..500 {
for cycle in 0..600 {
sim.advance_time(SimDuration::from_nanos(500));
println!("clock tick: {cycle}");
sim.write_clock(sim.io().cd.clk, true);
@ -4280,7 +4329,7 @@ fn test_rename_execute_retire_head_n1() {
};
sim.write_clock(sim.io().cd.clk, false);
sim.write_reset(sim.io().cd.rst, true);
for cycle in 0..200 {
for cycle in 0..300 {
sim.advance_time(SimDuration::from_nanos(500));
println!("clock tick: {cycle}");
sim.write_clock(sim.io().cd.clk, true);