feat(bytecode): +DupFrom
This commit is contained in:
parent
b889f626ab
commit
550c25340d
|
@ -13,10 +13,11 @@ pub enum OpType {
|
|||
Return = 0x52, /* R */
|
||||
|
||||
// stack operations
|
||||
Push = 0x50, /* P */
|
||||
Pop = 0x51, /* Q */
|
||||
Dup = 0x44, /* D */
|
||||
Swap = 0x53, /* S */
|
||||
Push = 0x50, /* P */
|
||||
Pop = 0x51, /* Q */
|
||||
Dup = 0x44, /* D */
|
||||
Swap = 0x53, /* S */
|
||||
DupFrom = 0x46, /* F */
|
||||
|
||||
// extensions
|
||||
Shift = 0x73, /* s */
|
||||
|
|
|
@ -47,6 +47,12 @@ pub enum Instr {
|
|||
/// shifts the top stack value by $0 ($0 is a signed integer)
|
||||
Shift(i8),
|
||||
|
||||
// indirect stack operations
|
||||
/// duplicates the top-(*top) stack value, pushing it to the top of the stack
|
||||
/// this does not change the stack height
|
||||
/// (the top value is replaced by the value it points to)
|
||||
DupFrom,
|
||||
|
||||
/// basic math operations (on integers and atoms)
|
||||
DoMath1(MathUnOp),
|
||||
|
||||
|
@ -69,6 +75,7 @@ impl Instr {
|
|||
Instr::Dup(_) => OpType::Dup,
|
||||
Instr::Swap(_) => OpType::Swap,
|
||||
Instr::Shift(_) => OpType::Shift,
|
||||
Instr::DupFrom => OpType::DupFrom,
|
||||
Instr::DoMath1(_) => OpType::DoMath1,
|
||||
Instr::DoMath2(_) => OpType::DoMath2,
|
||||
}
|
||||
|
@ -115,6 +122,7 @@ impl<'a> crate::Parse<'a> for Instr {
|
|||
OpType::Label => Ok((inp, Instr::Label)),
|
||||
OpType::CallRemote => Ok((inp, Instr::CallRemote)),
|
||||
OpType::Return => Ok((inp, Instr::Return)),
|
||||
OpType::DupFrom => Ok((inp, Instr::DupFrom)),
|
||||
}
|
||||
.map_err(|()| ParseError)
|
||||
}
|
||||
|
@ -136,7 +144,7 @@ impl Instr {
|
|||
Instr::Shift(shv) => writer.write_all(&shv.to_be_bytes()),
|
||||
Instr::DoMath1(val) => writer.write_all(&val.int_value().to_be_bytes()),
|
||||
Instr::DoMath2(val) => writer.write_all(&val.int_value().to_be_bytes()),
|
||||
Instr::Label | Instr::CallRemote | Instr::Return => Ok(()),
|
||||
Instr::Label | Instr::CallRemote | Instr::Return | Instr::DupFrom => Ok(()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -190,6 +190,14 @@ impl Process<'_> {
|
|||
*x >>= (shdelta as u8) + 1;
|
||||
}
|
||||
}
|
||||
Instr::DupFrom => {
|
||||
let x: u64 = self.stack.pop().ok_or(Error::NotEnoughStacked)?;
|
||||
let y: u64 = *self
|
||||
.stack
|
||||
.get(usize::try_from(x).map_err(|_| Error::NotEnoughStacked)?)
|
||||
.ok_or(Error::NotEnoughStacked)?;
|
||||
self.stack.push(y);
|
||||
}
|
||||
Instr::DoMath1(ubo) => {
|
||||
use consts::MathUnOp as U;
|
||||
let x = self.stpop()?;
|
||||
|
|
Loading…
Reference in a new issue