OLD | NEW |
---|---|
1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 // A Disassembler object is used to disassemble a block of code instruction by | 5 // A Disassembler object is used to disassemble a block of code instruction by |
6 // instruction. The default implementation of the NameConverter object can be | 6 // instruction. The default implementation of the NameConverter object can be |
7 // overriden to modify register names or to do symbol lookup on addresses. | 7 // overriden to modify register names or to do symbol lookup on addresses. |
8 // | 8 // |
9 // The example below will disassemble a block of code and print it to stdout. | 9 // The example below will disassemble a block of code and print it to stdout. |
10 // | 10 // |
(...skipping 1401 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1412 // Dd = vmls(Dn, Dm) | 1412 // Dd = vmls(Dn, Dm) |
1413 // Sd = vmls(Sn, Sm) | 1413 // Sd = vmls(Sn, Sm) |
1414 // Dd = vdiv(Dn, Dm) | 1414 // Dd = vdiv(Dn, Dm) |
1415 // Sd = vdiv(Sn, Sm) | 1415 // Sd = vdiv(Sn, Sm) |
1416 // vcmp(Dd, Dm) | 1416 // vcmp(Dd, Dm) |
1417 // vcmp(Sd, Sm) | 1417 // vcmp(Sd, Sm) |
1418 // Dd = vsqrt(Dm) | 1418 // Dd = vsqrt(Dm) |
1419 // Sd = vsqrt(Sm) | 1419 // Sd = vsqrt(Sm) |
1420 // vmrs | 1420 // vmrs |
1421 // vmsr | 1421 // vmsr |
1422 // Qd = vdup.size(Qd, Rt) | |
1422 void Decoder::DecodeTypeVFP(Instruction* instr) { | 1423 void Decoder::DecodeTypeVFP(Instruction* instr) { |
1423 VERIFY((instr->TypeValue() == 7) && (instr->Bit(24) == 0x0) ); | 1424 VERIFY((instr->TypeValue() == 7) && (instr->Bit(24) == 0x0) ); |
1424 VERIFY(instr->Bits(11, 9) == 0x5); | 1425 VERIFY(instr->Bits(11, 9) == 0x5); |
1425 | 1426 |
1426 if (instr->Bit(4) == 0) { | 1427 if (instr->Bit(4) == 0) { |
1427 if (instr->Opc1Value() == 0x7) { | 1428 if (instr->Opc1Value() == 0x7) { |
1428 // Other data processing instructions | 1429 // Other data processing instructions |
1429 if ((instr->Opc2Value() == 0x0) && (instr->Opc3Value() == 0x1)) { | 1430 if ((instr->Opc2Value() == 0x0) && (instr->Opc3Value() == 0x1)) { |
1430 // vmov register to register. | 1431 // vmov register to register. |
1431 if (instr->SzValue() == 0x1) { | 1432 if (instr->SzValue() == 0x1) { |
(...skipping 92 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1524 } else { | 1525 } else { |
1525 Format(instr, "vdiv'cond.f32 'Sd, 'Sn, 'Sm"); | 1526 Format(instr, "vdiv'cond.f32 'Sd, 'Sn, 'Sm"); |
1526 } | 1527 } |
1527 } else { | 1528 } else { |
1528 Unknown(instr); // Not used by V8. | 1529 Unknown(instr); // Not used by V8. |
1529 } | 1530 } |
1530 } else { | 1531 } else { |
1531 if ((instr->VCValue() == 0x0) && | 1532 if ((instr->VCValue() == 0x0) && |
1532 (instr->VAValue() == 0x0)) { | 1533 (instr->VAValue() == 0x0)) { |
1533 DecodeVMOVBetweenCoreAndSinglePrecisionRegisters(instr); | 1534 DecodeVMOVBetweenCoreAndSinglePrecisionRegisters(instr); |
1534 } else if ((instr->VLValue() == 0x0) && | 1535 } else if ((instr->VLValue() == 0x0) && (instr->VCValue() == 0x1)) { |
1535 (instr->VCValue() == 0x1) && | 1536 if (instr->Bit(23) == 0) { |
1536 (instr->Bit(23) == 0x0)) { | 1537 if (instr->Bit(21) == 0x0) { |
1537 if (instr->Bit(21) == 0x0) { | 1538 Format(instr, "vmov'cond.32 'Dd[0], 'rt"); |
1538 Format(instr, "vmov'cond.32 'Dd[0], 'rt"); | 1539 } else { |
1540 Format(instr, "vmov'cond.32 'Dd[1], 'rt"); | |
1541 } | |
1539 } else { | 1542 } else { |
1540 Format(instr, "vmov'cond.32 'Dd[1], 'rt"); | 1543 int size = 32; |
1544 if (instr->Bit(5) != 0) | |
1545 size = 16; | |
1546 else if (instr->Bit(22) != 0) | |
1547 size = 8; | |
1548 int Vd = (instr->Bit(7) << 3) | (instr->VnValue() >> 1); | |
Rodolph Perfetta (ARM)
2016/12/08 18:08:28
int Vd = instr->VFPNRegValue(kSimd128Precision);
bbudge
2016/12/10 21:33:04
Done.
| |
1549 int Rt = instr->RtValue(); | |
1550 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, | |
1551 "vdup.%i q%d, r%d", size, Vd, Rt); | |
1541 } | 1552 } |
1542 } else if ((instr->VLValue() == 0x1) && | 1553 } else if ((instr->VLValue() == 0x1) && |
1543 (instr->VCValue() == 0x1) && | 1554 (instr->VCValue() == 0x1) && |
1544 (instr->Bit(23) == 0x0)) { | 1555 (instr->Bit(23) == 0x0)) { |
1545 if (instr->Bit(21) == 0x0) { | 1556 if (instr->Bit(21) == 0x0) { |
1546 Format(instr, "vmov'cond.32 'rt, 'Dd[0]"); | 1557 Format(instr, "vmov'cond.32 'rt, 'Dd[0]"); |
1547 } else { | 1558 } else { |
1548 Format(instr, "vmov'cond.32 'rt, 'Dd[1]"); | 1559 Format(instr, "vmov'cond.32 'rt, 'Dd[1]"); |
1549 } | 1560 } |
1550 } else if ((instr->VCValue() == 0x0) && | 1561 } else if ((instr->VCValue() == 0x0) && |
1551 (instr->VAValue() == 0x7) && | 1562 (instr->VAValue() == 0x7) && |
1552 (instr->Bits(19, 16) == 0x1)) { | 1563 (instr->Bits(19, 16) == 0x1)) { |
1553 if (instr->VLValue() == 0) { | 1564 if (instr->VLValue() == 0) { |
1554 if (instr->Bits(15, 12) == 0xF) { | 1565 if (instr->Bits(15, 12) == 0xF) { |
1555 Format(instr, "vmsr'cond FPSCR, APSR"); | 1566 Format(instr, "vmsr'cond FPSCR, APSR"); |
1556 } else { | 1567 } else { |
1557 Format(instr, "vmsr'cond FPSCR, 'rt"); | 1568 Format(instr, "vmsr'cond FPSCR, 'rt"); |
1558 } | 1569 } |
1559 } else { | 1570 } else { |
1560 if (instr->Bits(15, 12) == 0xF) { | 1571 if (instr->Bits(15, 12) == 0xF) { |
1561 Format(instr, "vmrs'cond APSR, FPSCR"); | 1572 Format(instr, "vmrs'cond APSR, FPSCR"); |
1562 } else { | 1573 } else { |
1563 Format(instr, "vmrs'cond 'rt, FPSCR"); | 1574 Format(instr, "vmrs'cond 'rt, FPSCR"); |
1564 } | 1575 } |
1565 } | 1576 } |
1577 } else { | |
1578 Unknown(instr); // Not used by V8. | |
1566 } | 1579 } |
1567 } | 1580 } |
1568 } | 1581 } |
1569 | 1582 |
1570 void Decoder::DecodeTypeCP15(Instruction* instr) { | 1583 void Decoder::DecodeTypeCP15(Instruction* instr) { |
1571 VERIFY((instr->TypeValue() == 7) && (instr->Bit(24) == 0x0)); | 1584 VERIFY((instr->TypeValue() == 7) && (instr->Bit(24) == 0x0)); |
1572 VERIFY(instr->CoprocessorValue() == 15); | 1585 VERIFY(instr->CoprocessorValue() == 15); |
1573 | 1586 |
1574 if (instr->Bit(4) == 1) { | 1587 if (instr->Bit(4) == 1) { |
1575 int crn = instr->Bits(19, 16); | 1588 int crn = instr->Bits(19, 16); |
(...skipping 226 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1802 void Decoder::DecodeSpecialCondition(Instruction* instr) { | 1815 void Decoder::DecodeSpecialCondition(Instruction* instr) { |
1803 switch (instr->SpecialValue()) { | 1816 switch (instr->SpecialValue()) { |
1804 case 4: | 1817 case 4: |
1805 if (instr->Bits(21, 20) == 2 && instr->Bits(11, 8) == 1 && | 1818 if (instr->Bits(21, 20) == 2 && instr->Bits(11, 8) == 1 && |
1806 instr->Bit(4) == 1) { | 1819 instr->Bit(4) == 1) { |
1807 // vmov Qd, Qm | 1820 // vmov Qd, Qm |
1808 int Vd = instr->VFPDRegValue(kSimd128Precision); | 1821 int Vd = instr->VFPDRegValue(kSimd128Precision); |
1809 int Vm = instr->VFPMRegValue(kSimd128Precision); | 1822 int Vm = instr->VFPMRegValue(kSimd128Precision); |
1810 out_buffer_pos_ += | 1823 out_buffer_pos_ += |
1811 SNPrintF(out_buffer_ + out_buffer_pos_, "vmov q%d, q%d", Vd, Vm); | 1824 SNPrintF(out_buffer_ + out_buffer_pos_, "vmov q%d, q%d", Vd, Vm); |
1825 } else if (instr->Bits(11, 8) == 8) { | |
1826 const char* op = (instr->Bit(4) == 0) ? "vadd" : "vtst"; | |
1827 int size = kBitsPerByte * (1 << instr->Bits(21, 20)); | |
1828 int Vd = instr->VFPDRegValue(kSimd128Precision); | |
1829 int Vm = instr->VFPMRegValue(kSimd128Precision); | |
1830 int Vn = instr->VFPNRegValue(kSimd128Precision); | |
1831 // vadd/vtst.i<size> Qd, Qm, Qn. | |
1832 out_buffer_pos_ += | |
1833 SNPrintF(out_buffer_ + out_buffer_pos_, "%s.i%d q%d, q%d, q%d", op, | |
1834 size, Vd, Vn, Vm); | |
1835 } else if (instr->Bits(11, 8) == 0xd && instr->Bit(4) == 0) { | |
1836 const char* op = (instr->Bits(21, 20) == 0) ? "vadd" : "vsub"; | |
1837 int size = kBitsPerByte * (1 << instr->Bits(21, 20)); | |
1838 int Vd = instr->VFPDRegValue(kSimd128Precision); | |
1839 int Vm = instr->VFPMRegValue(kSimd128Precision); | |
1840 int Vn = instr->VFPNRegValue(kSimd128Precision); | |
1841 // vadd/vsub.f32 Qd, Qm, Qn. | |
1842 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, | |
1843 "%s.f32 q%d, q%d, q%d", op, Vd, Vn, Vm); | |
1812 } else { | 1844 } else { |
1813 Unknown(instr); | 1845 Unknown(instr); |
1814 } | 1846 } |
1815 break; | 1847 break; |
1816 case 5: | 1848 case 5: |
1817 if ((instr->Bits(18, 16) == 0) && (instr->Bits(11, 6) == 0x28) && | 1849 if ((instr->Bits(18, 16) == 0) && (instr->Bits(11, 6) == 0x28) && |
1818 (instr->Bit(4) == 1)) { | 1850 (instr->Bit(4) == 1)) { |
1819 // vmovl signed | 1851 // vmovl signed |
1820 if ((instr->VdValue() & 1) != 0) Unknown(instr); | 1852 if ((instr->VdValue() & 1) != 0) Unknown(instr); |
1821 int Vd = (instr->Bit(22) << 3) | (instr->VdValue() >> 1); | 1853 int Vd = (instr->Bit(22) << 3) | (instr->VdValue() >> 1); |
1822 int Vm = (instr->Bit(5) << 4) | instr->VmValue(); | 1854 int Vm = (instr->Bit(5) << 4) | instr->VmValue(); |
1823 int imm3 = instr->Bits(21, 19); | 1855 int imm3 = instr->Bits(21, 19); |
1824 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, | 1856 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, |
1825 "vmovl.s%d q%d, d%d", imm3*8, Vd, Vm); | 1857 "vmovl.s%d q%d, d%d", imm3*8, Vd, Vm); |
1826 } else { | 1858 } else { |
1827 Unknown(instr); | 1859 Unknown(instr); |
1828 } | 1860 } |
1829 break; | 1861 break; |
1830 case 6: | 1862 case 6: |
1831 if (instr->Bits(21, 20) == 0 && instr->Bits(11, 8) == 1 && | 1863 if (instr->Bits(11, 8) == 8) { |
1832 instr->Bit(4) == 1) { | 1864 int size = kBitsPerByte * (1 << instr->Bits(21, 20)); |
1865 int Vd = instr->VFPDRegValue(kSimd128Precision); | |
1866 int Vm = instr->VFPMRegValue(kSimd128Precision); | |
1867 int Vn = instr->VFPNRegValue(kSimd128Precision); | |
1868 if (instr->Bit(4) == 0) { | |
1869 out_buffer_pos_ += | |
1870 SNPrintF(out_buffer_ + out_buffer_pos_, "vsub.i%d q%d, q%d, q%d", | |
1871 size, Vd, Vn, Vm); | |
1872 } else { | |
1873 out_buffer_pos_ += | |
1874 SNPrintF(out_buffer_ + out_buffer_pos_, "vceq.i%d q%d, q%d, q%d", | |
1875 size, Vd, Vn, Vm); | |
1876 } | |
1877 } else if (instr->Bits(21, 20) == 1 && instr->Bits(11, 8) == 1 && | |
1878 instr->Bit(4) == 1) { | |
1879 int Vd = instr->VFPDRegValue(kSimd128Precision); | |
1880 int Vm = instr->VFPMRegValue(kSimd128Precision); | |
1881 int Vn = instr->VFPNRegValue(kSimd128Precision); | |
1882 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, | |
1883 "vbsl q%d, q%d, q%d", Vd, Vn, Vm); | |
1884 } else if (instr->Bits(21, 20) == 0 && instr->Bits(11, 8) == 1 && | |
1885 instr->Bit(4) == 1) { | |
1833 if (instr->Bit(6) == 0) { | 1886 if (instr->Bit(6) == 0) { |
1834 // veor Dd, Dn, Dm | 1887 // veor Dd, Dn, Dm |
1835 int Vd = instr->VFPDRegValue(kDoublePrecision); | 1888 int Vd = instr->VFPDRegValue(kDoublePrecision); |
1836 int Vn = instr->VFPNRegValue(kDoublePrecision); | 1889 int Vn = instr->VFPNRegValue(kDoublePrecision); |
1837 int Vm = instr->VFPMRegValue(kDoublePrecision); | 1890 int Vm = instr->VFPMRegValue(kDoublePrecision); |
1838 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, | 1891 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, |
1839 "veor d%d, d%d, d%d", Vd, Vn, Vm); | 1892 "veor d%d, d%d, d%d", Vd, Vn, Vm); |
1840 | 1893 |
1841 } else { | 1894 } else { |
1842 // veor Qd, Qn, Qm | 1895 // veor Qd, Qn, Qm |
(...skipping 10 matching lines...) Expand all Loading... | |
1853 case 7: | 1906 case 7: |
1854 if ((instr->Bits(18, 16) == 0) && (instr->Bits(11, 6) == 0x28) && | 1907 if ((instr->Bits(18, 16) == 0) && (instr->Bits(11, 6) == 0x28) && |
1855 (instr->Bit(4) == 1)) { | 1908 (instr->Bit(4) == 1)) { |
1856 // vmovl unsigned | 1909 // vmovl unsigned |
1857 if ((instr->VdValue() & 1) != 0) Unknown(instr); | 1910 if ((instr->VdValue() & 1) != 0) Unknown(instr); |
1858 int Vd = (instr->Bit(22) << 3) | (instr->VdValue() >> 1); | 1911 int Vd = (instr->Bit(22) << 3) | (instr->VdValue() >> 1); |
1859 int Vm = (instr->Bit(5) << 4) | instr->VmValue(); | 1912 int Vm = (instr->Bit(5) << 4) | instr->VmValue(); |
1860 int imm3 = instr->Bits(21, 19); | 1913 int imm3 = instr->Bits(21, 19); |
1861 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, | 1914 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, |
1862 "vmovl.u%d q%d, d%d", imm3*8, Vd, Vm); | 1915 "vmovl.u%d q%d, d%d", imm3*8, Vd, Vm); |
1916 } else if (instr->Opc1Value() == 7 && instr->Bits(19, 16) == 0 && | |
1917 instr->Bits(11, 6) == 0x17 && instr->Bit(4) == 0) { | |
1918 int Vd = instr->VFPDRegValue(kSimd128Precision); | |
1919 int Vm = instr->VFPMRegValue(kSimd128Precision); | |
1920 out_buffer_pos_ += | |
1921 SNPrintF(out_buffer_ + out_buffer_pos_, "vmvn q%d, q%d", Vd, Vm); | |
1922 } else if (instr->Opc1Value() == 7 && instr->Bits(19, 16) == 0xB && | |
1923 instr->Bits(11, 9) == 0x3 && instr->Bit(6) == 1 && | |
1924 instr->Bit(4) == 0) { | |
1925 int Vd = instr->VFPDRegValue(kSimd128Precision); | |
1926 int Vm = instr->VFPMRegValue(kSimd128Precision); | |
1927 const char* suffix = nullptr; | |
1928 int op = instr->Bits(8, 7); | |
1929 switch (op) { | |
1930 case 0: | |
1931 suffix = "f32.s32"; | |
1932 break; | |
1933 case 1: | |
1934 suffix = "f32.u32"; | |
1935 break; | |
1936 case 2: | |
1937 suffix = "s32.f32"; | |
1938 break; | |
1939 case 3: | |
1940 suffix = "u32.f32"; | |
1941 break; | |
1942 } | |
1943 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, | |
1944 "vcvt.%s q%d, q%d", suffix, Vd, Vm); | |
1863 } else if ((instr->Bits(21, 16) == 0x32) && (instr->Bits(11, 7) == 0) && | 1945 } else if ((instr->Bits(21, 16) == 0x32) && (instr->Bits(11, 7) == 0) && |
1864 (instr->Bit(4) == 0)) { | 1946 (instr->Bit(4) == 0)) { |
1865 if (instr->Bit(6) == 0) { | 1947 if (instr->Bit(6) == 0) { |
1866 int Vd = instr->VFPDRegValue(kDoublePrecision); | 1948 int Vd = instr->VFPDRegValue(kDoublePrecision); |
1867 int Vm = instr->VFPMRegValue(kDoublePrecision); | 1949 int Vm = instr->VFPMRegValue(kDoublePrecision); |
1868 out_buffer_pos_ += | 1950 out_buffer_pos_ += |
1869 SNPrintF(out_buffer_ + out_buffer_pos_, "vswp d%d, d%d", Vd, Vm); | 1951 SNPrintF(out_buffer_ + out_buffer_pos_, "vswp d%d, d%d", Vd, Vm); |
1870 } else { | 1952 } else { |
1871 int Vd = instr->VFPDRegValue(kSimd128Precision); | 1953 int Vd = instr->VFPDRegValue(kSimd128Precision); |
1872 int Vm = instr->VFPMRegValue(kSimd128Precision); | 1954 int Vm = instr->VFPMRegValue(kSimd128Precision); |
1873 out_buffer_pos_ += | 1955 out_buffer_pos_ += |
1874 SNPrintF(out_buffer_ + out_buffer_pos_, "vswp q%d, q%d", Vd, Vm); | 1956 SNPrintF(out_buffer_ + out_buffer_pos_, "vswp q%d, q%d", Vd, Vm); |
1875 } | 1957 } |
1958 } else if (instr->Opc1Value() == 0x7 && instr->Bits(11, 7) == 0x18 && | |
1959 instr->Bit(4) == 0x0) { | |
1960 int Vd = instr->VFPDRegValue(kSimd128Precision); | |
1961 int Vm = instr->VFPMRegValue(kDoublePrecision); | |
1962 int index = instr->Bit(19); | |
1963 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, | |
1964 "vdup q%d, d%d[%d]", Vd, Vm, index); | |
1965 } else if (instr->Opc1Value() == 0x7 && instr->Bits(11, 10) == 0x2 && | |
1966 instr->Bit(4) == 0x0) { | |
1967 int Vd = instr->VFPDRegValue(kDoublePrecision); | |
1968 int Vn = instr->VFPNRegValue(kDoublePrecision); | |
1969 int Vm = instr->VFPMRegValue(kDoublePrecision); | |
1970 int len = instr->Bits(9, 8); | |
1971 NeonListOperand list(DwVfpRegister::from_code(Vn), len + 1); | |
1972 out_buffer_pos_ += SNPrintF(out_buffer_ + out_buffer_pos_, "%s d%d, ", | |
1973 instr->Bit(6) == 0 ? "vtbl" : "vtbx", Vd); | |
Rodolph Perfetta (ARM)
2016/12/08 18:08:28
vtbl.8, vtbx.8
bbudge
2016/12/10 21:33:04
Done.
| |
1974 FormatNeonList(Vn, list.type()); | |
1975 Print(", "); | |
1976 PrintDRegister(Vm); | |
1876 } else { | 1977 } else { |
1877 Unknown(instr); | 1978 Unknown(instr); |
1878 } | 1979 } |
1879 break; | 1980 break; |
1880 case 8: | 1981 case 8: |
1881 if (instr->Bits(21, 20) == 0) { | 1982 if (instr->Bits(21, 20) == 0) { |
1882 // vst1 | 1983 // vst1 |
1883 int Vd = (instr->Bit(22) << 4) | instr->VdValue(); | 1984 int Vd = (instr->Bit(22) << 4) | instr->VdValue(); |
1884 int Rn = instr->VnValue(); | 1985 int Rn = instr->VnValue(); |
1885 int type = instr->Bits(11, 8); | 1986 int type = instr->Bits(11, 8); |
(...skipping 325 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2211 pc += d.InstructionDecode(buffer, pc); | 2312 pc += d.InstructionDecode(buffer, pc); |
2212 v8::internal::PrintF(f, "%p %08x %s\n", static_cast<void*>(prev_pc), | 2313 v8::internal::PrintF(f, "%p %08x %s\n", static_cast<void*>(prev_pc), |
2213 *reinterpret_cast<int32_t*>(prev_pc), buffer.start()); | 2314 *reinterpret_cast<int32_t*>(prev_pc), buffer.start()); |
2214 } | 2315 } |
2215 } | 2316 } |
2216 | 2317 |
2217 | 2318 |
2218 } // namespace disasm | 2319 } // namespace disasm |
2219 | 2320 |
2220 #endif // V8_TARGET_ARCH_ARM | 2321 #endif // V8_TARGET_ARCH_ARM |
OLD | NEW |