Add SIGNEXTEND op code

This commit is contained in:
nicksavers 2014-11-06 00:05:57 +01:00
parent 88e044cbbe
commit 5aeade32e2
3 changed files with 105 additions and 1 deletions

View File

@ -293,4 +293,13 @@ public class DataWord implements Comparable<DataWord> {
// Convert result into -1, 0 or 1 as is the convention
return (int) Math.signum(result);
}
public void signExtend(byte k) {
if (k > 31)
throw new IndexOutOfBoundsException();
byte mask = this.sValue().testBit((k * 8) + 7) ? (byte) 0xff : 0;
for (int i = 31; i > k; i--) {
this.data[31 - i] = mask;
}
}
}

View File

@ -280,6 +280,19 @@ public class VM {
program.stackPush(word1);
program.step();
} break;
case SIGNEXTEND: {
DataWord word1 = program.stackPop();
BigInteger k = word1.value();
if (k.compareTo(_32_) < 0) {
DataWord word2 = program.stackPop();
if (logger.isInfoEnabled())
hint = word1 + " " + word2.value();
word2.signExtend(k.byteValue());
program.stackPush(word2);
}
program.step();
} break;
case NOT:{
DataWord word1 = program.stackPop();
word1.bnot();

View File

@ -134,6 +134,88 @@ public class DataWordTest {
System.out.println(result2);
}
@Test
public void testSignExtend1() {
DataWord x = new DataWord(Hex.decode("f2"));
byte k = 0;
String expected = "fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff2";
x.signExtend(k);
System.out.println(x.toString());
assertEquals(expected, x.toString());
}
@Test
public void testSignExtend2() {
DataWord x = new DataWord(Hex.decode("f2"));
byte k = 1;
String expected = "00000000000000000000000000000000000000000000000000000000000000f2";
x.signExtend(k);
System.out.println(x.toString());
assertEquals(expected, x.toString());
}
@Test
public void testSignExtend3() {
byte k = 1;
DataWord x = new DataWord(Hex.decode("0f00ab"));
String expected = "00000000000000000000000000000000000000000000000000000000000000ab";
x.signExtend(k);
System.out.println(x.toString());
assertEquals(expected, x.toString());
}
@Test
public void testSignExtend4() {
byte k = 1;
DataWord x = new DataWord(Hex.decode("ffff"));
String expected = "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff";
x.signExtend(k);
System.out.println(x.toString());
assertEquals(expected, x.toString());
}
@Test
public void testSignExtend5() {
byte k = 3;
DataWord x = new DataWord(Hex.decode("ffffffff"));
String expected = "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff";
x.signExtend(k);
System.out.println(x.toString());
assertEquals(expected, x.toString());
}
@Test
public void testSignExtend6() {
byte k = 3;
DataWord x = new DataWord(Hex.decode("ab02345678"));
String expected = "0000000000000000000000000000000000000000000000000000000002345678";
x.signExtend(k);
System.out.println(x.toString());
assertEquals(expected, x.toString());
}
@Test
public void testSignExtend7() {
byte k = 3;
DataWord x = new DataWord(Hex.decode("ab82345678"));
String expected = "ffffffffffffffffffffffffffffffffffffffffffffffffffffffff82345678";
x.signExtend(k);
System.out.println(x.toString());
assertEquals(expected, x.toString());
}
public static BigInteger pow(BigInteger x, BigInteger y) {
if (y.compareTo(BigInteger.ZERO) < 0)