Пример #1
0
def Conditional():
    """
    Conditional instructions
    reg,dest
    con,dest
    """

    global Asm

    if MissingOperand():
        return

    val = assem.EvalExpr()[0]

    if not assem.MoreParameters():
        errors.DoError('missoper', False)
        return

    dest = assem.EvalExpr()[0]

    if dec.Asm.Pass == 2:
        if (val < 0 or val > 15):
            # Range error
            errors.DoError('range', False)

# !!!! isz on last 2 locations of page causes jump to next page. Strange but
# true according to page 3-42

    target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1] + (val & 15))
    target.CodeByte(dest)
    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    NoMore()
Пример #2
0
def BitInst():

    global Asm

    if MissingOperand():
        return

    opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1]

    bitno = assem.EvalExpr()[0]

    if dec.Asm.Pass == 2 and (bitno > 7 or bitno < 0):
        assem.DoError('range', False)
        bitno = bitno & 7

    if not assem.MoreParameters():
        errors.DoError('missoper', False)
        return

    datareg = GetReg()
    if datareg[0] > 5:
        assem.DoError('badoper', False)

    datareg = datareg[1]

    target.CodeByte(opcode + BitSwap(bitno))
    target.CodeByte(datareg)

    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    NoMore()
Пример #3
0
def Branch():
    """
    Branching is simply done by copying the second byte of the instruction
    to PCL. Therefore the destination is always on the same page as the second
    byte of the branch instruction.
    """

    global Asm

    if MissingOperand():
        return

    value = assem.EvalExpr()[0]

    if dec.Asm.Instructions[dec.Asm.Mnemonic][1] > 0xFF:
        # It's a 2 byte instruction
        target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1] >> 8)
        offset = 2
    else:
        offset = 1

    if dec.Asm.Pass == 2:
        # Don't check range in pass 1 as label may be forward referenced
        page = (dec.Asm.BOL_Address + offset) >> 8
        destpage = value >> 8
        if page != destpage:
            # Destination not on the same page
            errors.DoError('range', False)

    target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1])
    target.CodeByte(value)
    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    NoMore()
Пример #4
0
def Immediate():
    """
    Immediate operand. May be prefixed by one of the immediate prefixes.
    """

    global Asm

    if MissingOperand():
        return

    prefix = '#'
    if assem.NowChar() in '#/=\\':
        prefix = assem.NowChar(True)

    value = assem.EvalExpr()[0]

    if prefix == '#':
        val = value & 255
    elif prefix == '/':
        val = (value >> 8) & 255
    elif prefix == '=':
        val = (value >> 16) & 255
    else:
        val = (value >> 24) & 255

    if dec.Asm.Instructions[dec.Asm.Mnemonic][1] > 0xFF:
        # It's a 2 byte instruction
        target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1] >> 8)
    target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1])
    target.CodeByte(val)
    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    NoMore()
Пример #5
0
def BranchBit():
    """
    Handle the bit test branch instructions.
    """

    global Asm

    if MissingOperand():
        # We need operands
        return

    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    par1 = GetBit()

    if not assem.MoreParameters():
        # Oops only one operand given
        errors.DoError('missoper', False)
        return

    value = assem.EvalExpr()
    offset = value[0] - dec.Asm.BOL_Address - 3

    if dec.Asm.Pass == 2 and (offset < -128 or offset > 127):
        # Out of range
        errors.DoError('range', False)

    target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1])
    target.CodeByte(par1)
    target.CodeByte(offset)

    NoMore()
Пример #6
0
def LBranch():
    """
    Handle long branch instructions.
    Displacement is destinaiton - current address - 3 in case 3 byte long
    instruction
    Displacement is destinaiton - current address - 4 in case 4 byte long
    instruction
    """

    global Asm

    if MissingOperand():
        return

    opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1]
    value = assem.EvalExpr()
    offset = value[0] - dec.Asm.BOL_Address - 3

    if opcode > 255:
        # It's a 2 byte opcode
        offset = offset - 1
        target.CodeByte(opcode >> 8)
    target.CodeByte(opcode)
    target.CodeWord(offset)
    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    NoMore()
Пример #7
0
def Bits():
    """
    Handle Bit instructions
    Both bit set/clr as well as branch bit set/clr instructions are handled
    by this routine.
    """

    global Asm

    if MissingOperand():
        return

    bitno = assem.EvalExpr()[0]
    opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1] + ((bitno & 7))
    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    if not assem.MoreParameters():
        # We expected more parameters
        errors.DoError('missoper', False)
        return

    param = dec.Asm.Parse_Line[dec.Asm.Parse_Pointer:dec.Asm.Parse_Pointer+2]\
        .upper()

    if param in ('A,', 'X,', 'Y,', 'A ', 'X ', 'Y '):
        assem.NowChar(True)
        if param[0] == 'A':
            mem = 255
        elif param[0] == 'X':
            mem = 128
        else:
            mem = 129
    else:
        mem = assem.EvalExpr()[0]

    if dec.Asm.Mnemonic[1] == 'R':
        # It's a branch instruction
        if not assem.MoreParameters():
            # We expected more parameters
            errors.DoError('missoper', False)
            return
        dest = assem.EvalExpr()[0]
        offset = dest - dec.Asm.BOL_Address - 3

        target.CodeByte(opcode)
        target.CodeByte(mem)
        target.CodeByte(offset)
        if dec.Asm.Pass == 2 and (offset < -128 or offset > +127):
            errors.DoError('range', False)

    else:
        # It wasn't a branch instruction
        target.CodeByte(opcode)
        target.CodeByte(mem)

    if dec.Asm.Pass == 2:
        if (bitno < 0 or bitno > 7) or (mem < 0 or mem > 255):
            errors.DoError('range', False)

    NoMore()
Пример #8
0
def Branch(index):

    """
    Handle branch instructions.
    Displacement is destinaiton - current address - 2
    """

    global Asm

    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][index]
    if dec.Asm.Timing == 0:
        errros.DoError('badopco', False)
        return

    if MissingOperand():
        return

    value = assem.EvalExpr()
    offset = value[0] - dec.Asm.BOL_Address - 2

    if dec.Asm.Pass == 2 and (offset < -128 or offset > 127):
        errors.DoError('range', False)

    target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1])
    target.CodeByte(offset)

    NoMore()
Пример #9
0
def Math():

    global Asm

    if MissingOperand():
        return

    opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1]
    timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    if assem.GetWord().upper() != 'A':
        errors.DoError('badoper', False)
        return

    if not assem.MoreParameters():
        errors.DoError('missoper', False)
        return

    value = GetReg()

    for i in range(0, len(opcode[value[0]]), 2):
        byte = opcode[value[0]][i:i + 2]
        if byte == 'XX':
            target.CodeByte(value[1])
        else:
            target.CodeByte(int(byte, 16))

    dec.Asm.Timing = timing[value[0]]

    NoMore()
Пример #10
0
Файл: crz8.py Проект: Ivoah/6502
def SingleW():

    global Asm

    if MissingOperand():
        return

    reg1 = GetReg()

    if dec.Flags.ErrorInLine:
        # An error was found in parameter 1, no need to continue
        return

    if reg1[0] == 'rr' or reg1[0] == 'R' or reg1[0] == 'r':
        # Operand is register pair
        target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1][0])
        target.CodeByte(reg1[1])
        dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2][0]
        if dec.Asm.Pass == 2 and (reg1[1] & 1) != 0:
            errors.DoError('range', False)
    elif reg1[0] == '@r' or reg1[0] == '@R':
        # Operand is indirect register pair
        target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1][1])
        target.CodeByte(reg1[1])
        dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2][1]
    else:
        errors.DoError('badoper', False)

    NoMore()
Пример #11
0
def Implied():
    """
    Handle implied addressing mode.
    Simply save the opcode and we're done with it.
    """

    global Asm

    opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1]
    if (opcode >> 24) != 0:
        # Save 4 bytes of opcode
        target.CodeByte(opcode >> 24)
        target.CodeByte(opcode >> 16)
        target.CodeByte(opcode >> 8)
        target.CodeByte(opcode)
    elif (opcode >> 16) != 0:
        # Save 3 bytes of opcode
        target.CodeByte(opcode >> 16)
        target.CodeByte(opcode >> 8)
        target.CodeByte(opcode)
    elif (opcode >> 8) != 0:
        # Save 2 bytes of opcode
        target.CodeByte(opcode >> 8)
        target.CodeByte(opcode)
    else:
        # Save 1 byte of opcode
        target.CodeByte(opcode)

    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]
Пример #12
0
def Restart():

    global Asm

    if MissingOperand():
        return

    value = assem.EvalExpr()

    if dec.Flags.ErrorInLine:
        # Save dummy bute to keep passes in sync
        target.CodeByte(0)
    else:
        # No errors were found
        vector = value[0]
        if value[1] and dec.Asm.Pass == 1:
            # Don't bother about range in case of forward referenced in pass 1
            vector = 0
        if vector > 8:
            if vector not in (16, 24, 32, 40, 48, 56):
                errors.DoError('range', False)
                vector = 0
        if vector > 7:
            vector = vector >> 3

        target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1] +
                        (vector << 3))

    NoMore()
Пример #13
0
def Single():

    global Asm

    if MissingOperand():
        return

    opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1]
    timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    value = GetReg()

    if len(opcode[value[0]]) == 0:
        errors.DoError('badoper', False)
        return

    for i in range(0, len(opcode[value[0]]), 2):
        byte = opcode[value[0]][i:i + 2]
        if byte == 'XX':
            target.CodeByte(value[1])
        else:
            target.CodeByte(int(byte, 16))

    dec.Asm.Timing = timing[value[0]]

    NoMore()
Пример #14
0
def Immediate():

    global Asm

    if MissingOperand():
        return

    prefix = assem.NowChar()

    if prefix in '#/=\\':
        prefix = assem.NowChar(True)
    else:
        prefix = '#'

    value = assem.EvalExpr()

    if prefix == '#':
        byte = value[0]
    elif prefix == '/':
        byte = value[0] >> 8
    elif prefix == '=':
        byte = value[0] >> 16
    else:
        byte = value[0] >> 24

    target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1])
    target.CodeByte(byte)

    NoMore()
Пример #15
0
def Branch():

    global Asm

    if MissingOperand():
        return

    operand = GetOperand()

    if operand[0] == 1 or operand[0] == 2:
        # Branch relative
        offset = operand[1] - dec.Asm.BOL_Address - 2

        if dec.Asm.Pass == 2 and (offset < -128 or offset > 127):
            errors.DoError('range', False)

        target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1][0])
        target.CodeByte(offset)
        dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2][0]

    elif operand[0] == 9:
        # Branch [indirect]

        target.CodeWord(dec.Asm.Instructions[dec.Asm.Mnemonic][1][1])
        target.CodeByte(operand[1])
        dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2][1]

    else:
        errors.DoError('badoper', False)
        return

    NoMore()
Пример #16
0
Файл: crz8.py Проект: Ivoah/6502
def Jumps():

    global Asm

    if MissingOperand():
        return

    if assem.NowChar() == '@':
        # It is an indirect jump

        reg1 = GetReg()

        if reg1[0] == '@rr' or reg1[0] == '@R':
            target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1][1])
            target.CodeByte(reg1[1])
            dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2][1]
            if reg1[1] & 1 != 0:
                errors.DoError('range', False)
        else:
            errors.DoError('badoper', False)
    else:
        # It's not an indirect jump
        if dec.Asm.Mnemonic == 'CALL':
            # It's a CALL instruction
            opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1][0]
            dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2][0]

        else:
            # It's JP instruction
            conditions = {'F': 0x00, 'C': 0x70, 'NC': 0xF0, 'Z': 0x60,
                          'NZ': 0xE0, 'PL': 0xD0, 'MI': 0x50, 'OV': 0x40,
                          'NOV': 0xC0, 'EQ': 0x60, 'NE': 0xE0, 'GE': 0x90,
                          'LT': 0x10, 'GT': 0xA0, 'LE': 0x20, 'UGE': 0xF0,
                          'ULT': 0x70, 'UGT': 0xB0, 'ULE': 0x30}

            pointer = dec.Asm.Parse_Pointer
            cond = assem.GetWord().upper()

            if cond in conditions and assem.NowChar() == ',':
                # A legal condition code was given
                opcode = conditions[cond] + 13
                dec.Asm.Timing = '10+'
                if not assem.MoreParameters():
                    errors.DoError('missoper', False)
                    return
            else:
                # No condition was given
                dec.Asm.Parse_Pointer = pointer
                dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2][0]
                opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1][0]

        dest = assem.EvalExpr()

        target.CodeByte(opcode)
        target.CodeWord(dest[0])
        if dec.Asm.Pass == 2 and (dest[0] >> 16) != 0:
            errors.DoError('range', False)

    NoMore()
Пример #17
0
def Load():

    global Asm

    if MissingOperand():
        return

    reg1 = GetReg()

    if dec.Flags.ErrorInLine:
        # An error was found in parameter 1, no need to continue
        return

    if not assem.MoreParameters():
        errors.DoError('missoper', False)
        return

    reg2 = GetReg()

    firstpar = 'LD.' + reg1[0]
    if firstpar in dec.Asm.Instructions:
        secpar = dec.Asm.Instructions[firstpar][0]
        opcode = dec.Asm.Instructions[firstpar][1]
        timing = dec.Asm.Instructions[firstpar][2]
        extra = dec.Asm.Instructions[firstpar][3]

        index = 0
        for t in secpar:
            if t == reg2[0]:
                # Found 2nd parameter, now let's save it to the target file
                opc = opcode[index]
                Code(opc)
                dec.Asm.Timing = timing[index]
                if extra[index] == 1:
                    # save one extra byte from operand 2
                    target.CodeByte(reg2[1])
                elif extra[index] == 2:
                    # save two extra bytes from operand 2
                    target.CodeWord(reg2[1])
                elif extra[index] == 3:
                    # save one extra byte from operand 1
                    target.CodeByte(reg1[1])
                elif extra[index] == 4:
                    # save one extra byte from operand 1 and one from operand 2
                    target.CodeByte(reg1[1])
                    target.CodeByte(reg2[1])
                elif extra[index] == 5:
                    # save two extra bytes from operand 1
                    target.CodeWord(reg1[1])
                NoMore()
                return
            index = index + 1

        # This type of parameter was not allowed as second parameter
        errors.DoError('badoper', False)
    else:
        # This type of parameter was not allowed as first parameter
        errors.DoError('badoper', False)
Пример #18
0
def Code(opcode):
    """
    Write an opcode to the target file.
    If the opcode > 255 then a pre-byte must be saved first
    """

    if opcode > 255:
        target.CodeByte(opcode >> 8)
    target.CodeByte(opcode)
Пример #19
0
def Implied():

    global Asm

    if dec.Asm.Instructions[dec.Asm.Mnemonic][1] > 0xFF:
        # It's a two byte instruction
        target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1] >> 8)
    target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1] & 0xFF)
    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]
Пример #20
0
def MovXInst():
    """
    MOVX   A,@DPTR
    MOV    A,@Ri
    MOV    @DPTR,A
    MOV    @Ri,A
    """

    global Asm

    if MissingOperand():
        # We need some operands
        return

    par1 = GetReg()

    if not assem.MoreParameters():
        # Only one operand given
        errors.DoError('missoper', False)
        return

    par2 = GetReg()

    dec.Asm.Timing = '2'
    if par1[1] == 1:
        # Can be either A,@DPTR or A,@Ri
        if par2[1] == 7:
            # It's A,@DPTR for sure
            target.CodeByte(0xE0)
        elif par2[1] == 3:
            # It's A,@Ri
            target.CodeByte(0xE2 + par2[0])
        else:
            # None of the above
            errors.DoError('badoper', False)
            return
    elif par1[1] == 7:
        # It's @DPTR,A mode
        if par2[1] != 1:
            # Second parameter is not A
            errors.DoError('badoper', False)
            return
        target.CodeByte(0xF0)
    elif par1[1] == 3:
        # It's @Ri,A mode
        if par2[1] != 1:
            # Second parameter is not A
            errors.DoError('badoper', False)
            return
        target.CodeByte(0xF2 + par1[0])
    else:
        # 1st parameter is wrong
        errors.DoError('badoper', False)
        return

    NoMore()
Пример #21
0
def PointerData():
    """
    Pointer pair with data instructions
    pointer,data
    """

    global Asm

    MissingOperand()

    parsepointer = dec.Asm.Parse_Pointer
    pointer = -1

    pntr = assem.GetWord().upper()
    if len(pntr) == 2 and pntr[1] == "P":
        # It might as well be a poiner pair
        if pntr[0] >= '0' and pntr[0] <= '7':
            # It sure is
            pointer = int(pntr[0]) * 2

    if pointer == -1:
        # It wasn't a pointer, so it must be an expression now
        dec.Asm.Parse_Pointer = parsepointer
        pointer = assem.EvalExpr()[0]

    if not assem.MoreParameters():
        errors.DoError('missoper', False)
        return

    prefix = '#'
    if assem.NowChar() in '#/=\\':
        prefix = assem.NowChar(True)

    value = assem.EvalExpr()

    if prefix == '#':
        val = value[0] & 255
    elif prefix == '/':
        val = (value[0] >> 8) & 255
    elif prefix == '=':
        val = (value[0] >> 16) & 255
    else:
        val = (value[0] >> 24) & 255

    if dec.Asm.Pass == 2:
        # Range check only in pass 2
        if pointer < 0 or pointer > 15 or pointer % 2 == 1:
            # Range error
            errors.DoError('range', False)

    target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1] + pointer)
    target.CodeByte(val)
    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    NoMore()
Пример #22
0
def Djnz():
    """
    Handle DJNZ.
    DJNZ has two opcodes in the instruction table. The first one is for
    DJNZ Rx,dest. The second entry is for DJNZ @Rn,dest.
    If indirect mode doesn't exist the opcode for it should be 00.
    """

    global Asm

    if MissingOperand():
        return

    registers = ('R0', 'R1', 'R2', 'R3', 'R4', 'R5', 'R6', 'R7', '@R0', '@R1')
    regname = assem.GetWord().upper()

    if regname in registers:
        index = 0
        for t in registers:
            if t == regname:
                break
            index = index + 1
        if index < 8:
            # direct addressing mode
            opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1][0] + index
        else:
            # indirect addressing mode
            opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1][1]
            if opcode == 0:
                errors.DoError('badoper', False)
                return
            opcode = opcode + (index & 1)
    else:
        errors.DoError('badoper', False)
        return

    if not assem.MoreParameters():
        errors.DoError('missoper', False)
        return

    value = assem.EvalExpr()

    if dec.Asm.Pass == 2:
        temp = (dec.Asm.BOL_Address + 1) >> 8
        dest = value[0] >> 8
        if temp != dest:
            # Destination is not in the same memory page
            errors.DoError('range', False)

    target.CodeByte(opcode)
    target.CodeByte(value[0])
    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    NoMore()
Пример #23
0
def Pairs():
    """
    Handle paired operand instructions.
    """

    global Asm

    if MissingOperand():
        return

    reg1 = assem.GetWord().upper()

    if not assem.MoreParameters():
        errors.DoError('missoper', False)
        return

    if assem.NowChar() == ' ':
        errors.DoError('missoper', False)
        return

    if assem.NowChar() in '#/=\\':
        reg2 = '#'
    else:
        reg2 = assem.GetWord().upper()

    operand = reg1 + ',' + reg2

    operands = dec.Asm.Instructions[dec.Asm.Mnemonic][1]
    opcodes = dec.Asm.Instructions[dec.Asm.Mnemonic][2]
    times = dec.Asm.Instructions[dec.Asm.Mnemonic][3]

    if operand in operands:
        index = 0
        for t in operands:
            if t == operand:
                break
            index = index + 1
        target.CodeByte(opcodes[index])
        dec.Asm.Timing = times[index]
        if reg2 == '#':
            prefix = assem.NowChar(True)
            value = assem.EvalExpr()
            if prefix == '#':
                target.CodeByte(value[0])
            elif prefix == '/':
                target.CodeByte(value[0] >> 8)
            elif prefix == '=':
                target.CodeByte(value[0] >> 16)
            else:
                target.CodeByte(value[0] >> 24)
    else:
        errors.DoError('badoper', False)

    NoMore()
Пример #24
0
def MovBit():
    """
    See if first or second operand is a C.
    If it is it is a bit MOV.
    If it is not return False and parse normal MOV.
    """

    global Asm

    # Save the begin pointer in case're on a dead track
    pntr = dec.Asm.Parse_Pointer
    par1 = assem.GetWord().upper()

    if not assem.MoreParameters():
        # We need 2 paarameters
        errors.DoError('missoper', False)
        return

    if par1 == 'C':
        # First parameter is a C

        bitreg = GetBit()

        target.CodeByte(0xA2)
        target.CodeByte(bitreg)
        dec.Asm.Timing = '1'

        NoMore()

        return True

    par2 = assem.GetWord().upper()

    if par2 == 'C':
        # Second parameter is a C

        endpntr = dec.Asm.Parse_Pointer
        dec.Asm.Parse_Pointer = pntr
        bitreg = GetBit()
        dec.Asm.Parse_Pointer = endpntr

        target.CodeByte(0x92)
        target.CodeByte(bitreg)
        dec.Asm.Timing = '2'

        NoMore()

        return True

    # Nope, it's not MOV C, restore pointer and try again
    dec.Asm.Parse_Pointer = pntr

    return False
Пример #25
0
def Immediate():

    global Asm

    if MissingOperand():
        return

    opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1]
    timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    dest = GetReg()

    if dest[0] > 5:
        errors.DoError('badoper', False)
        return

    if len(opcode[dest[0]]) == 0:
        errors.DoError('badoper', False)
        return

    if not assem.MoreParameters():
        errors.DoError('missoper', False)
        return

    if assem.NowChar() in '#/=\\':
        prefix = assem.NowChar(True)
    else:
        prefix = '#'

    value = assem.EvalExpr()

    for i in range(0, len(opcode[dest[0]]), 2):
        byte = opcode[dest[0]][i:i + 2]
        if byte == 'XX':
            target.CodeByte(dest[1])
        else:
            target.CodeByte(int(byte, 16))

    if prefix == '#':
        data = value[0]
    elif prefix == '/':
        data = value[0] >> 8
    elif prefix == '=':
        data = value[0] >> 16
    else:
        data = value[0] >> 24

    target.CodeByte(data)

    dec.Asm.Timing = timing[dest[0]]

    NoMore()
Пример #26
0
def Exchange():
    """
    Handle EXG and TFR directives.
    Both directives take 2 operands of either 8-bit size or 16-bit size.
    Sizes of the registers may not be mixed.
    """

    global Asm

    if MissingOperand():
        return

    reg1 = assem.GetWord().upper()

    if not assem.MoreParameters():
        errors.DoError('missoper', False)
        return

    reg2 = assem.GetWord().upper()

    words = {
        'A:B': 0,
        'D': 0,
        'X': 1,
        'Y': 2,
        'US': 3,
        'U': 3,
        'SP': 4,
        'S': 4,
        'PC': 5
    }
    bytes = {'A': 8, 'B': 9, 'CC': 10, 'CCR': 10, 'DP': 11, 'DPR': 11}

    if reg1 in words:
        if reg2 in words:
            target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1])
            target.CodeByte((words[reg1] << 4) + words[reg2])
            dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]
        else:
            errors.DoError('badoper', False)
    elif reg1 in bytes:
        if reg2 in bytes:
            target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1])
            target.CodeByte((bytes[reg1] << 4) + bytes[reg2])
            dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]
        else:
            errors.DoError('badoper', False)
    else:
        errors.DoError('badoper', False)

    NoMore()
