def next(self): if not self._machine_code: raise StopIteration else: self._current_oprt = self._machine_code.next() if self._current_oprt in self.OPRT_R_R: regs = self._machine_code.next() return InstRR(self._current_oprt, hn(regs), ln(regs)) elif self._current_oprt in self.OPRT_R_IMM: reg = self._machine_code.next() imm = mkw(self._machine_code.next(), self._machine_code.next()) return InstRImm(self._current_oprt, hn(reg), i_2c(imm)) elif self._current_oprt in self.OPRT_R: reg = self._machine_code.next() return InstR(self._current_oprt, hn(reg)) elif self._current_oprt in self.OPRT_IMM_1_BYTE: imm = self._machine_code.next() return InstImm(self._current_oprt, i_2c(imm, size=8)) elif self._current_oprt in self.OPRT_IMM_2_BYTE: # operators with one 2-byte imm arg are always 2-byte long self._current_oprt = mkw(self._current_oprt, self._machine_code.next()) imm = mkw(self._machine_code.next(), self._machine_code.next()) return InstImm(self._current_oprt, i_2c(imm)) elif self._current_oprt in self.OPRT_NO_ARG: return InstNoArg(self._current_oprt)
def _ins_decode(self): self._d_dr, self._d_sr = (self._reg_mux(self._ir[1] >> 4), self._reg_mux(self._ir[1] & 0x0f)) # both of _d_xr are str op_code = self._ir[0] & 0x1f if self._ir[0] & 0xe0 == 0: # arithmetic instruction self.__f_single = False self.__f_modify = False self.__f_z = False self.__f_c = False if op_code in self._op_code_z_c_binary_table: self.__f_modify = True self.__f_z = True self.__f_c = True elif op_code in self._op_code_z_c_binary_n_table: self.__f_z = True self.__f_c = True elif op_code in self._op_code_z_binary_table: self.__f_modify = True self.__f_z = True elif op_code in self._op_code_z_binary_n_table: self.__f_z = True elif op_code in self._op_code_z_c_unary_table: self.__f_single = True self.__f_modify = True self.__f_z = True self.__f_c = True elif op_code in self._op_code_z_unary_table: self.__f_single = True self.__f_modify = True self.__f_z = True elif op_code in self._op_code_binary_table: self.__f_modify = True self._alu_func = self._op_codes[op_code] result, carry, zero = self._alu_proc() if self.__f_modify: self.__setattr__(self._d_dr, result) if self.__f_c: self._c_flag = carry if self.__f_z: self._z_flag = zero elif self._ir[0] & 0xe0 == 0x40: # jump instruction absolute, jump = False, False if op_code == 0: # jr jump = True elif op_code == 0x04: # jrc jump = self._c_flag elif op_code == 0x05: jump = not self._c_flag # jrnc elif op_code == 0x02: jump = self._z_flag # jrz elif op_code == 0x03: jump = not self._z_flag # jrnz elif op_code == 0x0f: # jmpa jump = True absolute = True if not absolute: if jump: self._pc += i_2c(self._ir[1], size=8) if absolute: self._pc = i_2c(mkw(*self._next_word())) elif self._ir[0] & 0xe0 == 0x80: # memory instruction if op_code == 0x01: self.__setattr__(self._d_dr, i_2c(mkw(*self._next_word()), size=16))
def report(self): print (' %s ' % self._ins_counter).rjust(8, '-').ljust(60, '-') print 'PC = %04x, IR = %04x' % (self._pc, mkw(*self._ir)) print 'R0 = %04x, R1 = %04x, R2 = %04x, R3 = %04x, R4 = %04x' %\ (self._r0, self._r1, self._r2, self._r3, self._r4) print 'CF = %s, ZF = %s' % (self._c_flag, self._z_flag)
def dump(self): return ('%04x' * 9) % (self._pc, mkw(*self._ir), self._r0, self._r1, self._r2, self._r3, self._r4, self._c_flag, self._z_flag)