diff --git a/hbbytecode/instructions.in b/hbbytecode/instructions.in index e6a61fa4..f57ce9f0 100644 --- a/hbbytecode/instructions.in +++ b/hbbytecode/instructions.in @@ -54,18 +54,18 @@ 0x35, ANDI, RRD, "Bitand with immediate" ; 0x36, ORI, RRD, "Bitor with immediate" ; 0x37, XORI, RRD, "Bitxor with immediate" ; -0x38, SLUI8, RRW, "Unsigned left bitshift with immedidate (8b)" ; -0x39, SLUI16, RRW, "Unsigned left bitshift with immedidate (16b)"; -0x3A, SLUI32, RRW, "Unsigned left bitshift with immedidate (32b)"; -0x3B, SLUI64, RRW, "Unsigned left bitshift with immedidate (64b)"; -0x3C, SRUI8, RRW, "Unsigned right bitshift with immediate (8b)" ; -0x3D, SRUI16, RRW, "Unsigned right bitshift with immediate (16b)"; -0x3E, SRUI32, RRW, "Unsigned right bitshift with immediate (32b)"; -0x3F, SRUI64, RRW, "Unsigned right bitshift with immediate (64b)"; -0x40, SRSI8, RRW, "Signed right bitshift with immediate" ; -0x41, SRSI16, RRW, "Signed right bitshift with immediate" ; -0x42, SRSI32, RRW, "Signed right bitshift with immediate" ; -0x43, SRSI64, RRW, "Signed right bitshift with immediate" ; +0x38, SLUI8, RRB, "Unsigned left bitshift with immedidate (8b)" ; +0x39, SLUI16, RRB, "Unsigned left bitshift with immedidate (16b)"; +0x3A, SLUI32, RRB, "Unsigned left bitshift with immedidate (32b)"; +0x3B, SLUI64, RRB, "Unsigned left bitshift with immedidate (64b)"; +0x3C, SRUI8, RRB, "Unsigned right bitshift with immediate (8b)" ; +0x3D, SRUI16, RRB, "Unsigned right bitshift with immediate (16b)"; +0x3E, SRUI32, RRB, "Unsigned right bitshift with immediate (32b)"; +0x3F, SRUI64, RRB, "Unsigned right bitshift with immediate (64b)"; +0x40, SRSI8, RRB, "Signed right bitshift with immediate" ; +0x41, SRSI16, RRB, "Signed right bitshift with immediate" ; +0x42, SRSI32, RRB, "Signed right bitshift with immediate" ; +0x43, SRSI64, RRB, "Signed right bitshift with immediate" ; 0x44, CMPUI, RRD, "Unsigned compare with immediate" ; 0x45, CMPSI, RRD, "Signed compare with immediate" ; 0x46, CP, RR, "Copy register" ; diff --git a/hbvm/src/vmrun.rs b/hbvm/src/vmrun.rs index 70d68778..6abc6787 100644 --- a/hbvm/src/vmrun.rs +++ b/hbvm/src/vmrun.rs @@ -85,17 +85,17 @@ where AND => self.binary_op::(ops::BitAnd::bitand), OR => self.binary_op::(ops::BitOr::bitor), XOR => self.binary_op::(ops::BitXor::bitxor), - SLU8 => self.binary_op(|l, r| u8::wrapping_shl(l, r as u32)), - SLU16 => self.binary_op(|l, r| u16::wrapping_shl(l, r as u32)), - SLU32 => self.binary_op(u32::wrapping_shl), - SLU64 => self.binary_op(|l, r| u64::wrapping_shl(l, r as u32)), - SRU8 => self.binary_op(|l, r| u8::wrapping_shr(l, r as u32)), - SRU16 => self.binary_op(|l, r| u16::wrapping_shr(l, r as u32)), - SRU32 => self.binary_op(u32::wrapping_shr), - SRS8 => self.binary_op(|l: i8, r| i8::wrapping_shl(l, r as u32)), - SRS16 => self.binary_op(|l: i16, r| i16::wrapping_shl(l, r as u32)), - SRS32 => self.binary_op(|l: i32, r| i32::wrapping_shl(l, r as u32)), - SRS64 => self.binary_op(|l: i64, r| i64::wrapping_shl(l, r as u32)), + SLU8 => self.binary_op::(ops::Shl::shl), + SLU16 => self.binary_op::(ops::Shl::shl), + SLU32 => self.binary_op::(ops::Shl::shl), + SLU64 => self.binary_op::(ops::Shl::shl), + SRU8 => self.binary_op::(ops::Shr::shr), + SRU16 => self.binary_op::(ops::Shr::shr), + SRU32 => self.binary_op::(ops::Shr::shr), + SRS8 => self.binary_op::(ops::Shr::shr), + SRS16 => self.binary_op::(ops::Shr::shr), + SRS32 => self.binary_op::(ops::Shr::shr), + SRS64 => self.binary_op::(ops::Shr::shr), CMPU => handler!(self, |OpsRRR(tg, a0, a1)| self.cmp( tg, a0, @@ -459,8 +459,8 @@ where /// Perform binary operation over register and shift immediate #[inline(always)] - unsafe fn binary_op_ims(&mut self, op: impl Fn(T, u32) -> T) { - let OpsRRW(tg, reg, imm) = self.decode(); + unsafe fn binary_op_ims(&mut self, op: impl Fn(T, u8) -> T) { + let OpsRRB(tg, reg, imm) = self.decode(); self.write_reg(tg, op(self.read_reg(reg).cast::(), imm)); self.bump_pc::(); } diff --git a/spec.md b/spec.md index 37cd6f93..772373c7 100644 --- a/spec.md +++ b/spec.md @@ -28,10 +28,13 @@ - Xi*n*: Sign-agnostic integer of size *n* bits (Xi8, Xi16, Xi32, Xi64) - Fl*n*: Floating point number of size *n* bits (Fl32, Fl64) -# Behaviours -- Integer operations are always wrapping, including signed numbers +# Behaviour +- Integer operations are wrapping, including signed numbers + - Bitshifts are truncating - Two's complement - Floats as specified by IEEE 754 +- Execution model is implementation defined as long all observable + effects are performed in correct order ## Relative addressing Relative addresses are computed from address of the first byte @@ -51,6 +54,25 @@ of offset in the code. Not from the beginning of current or following instructio | Towards +∞ (up) | 0b10 | | Towards -∞ (down) | 0b11 | +- Remaining values in the byte traps with invalid operand exception + +# Memory +- Memory implementation is implementation-defined +- Zero address (`0x0`) is considered invalid + +# Traps +- Environment call +- Environment breakpoint + +Program counter goes to the following instruction + +## Exceptions +- Memory access fault +- Invalid operand +- Unknown opcode + +Program counter stays on the currently executed instruction + # Instructions - `#n`: register in parameter *n* - `$n`: for immediate in parameter *n* @@ -210,6 +232,10 @@ of offset in the code. Not from the beginning of current or following instructio | 0x36 | ORI | Disjunction (\|) | | 0x37 | XORI | Non-equivalence (^) | +# Register-immediate bitshifts +- Type: `RRB` +- Operation: `#0 ← #1 $2` + ## Unsigned left bitshift (`<<`) | Opcode | Mnemonic | Type | |:-------|:---------|:-----|