def __init__(self, lineno, asm, arg = None): self.lineno = lineno if asm not in ('DEFB', 'DEFS', 'DEFW'): try: AsmInstruction.__init__(self, asm, arg) except Error, v: error(lineno, v.msg) self.pending = len([x for x in self.arg if isinstance(x, Expr) and x.try_eval() is None]) > 0 if not self.pending: self.arg = self.argval()
def bytes(self): ''' Returns opcodes ''' if self.asm not in ('DEFB', 'DEFS', 'DEFW'): if self.pending: tmp = self.arg # Saves current arg temporarily self.arg = tuple([0] * self.arg_num) result = AsmInstruction.bytes(self) self.arg = tmp # And recovers it return result return AsmInstruction.bytes(self) if self.asm == 'DEFB': if self.pending: return tuple([0] * self.arg_num) return tuple([x & 0xFF for x in self.argval()]) if self.asm == 'DEFS': if self.pending: N = self.arg[0] if isinstance(N, Expr): N = N.eval() return tuple([0] * N) # ?? args = self.argval() num = args[1] & 0xFF return tuple([num] * args[0]) if self.pending: # DEFW return tuple([0] * 2 * self.arg_num) result = () for i in self.argval(): x = i & 0xFFFF result += (x & 0xFF, x >> 8) return result
def argval(self): ''' Solve args values or raise errors if not defined yet ''' if self.asm in ('DEFB', 'DEFS', 'DEFW'): return tuple([x.eval() if isinstance(x, Expr) else x for x in self.arg]) self.arg = tuple([x if not isinstance(x, Expr) else x.eval() for x in self.arg]) if self.asm.split(' ')[0] in ('JR', 'DJNZ'): # A relative jump? if self.arg[0] < -128 or self.arg[0] > 127: error(self.lineno, 'Relative jump out of range') return AsmInstruction.argval(self)