⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 asm.c

📁 motorola 针对coldfire 5275 评估板的Dbug bootloader源程序
💻 C
📖 第 1 页 / 共 5 页
字号:
            temp = get_value(strg[0],&success,temp_base);
            /* 8-bit */
            if (success && temp >= -128 && temp <= 127)
            {
                ext_word_flag = 1;
                ext_word = (uint16)(temp & 0x00FF);
                if ((*reg2 = get_data_register(strg[2])) != 8)
                    temp = 0x0; /* write Data bit */
                else if ((*reg2 = get_addr_register(strg[2])) != 8)
                    temp = 0x8000;  /* write Addr bit */
                else 
                {
                    error = TRUE;
                    return 0;
                }   
                ext_word = (uint16)(ext_word | temp | (*reg2 << 12) | 0x800);
                strg[2] = &strg[2][2];
                                if (strg[2][0] == '.')
                                {
                                        switch (strg[2][1])
                                        {
                                            case 'L':
                                            case 'l':
                        /* wrote .L above with XXX | 0x800; */
                                                    break; 
                                            default:
                                                    error = TRUE;
                                                    return 0;
                                        }
                                        strg[2] = &strg[2][2];
                                }        
                                if (strg[2][0] == '*')
                                {
                                        switch (strg[2][1])
                                        {
                                                case '1':
                                                        break;
                                                case '2':
                                                        ext_word = ext_word | 0x200;
                                                        break;
                                                case '4':
                                                        ext_word = ext_word | 0x400;
                                                        break;
                                                case '8':
                                                        ext_word = ext_word | 0x600;
                                                        break;
                                                default:
                            error = TRUE;
                            return 0;
                    }
                    strg[2] = &strg[2][2];
                }
                if (strg[2][0] != NULL)
                {
                    error = TRUE;
                    return 0;
                }       
                return 1;
            }
        }   
    }
    return 0;
}
/****************************************************************/
static int
parse_operand (char *temp[], char *raw)
{
    int i, j, parens;
    
    i = j = parens = 0;
    temp[0] = raw;
    temp[1] = temp [2] = NULL;

    if (raw[0] == '(')
    {
        temp[0] = &raw[1];
        parens++;
        i++;
    }       
    while (raw[i] != NULL)
    {
        if (raw[i] == '(' || raw[i] == ',' || raw[i] == ')')
        {
            j++;
                if (raw[i] == '(')
                            parens++;
                        if (raw[i] == ')')
                                parens--;
                        raw[i] = NULL;
                        temp[j] = &raw[i+1];
                }
                i++;
        }
    if (parens != 0)
        return 0;
    else
        return 1;
}
/****************************************************************/
static uint16
get_ea (char *operand, int ea_mask, int force_long)
{
    uint16 ea; 
    int reg, reg2, mode;
    char *tstr[3], raw[MAX_OPERAND];

    strcpy(raw,operand);

    if (is_DRD(&reg, &mode, raw))
    {}
    else if (is_ARD(&reg, &mode, raw))
    {}
    else if (is_ARI(&reg, &mode, raw))
    {}
    else if (is_ARIPO(&reg, &mode, raw))
    {}
    else if (is_ARIPR(&reg, &mode, raw))
    {}
    else if (is_IM(&reg, &mode, raw))
    {
        if (force_long && ext_word_flag)
        {
            ext_long_flag = 1;
            ext_long = (uint32) ext_word;
            ext_word_flag = 0;
        }   
    }
    else if (is_AS_AL(&reg, &mode, raw))
    {}
    else /* Must seperate the operand */     
    {
        if (parse_operand(tstr, raw))
        {
            if (is_ARID_PCID(&reg, &mode, tstr))
            {}
            else if (is_ARII8_PCII8(&reg, &reg2, &mode, tstr))
            {}
            else
            { 
                printf("Invalid operand: %s\n",operand);
                error = TRUE;
                return 0;
            }
        }
        else
        {
            printf("Syntax Error: %s\n",operand);
            error = TRUE;
            return 0;
        }
    }
    if (!(addr_mode & ea_mask))
    {
        error = TRUE;
        printf("Invalid addressing mode for '%s' instruction\n",instruct[0]);
        return 0;
    }
    ea = (uint16)((mode << 3) | reg);
    return ea;
}
/****************************************************************/
void 
afun1 (int ea_mask, uint16 opword) /* funcs already have access to instruct[] */
{
    (void) ea_mask;
    /* This function is used for all instructions 
     * whose opcode is written entirely in the isa table
     * RTS, NOP, HALT, PULSE, RTE 
     */ 

    write_data (16,opword);
}   

