3x3 matrix multiplication
This commit is contained in:
@@ -131,7 +131,7 @@ impl PimVM {
|
||||
|
||||
let pim_unit = &mut self.pim_units[pim_unit_index as usize];
|
||||
|
||||
let mut inst = self.kernel.0[pim_unit.pc as usize];
|
||||
let inst = self.kernel.0[pim_unit.pc as usize];
|
||||
|
||||
if pim_unit_index == 0 {
|
||||
log::debug!(
|
||||
@@ -140,38 +140,15 @@ impl PimVM {
|
||||
);
|
||||
}
|
||||
|
||||
pim_unit.pc += 1;
|
||||
|
||||
let aam_grf_a_index = (address >> GRF_A_BIT_OFFSET) & 0b111;
|
||||
let aam_grf_b_index = (address >> GRF_B_BIT_OFFSET) & 0b111;
|
||||
|
||||
// The JUMP instruction is zero-cycle and not actually executed
|
||||
while let Instruction::JUMP { offset, count } = inst {
|
||||
pim_unit.jump_counter = match pim_unit.jump_counter {
|
||||
Some(jump_counter) => jump_counter.checked_sub(1),
|
||||
None => count.checked_sub(1),
|
||||
};
|
||||
|
||||
if pim_unit.jump_counter != None {
|
||||
let new_pc = pim_unit.pc as i32 + offset as i32;
|
||||
|
||||
if new_pc < 0 || new_pc >= 32 {
|
||||
panic!("Invalid PC {new_pc} after JUMP: {inst:?}");
|
||||
}
|
||||
|
||||
pim_unit.pc = new_pc as _;
|
||||
if pim_unit_index == 0 {
|
||||
log::debug!("PimUnit {pim_unit_index} New PC {new_pc}: {inst:?}");
|
||||
}
|
||||
}
|
||||
|
||||
inst = self.kernel.0[pim_unit.pc as usize];
|
||||
pim_unit.pc += 1;
|
||||
}
|
||||
|
||||
match inst {
|
||||
Instruction::NOP => (),
|
||||
Instruction::EXIT => pim_unit.reset(),
|
||||
Instruction::EXIT => {
|
||||
pim_unit.reset();
|
||||
return;
|
||||
}
|
||||
Instruction::JUMP { .. } => unreachable!(),
|
||||
Instruction::MOV { src, dst } | Instruction::FILL { src, dst } => {
|
||||
let data = PimVM::load(src, pim_unit, &bank_data);
|
||||
@@ -267,6 +244,9 @@ impl PimVM {
|
||||
} => {
|
||||
if aam {
|
||||
src1 = if let File::GrfA { index: _ } = src1 {
|
||||
if pim_unit_index == 0 {
|
||||
log::debug!("AAM index GrfA {aam_grf_a_index}");
|
||||
}
|
||||
File::GrfA {
|
||||
index: aam_grf_a_index as _,
|
||||
}
|
||||
@@ -275,6 +255,9 @@ impl PimVM {
|
||||
};
|
||||
|
||||
src2 = if let File::GrfB { index: _ } = src2 {
|
||||
if pim_unit_index == 0 {
|
||||
log::debug!("AAM index GrfB {aam_grf_a_index}");
|
||||
}
|
||||
File::GrfB {
|
||||
index: aam_grf_b_index as _,
|
||||
}
|
||||
@@ -326,6 +309,36 @@ impl PimVM {
|
||||
PimVM::store(dst, pim_unit, &sum);
|
||||
}
|
||||
}
|
||||
|
||||
pim_unit.pc += 1;
|
||||
|
||||
// The JUMP instruction is zero-cycle and not actually executed
|
||||
while let Instruction::JUMP { offset, count } = self.kernel.0[pim_unit.pc as usize] {
|
||||
pim_unit.jump_counter = match pim_unit.jump_counter {
|
||||
Some(jump_counter) => jump_counter.checked_sub(1),
|
||||
None => count.checked_sub(1),
|
||||
};
|
||||
|
||||
if pim_unit.jump_counter != None {
|
||||
let new_pc = pim_unit.pc as i32 + offset as i32;
|
||||
|
||||
if new_pc < 0 || new_pc >= 32 {
|
||||
panic!("Invalid PC {new_pc} after JUMP: {inst:?}");
|
||||
}
|
||||
|
||||
pim_unit.pc = new_pc as _;
|
||||
} else {
|
||||
pim_unit.pc += 1;
|
||||
}
|
||||
|
||||
if pim_unit_index == 0 {
|
||||
log::debug!(
|
||||
"PimUnit {pim_unit_index} JUMP to PC {}: {:?}",
|
||||
pim_unit.pc,
|
||||
self.kernel.0[pim_unit.pc as usize]
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn execute_write(&mut self, bank_index: u32) -> [u8; BURST_LENGTH] {
|
||||
@@ -336,24 +349,24 @@ impl PimVM {
|
||||
};
|
||||
|
||||
let pim_unit = &mut self.pim_units[pim_unit_index as usize];
|
||||
|
||||
let current_pc = pim_unit.pc;
|
||||
pim_unit.pc += 1;
|
||||
|
||||
let inst = &self.kernel.0[current_pc as usize];
|
||||
let inst = self.kernel.0[pim_unit.pc as usize];
|
||||
|
||||
if pim_unit_index == 0 {
|
||||
log::debug!("PimUnit {pim_unit_index} Execute PC {current_pc}: {inst:?}");
|
||||
log::debug!(
|
||||
"PimUnit {pim_unit_index} Execute PC {}: {inst:?}",
|
||||
pim_unit.pc
|
||||
);
|
||||
}
|
||||
|
||||
let data = match inst {
|
||||
Instruction::FILL { src, dst } => {
|
||||
let data: [f16; FP_UNITS] = match src {
|
||||
File::GrfA { index } => pim_unit.grf_a[*index as usize],
|
||||
File::GrfB { index } => pim_unit.grf_b[*index as usize],
|
||||
File::GrfA { index } => pim_unit.grf_a[index as usize],
|
||||
File::GrfB { index } => pim_unit.grf_b[index as usize],
|
||||
_ => panic!("Unsupported src operand: {src:?}"),
|
||||
};
|
||||
|
||||
if *dst != File::Bank {
|
||||
if dst != File::Bank {
|
||||
panic!("Unsupported dst operand: {dst:?}")
|
||||
}
|
||||
|
||||
@@ -366,6 +379,36 @@ impl PimVM {
|
||||
_ => panic!("Unsupported instruction for write: {inst:?}"),
|
||||
};
|
||||
|
||||
pim_unit.pc += 1;
|
||||
|
||||
// The JUMP instruction is zero-cycle and not actually executed
|
||||
while let Instruction::JUMP { offset, count } = self.kernel.0[pim_unit.pc as usize] {
|
||||
pim_unit.jump_counter = match pim_unit.jump_counter {
|
||||
Some(jump_counter) => jump_counter.checked_sub(1),
|
||||
None => count.checked_sub(1),
|
||||
};
|
||||
|
||||
if pim_unit.jump_counter != None {
|
||||
let new_pc = pim_unit.pc as i32 + offset as i32;
|
||||
|
||||
if new_pc < 0 || new_pc >= 32 {
|
||||
panic!("Invalid PC {new_pc} after JUMP: {inst:?}");
|
||||
}
|
||||
|
||||
pim_unit.pc = new_pc as _;
|
||||
} else {
|
||||
pim_unit.pc += 1;
|
||||
}
|
||||
|
||||
if pim_unit_index == 0 {
|
||||
log::debug!(
|
||||
"PimUnit {pim_unit_index} JUMP to PC {}: {:?}",
|
||||
pim_unit.pc,
|
||||
self.kernel.0[pim_unit.pc as usize]
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
unsafe { std::mem::transmute(data) }
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user