fix: dont always flip sign_extend msb

This commit is contained in:
2025-06-10 20:00:07 +09:00
parent 3756ada3e0
commit 037d74ac6a
2 changed files with 44 additions and 7 deletions

View File

@@ -32,14 +32,11 @@ impl ImmediateOperand {
pub fn sign_extend(self) -> Self {
match self {
Self::Byte(_) => {
let sign = self.msb();
let byte = self.flip_sign();
let word = byte.as_word();
if sign {
return word.flip_sign();
return if self.msb() {
self.flip_sign().as_word().flip_sign()
} else {
return word;
}
self.as_word()
};
}
Self::Word(_) => self,
}
@@ -391,6 +388,34 @@ impl std::fmt::Display for Pointer32 {
mod tests {
use super::*;
#[test]
fn add_byte_byte() {
let a = ImmediateOperand::Byte(5);
let b = ImmediateOperand::Byte(7);
assert_eq!(a + b, ImmediateOperand::Byte(5 + 7))
}
#[test]
fn add_word_word() {
let a = ImmediateOperand::Word(5);
let b = ImmediateOperand::Word(7);
assert_eq!(a + b, ImmediateOperand::Word(5 + 7))
}
#[test]
fn add_byte_word() {
let a = ImmediateOperand::Byte(5);
let b = ImmediateOperand::Word(7);
assert_eq!(b + a, ImmediateOperand::Word(5 + 7))
}
#[test]
fn sub_byte_word() {
let a = ImmediateOperand::Byte(5);
let b = ImmediateOperand::Word(7);
assert_eq!(b - a, ImmediateOperand::Word(7 - 5))
}
#[test]
fn test_msb() {
let pos = ImmediateOperand::Byte(1 << 4);
@@ -431,6 +456,13 @@ mod tests {
#[test]
fn test_sign_extend() {
let byte = ImmediateOperand::Byte(0b01010101);
let word = ImmediateOperand::Word(0b0000000001010101);
assert_eq!(byte.sign_extend(), word);
}
#[test]
fn test_sign_extend_neg() {
let byte = ImmediateOperand::Byte(1 << 7);
let word = ImmediateOperand::Word(1 << 15);
assert_eq!(byte.sign_extend(), word);