comparison 68kinst.c @ 634:4a6ec64acd79

Better support for labels sourced from VOS program module header
author Michael Pavone <pavone@retrodev.com>
date Sat, 11 Oct 2014 22:18:49 -0700
parents 47123183c336
children 22e357678fad
comparison
equal deleted inserted replaced
633:a759f4e38488 634:4a6ec64acd79
1531 "ISP" 1531 "ISP"
1532 #endif 1532 #endif
1533 }; 1533 };
1534 #endif 1534 #endif
1535 1535
1536 int m68k_disasm_op(m68k_op_info *decoded, char *dst, int need_comma, uint8_t labels, uint32_t address) 1536 int m68k_disasm_op(m68k_op_info *decoded, char *dst, int need_comma, uint8_t labels, uint32_t address, format_label_fun label_fun, void * data)
1537 { 1537 {
1538 char * c = need_comma ? "," : ""; 1538 char * c = need_comma ? "," : "";
1539 switch(decoded->addr_mode) 1539 switch(decoded->addr_mode)
1540 { 1540 {
1541 case MODE_REG: 1541 case MODE_REG:
1554 return sprintf(dst, "%s (%d, a%d, %c%d.%c)", c, decoded->params.regs.displacement, decoded->params.regs.pri, (decoded->params.regs.sec & 0x10) ? 'a': 'd', (decoded->params.regs.sec >> 1) & 0x7, (decoded->params.regs.sec & 1) ? 'l': 'w'); 1554 return sprintf(dst, "%s (%d, a%d, %c%d.%c)", c, decoded->params.regs.displacement, decoded->params.regs.pri, (decoded->params.regs.sec & 0x10) ? 'a': 'd', (decoded->params.regs.sec >> 1) & 0x7, (decoded->params.regs.sec & 1) ? 'l': 'w');
1555 case MODE_IMMEDIATE: 1555 case MODE_IMMEDIATE:
1556 case MODE_IMMEDIATE_WORD: 1556 case MODE_IMMEDIATE_WORD:
1557 return sprintf(dst, (decoded->params.immed <= 128 ? "%s #%d" : "%s #$%X"), c, decoded->params.immed); 1557 return sprintf(dst, (decoded->params.immed <= 128 ? "%s #%d" : "%s #$%X"), c, decoded->params.immed);
1558 case MODE_ABSOLUTE_SHORT: 1558 case MODE_ABSOLUTE_SHORT:
1559 if (labels) { 1559 if (labels) {
1560 return sprintf(dst, "%s ADR_%X.w", c, decoded->params.immed); 1560 int ret = sprintf(dst, "%s ", c);
1561 ret += label_fun(dst+ret, decoded->params.immed, data);
1562 strcat(dst+ret, ".w");
1563 return ret + 2;
1561 } else { 1564 } else {
1562 return sprintf(dst, "%s $%X.w", c, decoded->params.immed); 1565 return sprintf(dst, "%s $%X.w", c, decoded->params.immed);
1563 } 1566 }
1564 case MODE_ABSOLUTE: 1567 case MODE_ABSOLUTE:
1565 if (labels) { 1568 if (labels) {
1566 return sprintf(dst, "%s ADR_%X.l", c, decoded->params.immed); 1569 int ret = sprintf(dst, "%s ", c);
1570 ret += label_fun(dst+ret, decoded->params.immed, data);
1571 strcat(dst+ret, ".l");
1572 return ret + 2;
1567 } else { 1573 } else {
1568 return sprintf(dst, "%s $%X", c, decoded->params.immed); 1574 return sprintf(dst, "%s $%X", c, decoded->params.immed);
1569 } 1575 }
1570 case MODE_PC_DISPLACE: 1576 case MODE_PC_DISPLACE:
1571 if (labels) { 1577 if (labels) {
1572 return sprintf(dst, "%s ADR_%X(pc)", c, address + 2 + decoded->params.regs.displacement); 1578 int ret = sprintf(dst, "%s ", c);
1579 ret += label_fun(dst+ret, address + 2 + decoded->params.regs.displacement, data);
1580 strcat(dst+ret, "(pc)");
1581 return ret + 4;
1573 } else { 1582 } else {
1574 return sprintf(dst, "%s (%d, pc)", c, decoded->params.regs.displacement); 1583 return sprintf(dst, "%s (%d, pc)", c, decoded->params.regs.displacement);
1575 } 1584 }
1576 case MODE_PC_INDEX_DISP8: 1585 case MODE_PC_INDEX_DISP8:
1577 return sprintf(dst, "%s (%d, pc, %c%d.%c)", c, decoded->params.regs.displacement, (decoded->params.regs.sec & 0x10) ? 'a': 'd', (decoded->params.regs.sec >> 1) & 0x7, (decoded->params.regs.sec & 1) ? 'l': 'w'); 1586 return sprintf(dst, "%s (%d, pc, %c%d.%c)", c, decoded->params.regs.displacement, (decoded->params.regs.sec & 0x10) ? 'a': 'd', (decoded->params.regs.sec >> 1) & 0x7, (decoded->params.regs.sec & 1) ? 'l': 'w');
1578 default: 1587 default:
1579 return 0; 1588 return 0;
1580 } 1589 }
1581 } 1590 }
1582 1591
1583 int m68k_disasm_movem_op(m68k_op_info *decoded, m68k_op_info *other, char *dst, int need_comma, uint8_t labels, uint32_t address) 1592 int m68k_disasm_movem_op(m68k_op_info *decoded, m68k_op_info *other, char *dst, int need_comma, uint8_t labels, uint32_t address, format_label_fun label_fun, void * data)
1584 { 1593 {
1585 int8_t dir, reg, bit, regnum, last=-1, lastreg, first=-1; 1594 int8_t dir, reg, bit, regnum, last=-1, lastreg, first=-1;
1586 char *rtype, *last_rtype; 1595 char *rtype, *last_rtype;
1587 int oplen; 1596 int oplen;
1588 if (decoded->addr_mode == MODE_REG) { 1597 if (decoded->addr_mode == MODE_REG) {
1632 if (last >= 0 && last != first) { 1641 if (last >= 0 && last != first) {
1633 oplen += sprintf(dst + oplen, "-%s%d", last_rtype, last); 1642 oplen += sprintf(dst + oplen, "-%s%d", last_rtype, last);
1634 } 1643 }
1635 return oplen; 1644 return oplen;
1636 } else { 1645 } else {
1637 return m68k_disasm_op(decoded, dst, need_comma, labels, address); 1646 return m68k_disasm_op(decoded, dst, need_comma, labels, address, label_fun, data);
1638 } 1647 }
1639 } 1648 }
1640 1649
1641 int m68k_disasm_ex(m68kinst * decoded, char * dst, uint8_t labels) 1650 int m68k_default_label_fun(char * dst, uint32_t address, void * data)
1651 {
1652 return sprintf(dst, "ADR_%X", address);
1653 }
1654
1655 int m68k_disasm_ex(m68kinst * decoded, char * dst, uint8_t labels, format_label_fun label_fun, void * data)
1642 { 1656 {
1643 int ret,op1len; 1657 int ret,op1len;
1644 uint8_t size; 1658 uint8_t size;
1645 char * special_op = "CCR"; 1659 char * special_op = "CCR";
1646 switch (decoded->op) 1660 switch (decoded->op)
1654 strcpy(dst+ret, cond_mnem[decoded->extra.cond]); 1668 strcpy(dst+ret, cond_mnem[decoded->extra.cond]);
1655 ret = strlen(dst); 1669 ret = strlen(dst);
1656 if (decoded->op != M68K_SCC) { 1670 if (decoded->op != M68K_SCC) {
1657 if (labels) { 1671 if (labels) {
1658 if (decoded->op == M68K_DBCC) { 1672 if (decoded->op == M68K_DBCC) {
1659 ret += sprintf(dst+ret, " d%d, ADR_%X", decoded->dst.params.regs.pri, decoded->address + 2 + decoded->src.params.immed); 1673 ret += sprintf(dst+ret, " d%d, ", decoded->dst.params.regs.pri);
1674 ret += label_fun(dst+ret, decoded->address + 2 + decoded->src.params.immed, data);
1660 } else { 1675 } else {
1661 ret += sprintf(dst+ret, " ADR_%X", decoded->address + 2 + decoded->src.params.immed); 1676 dst[ret++] = ' ';
1677 ret += label_fun(dst+ret, decoded->address + 2 + decoded->src.params.immed, data);
1662 } 1678 }
1663 } else { 1679 } else {
1664 if (decoded->op == M68K_DBCC) { 1680 if (decoded->op == M68K_DBCC) {
1665 ret += sprintf(dst+ret, " d%d, #%d <%X>", decoded->dst.params.regs.pri, decoded->src.params.immed, decoded->address + 2 + decoded->src.params.immed); 1681 ret += sprintf(dst+ret, " d%d, #%d <%X>", decoded->dst.params.regs.pri, decoded->src.params.immed, decoded->address + 2 + decoded->src.params.immed);
1666 } else { 1682 } else {
1670 return ret; 1686 return ret;
1671 } 1687 }
1672 break; 1688 break;
1673 case M68K_BSR: 1689 case M68K_BSR:
1674 if (labels) { 1690 if (labels) {
1675 ret = sprintf(dst, "bsr%s ADR_%X", decoded->variant == VAR_BYTE ? ".s" : "", 1691 ret = sprintf(dst, "bsr%s ", decoded->variant == VAR_BYTE ? ".s" : "");
1676 decoded->address + 2 + decoded->src.params.immed); 1692 ret += label_fun(dst+ret, decoded->address + 2 + decoded->src.params.immed, data);
1677 } else { 1693 } else {
1678 ret = sprintf(dst, "bsr%s #%d <%X>", decoded->variant == VAR_BYTE ? ".s" : "", decoded->src.params.immed, decoded->address + 2 + decoded->src.params.immed); 1694 ret = sprintf(dst, "bsr%s #%d <%X>", decoded->variant == VAR_BYTE ? ".s" : "", decoded->src.params.immed, decoded->address + 2 + decoded->src.params.immed);
1679 } 1695 }
1680 return ret; 1696 return ret;
1681 case M68K_MOVE_FROM_SR: 1697 case M68K_MOVE_FROM_SR:
1682 ret = sprintf(dst, "%s", mnemonics[decoded->op]); 1698 ret = sprintf(dst, "%s", mnemonics[decoded->op]);
1683 ret += sprintf(dst + ret, " SR"); 1699 ret += sprintf(dst + ret, " SR");
1684 ret += m68k_disasm_op(&(decoded->dst), dst + ret, 1, labels, decoded->address); 1700 ret += m68k_disasm_op(&(decoded->dst), dst + ret, 1, labels, decoded->address, label_fun, data);
1685 return ret; 1701 return ret;
1686 case M68K_ANDI_SR: 1702 case M68K_ANDI_SR:
1687 case M68K_EORI_SR: 1703 case M68K_EORI_SR:
1688 case M68K_MOVE_SR: 1704 case M68K_MOVE_SR:
1689 case M68K_ORI_SR: 1705 case M68K_ORI_SR:
1691 case M68K_ANDI_CCR: 1707 case M68K_ANDI_CCR:
1692 case M68K_EORI_CCR: 1708 case M68K_EORI_CCR:
1693 case M68K_MOVE_CCR: 1709 case M68K_MOVE_CCR:
1694 case M68K_ORI_CCR: 1710 case M68K_ORI_CCR:
1695 ret = sprintf(dst, "%s", mnemonics[decoded->op]); 1711 ret = sprintf(dst, "%s", mnemonics[decoded->op]);
1696 ret += m68k_disasm_op(&(decoded->src), dst + ret, 0, labels, decoded->address); 1712 ret += m68k_disasm_op(&(decoded->src), dst + ret, 0, labels, decoded->address, label_fun, data);
1697 ret += sprintf(dst + ret, ", %s", special_op); 1713 ret += sprintf(dst + ret, ", %s", special_op);
1698 return ret; 1714 return ret;
1699 case M68K_MOVE_USP: 1715 case M68K_MOVE_USP:
1700 ret = sprintf(dst, "%s", mnemonics[decoded->op]); 1716 ret = sprintf(dst, "%s", mnemonics[decoded->op]);
1701 if (decoded->src.addr_mode != MODE_UNUSED) { 1717 if (decoded->src.addr_mode != MODE_UNUSED) {
1702 ret += m68k_disasm_op(&(decoded->src), dst + ret, 0, labels, decoded->address); 1718 ret += m68k_disasm_op(&(decoded->src), dst + ret, 0, labels, decoded->address, label_fun, data);
1703 ret += sprintf(dst + ret, ", USP"); 1719 ret += sprintf(dst + ret, ", USP");
1704 } else { 1720 } else {
1705 ret += sprintf(dst + ret, "USP, "); 1721 ret += sprintf(dst + ret, "USP, ");
1706 ret += m68k_disasm_op(&(decoded->dst), dst + ret, 0, labels, decoded->address); 1722 ret += m68k_disasm_op(&(decoded->dst), dst + ret, 0, labels, decoded->address, label_fun, data);
1707 } 1723 }
1708 return ret; 1724 return ret;
1709 case M68K_INVALID: 1725 case M68K_INVALID:
1710 ret = sprintf(dst, "dc.w $%X", decoded->src.params.immed); 1726 ret = sprintf(dst, "dc.w $%X", decoded->src.params.immed);
1711 return ret; 1727 return ret;
1712 #ifdef M68010 1728 #ifdef M68010
1713 case M68K_MOVEC: 1729 case M68K_MOVEC:
1714 ret = sprintf(dst, "%s ", mnemonics[decoded->op]); 1730 ret = sprintf(dst, "%s ", mnemonics[decoded->op]);
1715 if (decoded->src.addr_mode == MODE_UNUSED) { 1731 if (decoded->src.addr_mode == MODE_UNUSED) {
1716 ret += sprintf(dst + ret, "%s, ", cr_mnem[decoded->src.params.immed]); 1732 ret += sprintf(dst + ret, "%s, ", cr_mnem[decoded->src.params.immed]);
1717 ret += m68k_disasm_op(&(decoded->dst), dst + ret, 0, labels, decoded->address); 1733 ret += m68k_disasm_op(&(decoded->dst), dst + ret, 0, labels, decoded->address, label_fun, data);
1718 } else { 1734 } else {
1719 ret += m68k_disasm_op(&(decoded->src), dst + ret, 0, labels, decoded->address); 1735 ret += m68k_disasm_op(&(decoded->src), dst + ret, 0, labels, decoded->address, label_fun, data);
1720 ret += sprintf(dst + ret, ", %s", cr_mnem[decoded->dst.params.immed]); 1736 ret += sprintf(dst + ret, ", %s", cr_mnem[decoded->dst.params.immed]);
1721 } 1737 }
1722 return ret; 1738 return ret;
1723 #endif 1739 #endif
1724 default: 1740 default:
1727 mnemonics[decoded->op], 1743 mnemonics[decoded->op],
1728 decoded->variant == VAR_QUICK ? "q" : (decoded->variant == VAR_IMMEDIATE ? "i" : ""), 1744 decoded->variant == VAR_QUICK ? "q" : (decoded->variant == VAR_IMMEDIATE ? "i" : ""),
1729 size == OPSIZE_BYTE ? ".b" : (size == OPSIZE_WORD ? ".w" : (size == OPSIZE_LONG ? ".l" : ""))); 1745 size == OPSIZE_BYTE ? ".b" : (size == OPSIZE_WORD ? ".w" : (size == OPSIZE_LONG ? ".l" : "")));
1730 } 1746 }
1731 if (decoded->op == M68K_MOVEM) { 1747 if (decoded->op == M68K_MOVEM) {
1732 op1len = m68k_disasm_movem_op(&(decoded->src), &(decoded->dst), dst + ret, 0, labels, decoded->address); 1748 op1len = m68k_disasm_movem_op(&(decoded->src), &(decoded->dst), dst + ret, 0, labels, decoded->address, label_fun, data);
1733 ret += op1len; 1749 ret += op1len;
1734 ret += m68k_disasm_movem_op(&(decoded->dst), &(decoded->src), dst + ret, op1len, labels, decoded->address); 1750 ret += m68k_disasm_movem_op(&(decoded->dst), &(decoded->src), dst + ret, op1len, labels, decoded->address, label_fun, data);
1735 } else { 1751 } else {
1736 op1len = m68k_disasm_op(&(decoded->src), dst + ret, 0, labels, decoded->address); 1752 op1len = m68k_disasm_op(&(decoded->src), dst + ret, 0, labels, decoded->address, label_fun, data);
1737 ret += op1len; 1753 ret += op1len;
1738 ret += m68k_disasm_op(&(decoded->dst), dst + ret, op1len, labels, decoded->address); 1754 ret += m68k_disasm_op(&(decoded->dst), dst + ret, op1len, labels, decoded->address, label_fun, data);
1739 } 1755 }
1740 return ret; 1756 return ret;
1741 } 1757 }
1742 1758
1743 int m68k_disasm(m68kinst * decoded, char * dst) 1759 int m68k_disasm(m68kinst * decoded, char * dst)
1744 { 1760 {
1745 return m68k_disasm_ex(decoded, dst, 0); 1761 return m68k_disasm_ex(decoded, dst, 0, NULL, NULL);
1746 } 1762 }
1747 1763
1748 int m68k_disasm_labels(m68kinst * decoded, char * dst) 1764 int m68k_disasm_labels(m68kinst * decoded, char * dst, format_label_fun label_fun, void * data)
1749 { 1765 {
1750 return m68k_disasm_ex(decoded, dst, 1); 1766 if (!label_fun)
1767 {
1768 label_fun = m68k_default_label_fun;
1769 }
1770 return m68k_disasm_ex(decoded, dst, 1, label_fun, data);
1751 } 1771 }