Пример #27
0
def Move():

    global Asm

    if MissingOperand():
        return

    param = dec.Asm.Parse_Line[dec.Asm.Parse_Pointer:dec.Asm.Parse_Pointer+2]\
        .upper()

    if param in ('A,', 'X,', 'Y,'):
        assem.NowChar(True)
        if param == 'A,':
            dest = 255
        elif param == 'X,':
            dest = 128
        else:
            dest = 129
    else:
        dest = assem.EvalExpr()[0]

    if not assem.MoreParameters():
        # We expected more parameters
        errors.DoError('missoper', False)
        return

    prefix = assem.NowChar(True)

    if prefix not in '#/=\\':
        errors.DoError('badoper', False)
        return

    value = assem.EvalExpr()[0]

    if prefix == '/':
        value = value >> 8
    elif prefix == '=':
        value = value >> 16
    elif prefix == '\\':
        value = value >> 24

    Code(dec.Asm.Instructions[dec.Asm.Mnemonic][1])
    target.CodeByte(dest)
    target.CodeByte(value)

    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    if dest < 0 or dest > 255:
        errors.DoError('range', False)

    NoMore()
Пример #28
0
def MviInst():

    global Asm

    if MissingOperand():
        return

    registers = 'ABCDEHLM'

    reg1 = registers.find(assem.NowChar(True).upper())

    if reg1 < 0:
        errors.DoError('badoper', False)
        return

    if reg1 == 7:
        # timing is different if first operand is M
        dec.Asm.Timing = '9'

    if not assem.MoreParameters():
        errors.DoError('missoper', False)
        return

    if assem.NowChar() == ' ':
        errors.DoError('missoper', False)
        return

    prefix = assem.NowChar()

    if prefix in '#/=\\':
        prefix = assem.NowChar(True)
    else:
        prefix = '#'

    value = assem.EvalExpr()

    if prefix == '#':
        byte = value[0]
    elif prefix == '/':
        byte = value[0] >> 8
    elif prefix == '=':
        byte = value[0] >> 16
    else:
        byte = value[0] >> 24

    NoMore()

    opcode = dec.Asm.Instructions[dec.Asm.Mnemonic][1] + (reg1 << 3)

    target.CodeByte(opcode)
    target.CodeByte(byte)
Пример #29
0
def Immediate2():
    """
    RLDI instruction with immediate operand.
    First operand is the register to be loaded.
    Second operand is the immediate 16 bit data.
    May be prefixed by one of the immediate prefixes.
    """

    global Asm

    if MissingOperand():
        return

    # Get register
    register = assem.EvalExpr()[0]

    if dec.Asm.Pass == 2:
        # Don't check range in pass 1 as label may be forward referenced
        if register < 0 or register > 15:
            register = 0

    if not assem.MoreParameters():
        errors.DoError('missoper', False)
        return

    prefix = '#'
    if assem.NowChar() in '#/=\\':
        prefix = assem.NowChar(True)

    value = assem.EvalExpr()[0]

    if prefix == '#':
        val = value & 0xFFFF
    elif prefix == '/':
        val = (value >> 8) & 0xFFFF
    elif prefix == '=':
        val = (value >> 16) & 0xFFFF
    else:
        val = (value >> 24) & 0xFFFF

    target.CodeByte(dec.Asm.Instructions[dec.Asm.Mnemonic][1] >> 8)
    target.CodeByte((dec.Asm.Instructions[dec.Asm.Mnemonic][1] & 0xFF) +
                    register)
    target.CodeByte(val >> 8)
    target.CodeByte(val & 0xFF)
    dec.Asm.Timing = dec.Asm.Instructions[dec.Asm.Mnemonic][2]

    NoMore()
Пример #30
0
def SaveAll(prebyte, opcode, operand):

    if opcode == 0:
        errors.DoError('badoper', False)
        return

    if prebyte != 0:
        target.CodeByte(prebyte)
    target.CodeByte(opcode)

    if operand[0] in (0, 1, 4, 7, 9, 10, 11, 12, 13, 14):
        target.CodeByte(operand[1])
    elif operand[0] in (2, 5, 8):
        target.CodeWord(operand[1])

    NoMore()