2021-02-01 14:31:07 -05:00
|
|
|
#made by zombie
|
|
|
|
#02/01/21
|
|
|
|
|
|
|
|
#0-255 is internal registers and flags and etc
|
|
|
|
# program execcution starts at 256
|
2021-02-03 01:57:23 -05:00
|
|
|
#stack starts at end of memory FILO
|
2021-02-01 14:31:07 -05:00
|
|
|
|
|
|
|
|
|
|
|
import numpy as np
|
2021-02-01 18:50:32 -05:00
|
|
|
import opcodes as ops
|
2021-02-03 01:57:23 -05:00
|
|
|
from registers import Registers
|
2021-02-01 17:14:01 -05:00
|
|
|
np.set_printoptions(threshold=np.inf)
|
2021-02-01 14:31:07 -05:00
|
|
|
|
|
|
|
|
|
|
|
|
2021-02-03 01:57:23 -05:00
|
|
|
class ZombieCPU:
|
|
|
|
_regs = Registers()
|
2021-02-01 14:31:07 -05:00
|
|
|
def __init__(self, memorysize=None, debug=None):
|
|
|
|
self._memorysize = memorysize
|
|
|
|
self._memory = np.zeros(memorysize)
|
|
|
|
self._debug = debug
|
|
|
|
|
2021-02-03 01:57:23 -05:00
|
|
|
|
2021-02-01 14:31:07 -05:00
|
|
|
def reset(self):
|
2021-02-03 01:57:23 -05:00
|
|
|
if self._debug:
|
|
|
|
print('Processor Reseting')
|
2021-02-01 14:31:07 -05:00
|
|
|
self._memory = np.zeros(self._memorysize) #clear memory
|
|
|
|
|
2021-02-03 01:57:23 -05:00
|
|
|
self._regs.esp = self._memorysize - 1 #set stackpointer
|
|
|
|
self._regs.eip = 256 #set instructiojn pointer #fuck you thomas
|
2021-02-01 14:31:07 -05:00
|
|
|
|
|
|
|
def exec(self):
|
2021-02-01 18:50:32 -05:00
|
|
|
Halted = False
|
|
|
|
while not Halted: #change this to if not halt
|
2021-02-01 14:31:07 -05:00
|
|
|
#fetch
|
2021-02-03 01:57:23 -05:00
|
|
|
|
|
|
|
opcode = self._memory[int(self._regs.eip)]
|
|
|
|
address = self._memory[int(self._regs.eip + 1)]
|
|
|
|
value = self._memory[int(self._regs.eip + 2)]
|
2021-02-01 14:31:07 -05:00
|
|
|
|
|
|
|
if self._debug:
|
2021-02-03 01:57:23 -05:00
|
|
|
print(f'Opcode: {opcode}\nAddress: {address}\nValue: {value}\nIP: {self._regs.eip}')
|
2021-02-01 18:50:32 -05:00
|
|
|
|
|
|
|
if opcode == ops.NOP:
|
|
|
|
pass
|
|
|
|
|
|
|
|
elif opcode == ops.HLT:
|
|
|
|
Halted = True
|
2021-02-03 01:57:23 -05:00
|
|
|
if self._debug:
|
|
|
|
print('Processor Halted')
|
2021-02-01 14:31:07 -05:00
|
|
|
|
2021-02-01 18:50:32 -05:00
|
|
|
elif opcode == ops.RST: #reset
|
2021-02-01 14:31:07 -05:00
|
|
|
self.reset()
|
|
|
|
|
2021-02-03 01:57:23 -05:00
|
|
|
elif opcode == ops.DBG: #debug toggle
|
2021-02-01 18:50:32 -05:00
|
|
|
self._debug = value
|
2021-02-01 14:31:07 -05:00
|
|
|
|
2021-02-01 18:50:32 -05:00
|
|
|
elif opcode == ops.LDI: #mov but actually load immediate
|
2021-02-01 14:31:07 -05:00
|
|
|
self.write_memory(address, value)
|
2021-02-03 01:57:23 -05:00
|
|
|
if value == 0:
|
|
|
|
self._regs.flags = self._regs.flags | 0b00000001
|
2021-02-01 14:31:07 -05:00
|
|
|
|
2021-02-01 18:50:32 -05:00
|
|
|
elif opcode == ops.PUSH: #push
|
2021-02-03 01:57:23 -05:00
|
|
|
self.write_memory(self._regs.esp, value) #put value onto stack
|
|
|
|
self._regs.esp -= 1 #dec stackpointer
|
2021-02-01 17:14:01 -05:00
|
|
|
|
2021-02-01 18:50:32 -05:00
|
|
|
elif opcode == ops.POP: #pop
|
2021-02-03 01:57:23 -05:00
|
|
|
self.write_memory(address, self.read_memory_address(self._regs.esp + 1)) #read the last value and put it into address (not the empty space)
|
|
|
|
self._regs.esp += 1 #inc stackpointer
|
|
|
|
|
|
|
|
elif opcode == ops.JMP:
|
|
|
|
self._regs.eip = address - 3
|
|
|
|
|
|
|
|
elif opcode == ops.JZ:
|
|
|
|
if self._regs.flags & 0b00000001:
|
|
|
|
self._regs.eip = address - 3
|
2021-02-01 17:14:01 -05:00
|
|
|
|
2021-02-03 01:57:23 -05:00
|
|
|
self._regs.eip += 3 #increment instruction pointer
|
2021-02-01 14:31:07 -05:00
|
|
|
|
|
|
|
|
|
|
|
def set_memory(self, memory):
|
|
|
|
self._memory = memory
|
|
|
|
def write_memory(self, address, value):
|
|
|
|
self._memory[int(address)] = value
|
|
|
|
def read_memory(self):
|
|
|
|
return self._memory
|
|
|
|
def read_memory_address(self, address):
|
2021-02-01 17:14:01 -05:00
|
|
|
return self._memory[int(address)]
|
2021-02-01 14:31:07 -05:00
|
|
|
|
|
|
|
if __name__ == "__main__":
|
2021-02-03 01:57:23 -05:00
|
|
|
cpu = ZombieCPU(65536, False)
|
2021-02-01 14:31:07 -05:00
|
|
|
cpu.reset()
|
|
|
|
|
|
|
|
#hard coded opcodes
|
2021-02-01 18:50:32 -05:00
|
|
|
cpu.write_memory(256, ops.LDI) #mov
|
2021-02-01 17:14:01 -05:00
|
|
|
cpu.write_memory(257, 27) #address 27
|
|
|
|
cpu.write_memory(258, 105) #105 into ^
|
2021-02-01 18:50:32 -05:00
|
|
|
cpu.write_memory(259, ops.PUSH) #push
|
2021-02-01 17:14:01 -05:00
|
|
|
cpu.write_memory(260, 0) #unused in this op
|
|
|
|
cpu.write_memory(261, 27) #the value at address 27 onto the stack
|
2021-02-01 18:50:32 -05:00
|
|
|
cpu.write_memory(262, ops.POP) #pop
|
2021-02-01 17:14:01 -05:00
|
|
|
cpu.write_memory(263, 100) #into 100
|
|
|
|
cpu.write_memory(264, 0) #unused in this op
|
2021-02-03 01:57:23 -05:00
|
|
|
cpu.write_memory(265, ops.HLT) #jmp
|
2021-02-01 17:14:01 -05:00
|
|
|
|
|
|
|
|
2021-02-01 14:31:07 -05:00
|
|
|
cpu.exec()
|
2021-02-03 01:57:23 -05:00
|
|
|
|
2021-02-01 17:14:01 -05:00
|
|
|
|
|
|
|
#c = Console(cpu.read_memory()) ima finish this later
|
|
|
|
#c.draw()
|
2021-02-01 14:31:07 -05:00
|
|
|
|