/****************************************************************/
void
afun2 (int ea_mask, uint16 opword)
{
    (void) ea_mask;
    /* First opword is known, Second word is immediate data */
    /* STOP #0xDATA                                         */ 

    ext_word = (uint16)get_imm_data(instruct[1],0xFFFF0000);
    if (!error)
    {
        ext_word_flag = 1;
        write_data (16,opword);
        handle_ext_words();
    }
}
/****************************************************************/
void 
afun3 (int ea_mask, uint16 opword)
{
    /* ORI, ANDI, SUBI, ADDI, EORI,*/
    /* ORI #<data>,Dn            */

    if (size_is_long())
    {
        ext_long = get_imm_data(instruct[1],0x0);
        if (!error)
        {
            ext_long_flag = 1;
            afun5(ea_mask,opword);
        }
    }
}   
/****************************************************************/
void
afun4 (int ea_mask, uint16 opword)
{
    /* NEG,NEGX,NOT,SWAP,EXTB */
    /* Dn - source operand       */
    /* opword: XXXXXXXXXXXXX|REG#   */
 
    int Dn;
    (void)ea_mask;
    
    if (size_is_long())
    {
        Dn = get_data_register(instruct[1]);
        if (!reg_error)
        {
            opword = (uint16)(opword | Dn);
            write_data(16,opword);
        }
        else
            printf(ERR_DATA_REG,instruct[1]);
    }
}
/****************************************************************/
void
afun5 (int ea_mask, uint16 opword)
{
    /* Dn - destination operand     */
    /* opword: XXXXXXXXXXXXX|REG#   */

    int Dn;
    (void) ea_mask;

    Dn = get_data_register(instruct[2]);
    if (!reg_error)
    {
        opword = (uint16)(opword | Dn);
        write_data(16,opword);
        handle_ext_words();
    }
    else
        printf(ERR_DATA_REG,instruct[2]);
}
/****************************************************************/
void
afun5b (int ea_mask, uint16 opword)
{
    /* Rn - destination register    */
    /* opword: XXXXXXXXXXXXX|REG#   */

    int Rn;
    (void) ea_mask;

    if ((Rn=get_data_register(instruct[2]))==8)             /* Check is Rn IS NOT a Data register */
    {   
        if ((Rn=get_addr_register(instruct[2])) != 8)       /* Check is Rn IS an Address register */
        {
            opword = (uint16)(opword | Rn | 8 );                    /* Rn is a Address register */
            write_data(16,opword);
            handle_ext_words();
        }
        else
            printf(ERR_REG,instruct[2]);                    /* Rn is NOT a data or address register */
    }
    else
    {
            opword = (uint16)(opword | Rn);                 /* Rn is a Data register */
            write_data(16,opword);
            handle_ext_words();
    }

}
/****************************************************************/
void
afun6 (int ea_mask, uint16 opword)
{
    /* LINK An,#<displacement>      */
    /* opword: XXXXXXXXXXXXX|REG#   */  
    /*         |  displacement  |   */

    int32 disp;

    disp = get_imm_data(instruct[2],0x0);
    if (!error)
    {
                /* 16-bit, -32768 < disp < 32767 */
        if (disp <= 32767 && disp >= -32768)
        {   
            ext_word = (uint16)disp;
            ext_word_flag = 1;
            afun7(ea_mask,opword);
        }
        else
                        printf("Error: displacement larger that 16-bits\n");
    }
}   
/****************************************************************/
void
afun7 (int ea_mask, uint16 opword)
{
    /* UNLK An          */
    /* An - source operand      */
    /* opword: XXXXXXXXXXXXX|REG#   */

    int An;
    (void) ea_mask;

    An = get_addr_register(instruct[1]);
    if (!reg_error)
    {
        opword = (uint16)(opword | An);
        write_data(16,opword);
        handle_ext_words();
    }
    else
        printf(ERR_ADDR_REG,instruct[1]);
}
/****************************************************************/
void
afun8 (int ea_mask, uint16 opword)
{
    /* PEA, JMP, JSR, Scc's */
    /* <ea> - source operand*/
    /* XXXXXXXXXX|mod|reg|  */

    uint16 ea;
    ea = get_ea(instruct[1],ea_mask,0);
    if (!error)
    {
        opword = (uint16)(opword | ea);
        write_data(16,opword);
        handle_ext_words();
    }
}
/****************************************************************/
static void
afun8b (int ea_mask, uint16 opword, int force_long)
{
    /* <ea> - source operand*/
    /* XXXXXXXXXX|mod|reg|  */

    uint16 ea;
    ea = get_ea(instruct[2],ea_mask,force_long);
    if (!error)
    {
        opword = (uint16)(opword | ea);
        write_data(16,opword);
        handle_ext_words();
    }
}
/****************************************************************/
void 
afun9 (int ea_mask, uint16 opword)
{
    /* BTST, BSET, BCHG, BCLR */

    if (instruct[1][0] == '#')  /* BXXX #<data>,<ea> */ 
    {
        ea_mask = EA_DATA1;
        if (strcasecmp(instruct[0],"BTST") == 0)
            opword = 0x0800;
        else if (strcasecmp(instruct[0],"BCHG") == 0)
            opword = 0x0840;
        else if (strcasecmp(instruct[0],"BSET") == 0)
            opword = 0x08C0;
        else             /* BCLR */
            opword = 0x0880;
        
        opword2 = (uint16)get_imm_data(instruct[1],0xffffff00); 
        if (!error)     
        {
            opword2_flag = 1;   /* tell handle_ext_words() that there */
            afun8b(ea_mask,opword,0);       /*    are two opwords */
        }
    }
    else                /* BXXX Dn,<ea> */ 
    {
        if (strcasecmp(instruct[0],"BTST") == 0)
            opword = 0x0100;
        else if (strcasecmp(instruct[0],"BCHG") == 0)
            opword = 0x0140;
        else if (strcasecmp(instruct[0],"BSET") == 0)
            opword = 0x01C0;
        else             /* BCLR */
            opword = 0x0180;

        if (strcasecmp(instruct[0],"BTST") == 0)
            ea_mask = EA_DATA;
        else 
            ea_mask = EA_DATALT1;

        afun17(ea_mask,opword);
    }
}
/****************************************************************/
void
afun10 (int ea_mask,  uint16 opword)
{
    /* CLR, TST, WDDATA    */
    /* XXXXXXXX|SZ|MOD|REG */

    opword = (uint16)(opword & 0xff00); /* clear size bits */
    opword = (uint16)(opword | (size << 6));
    afun8(ea_mask,opword);
}
/****************************************************************/
void
afun11 (int ea_mask, uint16 opword) 
{
    /* EXT.s Dn  */
    /* XXXXXXX|OPM|XXX|REG  */

    switch (size)  /* write OPMODE for each instruction */
    {
        case 0:
            error = TRUE;
            printf("Invalid size specified:  .W or .L only\n");
            break;
        case 1:
            opword = (uint16)(opword | 0x80);
            break;
        case 2:
            opword = (uint16)(opword | 0xC0);
            break;
    }
    if (!error)
        afun4(ea_mask,opword);
}               
/****************************************************************/
void 
afun12 (int ea_mask, uint16 opword)
{
    /* MULU, MULS   */
    /* MULx.s <ea>,Dn */
    /* .W: XXXX|REG|XXX|MOD|REG */
    /* .L: XXXXXXXXXX|MOD|REG   */
    /*     X|RDI|XXXXXXXXXXXX   */

    int Dn;
        
    switch (size)
    {
        case 0:
            error = TRUE;
            printf("Invalid size specified:  .W or .L only\n");
            break;
        case 1:
            if (strcasecmp(instruct[0],"MULS") == 0)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -