Compare commits

...

4 Commits

Author SHA1 Message Date
88a34b87ab fix: исправил проверку выхода за границы памяти 2025-03-29 22:26:57 +03:00
6e3216d16c feat: добавлено выбрасывание исключений в некоторые места
так странно написано потому что я уверен, что будут еще другие исключительные случаи и корнеркейсы, которые я забыл
2025-03-29 22:26:57 +03:00
bdfdfe06da chore: убрал отладочный print в main.py 2025-03-29 22:26:57 +03:00
430db1c2ac fix: всем математические операции помечены как не имеющие доп поля 2025-03-29 22:26:57 +03:00
3 changed files with 19 additions and 10 deletions

View File

@ -15,7 +15,6 @@ def main():
default="out.mem" default="out.mem"
) )
args = parser.parse_args() args = parser.parse_args()
print(args)
with open(args.mem_file, 'rb') as f: with open(args.mem_file, 'rb') as f:
mem = bytearray(f.read()) mem = bytearray(f.read())
vm = VM(mem) vm = VM(mem)

View File

@ -43,13 +43,13 @@ OpD = OpcodeDescription
OPCODES = { OPCODES = {
# block 1 # block 1
0x00: OpD(OpF(0), OpL.MATH, OpA.ADD), 0x00: OpD(OpF.UNEXPANDED, OpL.MATH, OpA.ADD),
0x10: OpD(OpF.QUICK, OpL.MATH, OpA.ADD), 0x10: OpD(OpF.QUICK, OpL.MATH, OpA.ADD),
0x01: OpD(OpF(0), OpL.MATH, OpA.SUB), 0x01: OpD(OpF.UNEXPANDED, OpL.MATH, OpA.SUB),
0x11: OpD(OpF.QUICK, OpL.MATH, OpA.SUB), 0x11: OpD(OpF.QUICK, OpL.MATH, OpA.SUB),
0x02: OpD(OpF(0), OpL.MATH, OpA.MUL), 0x02: OpD(OpF.UNEXPANDED, OpL.MATH, OpA.MUL),
0x12: OpD(OpF.QUICK, OpL.MATH, OpA.MUL), 0x12: OpD(OpF.QUICK, OpL.MATH, OpA.MUL),
0x03: OpD(OpF(0), OpL.MATH, OpA.DIV), 0x03: OpD(OpF.UNEXPANDED, OpL.MATH, OpA.DIV),
0x13: OpD(OpF.QUICK, OpL.MATH, OpA.DIV), 0x13: OpD(OpF.QUICK, OpL.MATH, OpA.DIV),
0x04: OpD(OpF.UNEXPANDED, OpL.MATH, OpA.AND), 0x04: OpD(OpF.UNEXPANDED, OpL.MATH, OpA.AND),
0x05: OpD(OpF.UNEXPANDED, OpL.MATH, OpA.OR), 0x05: OpD(OpF.UNEXPANDED, OpL.MATH, OpA.OR),

View File

@ -57,25 +57,25 @@ class VM:
def __init_callbacks__(self): def __init_callbacks__(self):
VM.instr_callbacks = { VM.instr_callbacks = {
# ariphmetic # ariphmetic
OpD(OpF(0), OpL.MATH, OpA.ADD): OpD(OpF.UNEXPANDED, OpL.MATH, OpA.ADD):
self._math_callback_gen(lambda lhs, rhs: lhs + rhs), self._math_callback_gen(lambda lhs, rhs: lhs + rhs),
OpD(OpF.QUICK, OpL.MATH, OpA.ADD): OpD(OpF.QUICK, OpL.MATH, OpA.ADD):
self._math_quick_callback_gen(lambda lhs, rhs: lhs + rhs), self._math_quick_callback_gen(lambda lhs, rhs: lhs + rhs),
OpD(OpF(0), OpL.MATH, OpA.SUB): OpD(OpF.UNEXPANDED, OpL.MATH, OpA.SUB):
self._math_callback_gen(lambda lhs, rhs: lhs - rhs), self._math_callback_gen(lambda lhs, rhs: lhs - rhs),
OpD(OpF.QUICK, OpL.MATH, OpA.SUB): OpD(OpF.QUICK, OpL.MATH, OpA.SUB):
self._math_quick_callback_gen(lambda lhs, rhs: lhs - rhs), self._math_quick_callback_gen(lambda lhs, rhs: lhs - rhs),
OpD(OpF(0), OpL.MATH, OpA.MUL): OpD(OpF.UNEXPANDED, OpL.MATH, OpA.MUL):
self._math_callback_gen(lambda lhs, rhs: lhs * rhs), self._math_callback_gen(lambda lhs, rhs: lhs * rhs),
OpD(OpF.QUICK, OpL.MATH, OpA.MUL): OpD(OpF.QUICK, OpL.MATH, OpA.MUL):
self._math_quick_callback_gen(lambda lhs, rhs: lhs * rhs), self._math_quick_callback_gen(lambda lhs, rhs: lhs * rhs),
OpD(OpF(0), OpL.MATH, OpA.DIV): OpD(OpF.UNEXPANDED, OpL.MATH, OpA.DIV):
self._math_callback_gen(lambda lhs, rhs: lhs // rhs), self._math_callback_gen(lambda lhs, rhs: lhs // rhs),
OpD(OpF.QUICK, OpL.MATH, OpA.DIV): OpD(OpF.QUICK, OpL.MATH, OpA.DIV):
@ -119,6 +119,11 @@ class VM:
""" """
Make one step (only step into) Make one step (only step into)
""" """
if self.pc.value * 4 > len(self.mem) - 4:
raise VMException(
VMExceptionType.END_OF_MEM,
self.pc.value
)
opcode = self.mem[self.pc.value * 4] opcode = self.mem[self.pc.value * 4]
opdesc = self._fetch_opcode_desc(opcode) opdesc = self._fetch_opcode_desc(opcode)
args = self._parse_arguments(opdesc) args = self._parse_arguments(opdesc)
@ -134,7 +139,7 @@ class VM:
""" """
Continue from current breakpoint Continue from current breakpoint
""" """
while self.pc.value < len(self.mem): while self.pc.value * 4 < len(self.mem):
if self.pc.value in self.breakpoints: if self.pc.value in self.breakpoints:
raise Breakpoint(self.pc.value) raise Breakpoint(self.pc.value)
self.step() self.step()
@ -148,6 +153,11 @@ class VM:
self.continue_() self.continue_()
def _fetch_opcode_desc(self, opcode: int): def _fetch_opcode_desc(self, opcode: int):
if not opcode in OPCODES:
raise VMException(
VMExceptionType.INVALID_OPCODE,
self.pc.value
)
return OPCODES[opcode] return OPCODES[opcode]
def _parse_arguments(self, opdesc: OpcodeDescription) -> tuple[int, ...]: def _parse_arguments(self, opdesc: OpcodeDescription) -> tuple[int, ...]: