Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(319)

Side by Side Diff: src/mips64/simulator-mips64.cc

Issue 1902743002: MIPS: Implement unaligned access instruction. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Address code review remarks Created 4 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/mips64/macro-assembler-mips64.cc ('k') | test/cctest/test-macro-assembler-mips.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 #include <limits.h> 5 #include <limits.h>
6 #include <stdarg.h> 6 #include <stdarg.h>
7 #include <stdlib.h> 7 #include <stdlib.h>
8 #include <cmath> 8 #include <cmath>
9 9
10 #if V8_TARGET_ARCH_MIPS64 10 #if V8_TARGET_ARCH_MIPS64
(...skipping 1725 matching lines...) Expand 10 before | Expand all | Expand 10 after
1736 // TODO(plind): sign-extend and zero-extend not implmented properly 1736 // TODO(plind): sign-extend and zero-extend not implmented properly
1737 // on all the ReadXX functions, I don't think re-interpret cast does it. 1737 // on all the ReadXX functions, I don't think re-interpret cast does it.
1738 int32_t Simulator::ReadW(int64_t addr, Instruction* instr) { 1738 int32_t Simulator::ReadW(int64_t addr, Instruction* instr) {
1739 if (addr >=0 && addr < 0x400) { 1739 if (addr >=0 && addr < 0x400) {
1740 // This has to be a NULL-dereference, drop into debugger. 1740 // This has to be a NULL-dereference, drop into debugger.
1741 PrintF("Memory read from bad address: 0x%08" PRIx64 " , pc=0x%08" PRIxPTR 1741 PrintF("Memory read from bad address: 0x%08" PRIx64 " , pc=0x%08" PRIxPTR
1742 " \n", 1742 " \n",
1743 addr, reinterpret_cast<intptr_t>(instr)); 1743 addr, reinterpret_cast<intptr_t>(instr));
1744 DieOrDebug(); 1744 DieOrDebug();
1745 } 1745 }
1746 if ((addr & 0x3) == 0) { 1746 if ((addr & 0x3) == 0 || kArchVariant == kMips64r6) {
1747 int32_t* ptr = reinterpret_cast<int32_t*>(addr); 1747 int32_t* ptr = reinterpret_cast<int32_t*>(addr);
1748 TraceMemRd(addr, static_cast<int64_t>(*ptr)); 1748 TraceMemRd(addr, static_cast<int64_t>(*ptr));
1749 return *ptr; 1749 return *ptr;
1750 } 1750 }
1751 PrintF("Unaligned read at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n", addr, 1751 PrintF("Unaligned read at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n", addr,
1752 reinterpret_cast<intptr_t>(instr)); 1752 reinterpret_cast<intptr_t>(instr));
1753 DieOrDebug(); 1753 DieOrDebug();
1754 return 0; 1754 return 0;
1755 } 1755 }
1756 1756
1757 1757
1758 uint32_t Simulator::ReadWU(int64_t addr, Instruction* instr) { 1758 uint32_t Simulator::ReadWU(int64_t addr, Instruction* instr) {
1759 if (addr >=0 && addr < 0x400) { 1759 if (addr >=0 && addr < 0x400) {
1760 // This has to be a NULL-dereference, drop into debugger. 1760 // This has to be a NULL-dereference, drop into debugger.
1761 PrintF("Memory read from bad address: 0x%08" PRIx64 " , pc=0x%08" PRIxPTR 1761 PrintF("Memory read from bad address: 0x%08" PRIx64 " , pc=0x%08" PRIxPTR
1762 " \n", 1762 " \n",
1763 addr, reinterpret_cast<intptr_t>(instr)); 1763 addr, reinterpret_cast<intptr_t>(instr));
1764 DieOrDebug(); 1764 DieOrDebug();
1765 } 1765 }
1766 if ((addr & 0x3) == 0) { 1766 if ((addr & 0x3) == 0 || kArchVariant == kMips64r6) {
1767 uint32_t* ptr = reinterpret_cast<uint32_t*>(addr); 1767 uint32_t* ptr = reinterpret_cast<uint32_t*>(addr);
1768 TraceMemRd(addr, static_cast<int64_t>(*ptr)); 1768 TraceMemRd(addr, static_cast<int64_t>(*ptr));
1769 return *ptr; 1769 return *ptr;
1770 } 1770 }
1771 PrintF("Unaligned read at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n", addr, 1771 PrintF("Unaligned read at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n", addr,
1772 reinterpret_cast<intptr_t>(instr)); 1772 reinterpret_cast<intptr_t>(instr));
1773 DieOrDebug(); 1773 DieOrDebug();
1774 return 0; 1774 return 0;
1775 } 1775 }
1776 1776
1777 1777
1778 void Simulator::WriteW(int64_t addr, int32_t value, Instruction* instr) { 1778 void Simulator::WriteW(int64_t addr, int32_t value, Instruction* instr) {
1779 if (addr >= 0 && addr < 0x400) { 1779 if (addr >= 0 && addr < 0x400) {
1780 // This has to be a NULL-dereference, drop into debugger. 1780 // This has to be a NULL-dereference, drop into debugger.
1781 PrintF("Memory write to bad address: 0x%08" PRIx64 " , pc=0x%08" PRIxPTR 1781 PrintF("Memory write to bad address: 0x%08" PRIx64 " , pc=0x%08" PRIxPTR
1782 " \n", 1782 " \n",
1783 addr, reinterpret_cast<intptr_t>(instr)); 1783 addr, reinterpret_cast<intptr_t>(instr));
1784 DieOrDebug(); 1784 DieOrDebug();
1785 } 1785 }
1786 if ((addr & 0x3) == 0) { 1786 if ((addr & 0x3) == 0 || kArchVariant == kMips64r6) {
1787 TraceMemWr(addr, value, WORD); 1787 TraceMemWr(addr, value, WORD);
1788 int* ptr = reinterpret_cast<int*>(addr); 1788 int* ptr = reinterpret_cast<int*>(addr);
1789 *ptr = value; 1789 *ptr = value;
1790 return; 1790 return;
1791 } 1791 }
1792 PrintF("Unaligned write at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n", addr, 1792 PrintF("Unaligned write at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n", addr,
1793 reinterpret_cast<intptr_t>(instr)); 1793 reinterpret_cast<intptr_t>(instr));
1794 DieOrDebug(); 1794 DieOrDebug();
1795 } 1795 }
1796 1796
1797 1797
1798 int64_t Simulator::Read2W(int64_t addr, Instruction* instr) { 1798 int64_t Simulator::Read2W(int64_t addr, Instruction* instr) {
1799 if (addr >=0 && addr < 0x400) { 1799 if (addr >=0 && addr < 0x400) {
1800 // This has to be a NULL-dereference, drop into debugger. 1800 // This has to be a NULL-dereference, drop into debugger.
1801 PrintF("Memory read from bad address: 0x%08" PRIx64 " , pc=0x%08" PRIxPTR 1801 PrintF("Memory read from bad address: 0x%08" PRIx64 " , pc=0x%08" PRIxPTR
1802 " \n", 1802 " \n",
1803 addr, reinterpret_cast<intptr_t>(instr)); 1803 addr, reinterpret_cast<intptr_t>(instr));
1804 DieOrDebug(); 1804 DieOrDebug();
1805 } 1805 }
1806 if ((addr & kPointerAlignmentMask) == 0) { 1806 if ((addr & kPointerAlignmentMask) == 0 || kArchVariant == kMips64r6) {
1807 int64_t* ptr = reinterpret_cast<int64_t*>(addr); 1807 int64_t* ptr = reinterpret_cast<int64_t*>(addr);
1808 TraceMemRd(addr, *ptr); 1808 TraceMemRd(addr, *ptr);
1809 return *ptr; 1809 return *ptr;
1810 } 1810 }
1811 PrintF("Unaligned read at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n", addr, 1811 PrintF("Unaligned read at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n", addr,
1812 reinterpret_cast<intptr_t>(instr)); 1812 reinterpret_cast<intptr_t>(instr));
1813 DieOrDebug(); 1813 DieOrDebug();
1814 return 0; 1814 return 0;
1815 } 1815 }
1816 1816
1817 1817
1818 void Simulator::Write2W(int64_t addr, int64_t value, Instruction* instr) { 1818 void Simulator::Write2W(int64_t addr, int64_t value, Instruction* instr) {
1819 if (addr >= 0 && addr < 0x400) { 1819 if (addr >= 0 && addr < 0x400) {
1820 // This has to be a NULL-dereference, drop into debugger. 1820 // This has to be a NULL-dereference, drop into debugger.
1821 PrintF("Memory write to bad address: 0x%08" PRIx64 " , pc=0x%08" PRIxPTR 1821 PrintF("Memory write to bad address: 0x%08" PRIx64 " , pc=0x%08" PRIxPTR
1822 "\n", 1822 "\n",
1823 addr, reinterpret_cast<intptr_t>(instr)); 1823 addr, reinterpret_cast<intptr_t>(instr));
1824 DieOrDebug(); 1824 DieOrDebug();
1825 } 1825 }
1826 if ((addr & kPointerAlignmentMask) == 0) { 1826 if ((addr & kPointerAlignmentMask) == 0 || kArchVariant == kMips64r6) {
1827 TraceMemWr(addr, value, DWORD); 1827 TraceMemWr(addr, value, DWORD);
1828 int64_t* ptr = reinterpret_cast<int64_t*>(addr); 1828 int64_t* ptr = reinterpret_cast<int64_t*>(addr);
1829 *ptr = value; 1829 *ptr = value;
1830 return; 1830 return;
1831 } 1831 }
1832 PrintF("Unaligned write at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n", addr, 1832 PrintF("Unaligned write at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n", addr,
1833 reinterpret_cast<intptr_t>(instr)); 1833 reinterpret_cast<intptr_t>(instr));
1834 DieOrDebug(); 1834 DieOrDebug();
1835 } 1835 }
1836 1836
1837 1837
1838 double Simulator::ReadD(int64_t addr, Instruction* instr) { 1838 double Simulator::ReadD(int64_t addr, Instruction* instr) {
1839 if ((addr & kDoubleAlignmentMask) == 0) { 1839 if ((addr & kDoubleAlignmentMask) == 0 || kArchVariant == kMips64r6) {
1840 double* ptr = reinterpret_cast<double*>(addr); 1840 double* ptr = reinterpret_cast<double*>(addr);
1841 return *ptr; 1841 return *ptr;
1842 } 1842 }
1843 PrintF("Unaligned (double) read at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n", 1843 PrintF("Unaligned (double) read at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR "\n",
1844 addr, reinterpret_cast<intptr_t>(instr)); 1844 addr, reinterpret_cast<intptr_t>(instr));
1845 base::OS::Abort(); 1845 base::OS::Abort();
1846 return 0; 1846 return 0;
1847 } 1847 }
1848 1848
1849 1849
1850 void Simulator::WriteD(int64_t addr, double value, Instruction* instr) { 1850 void Simulator::WriteD(int64_t addr, double value, Instruction* instr) {
1851 if ((addr & kDoubleAlignmentMask) == 0) { 1851 if ((addr & kDoubleAlignmentMask) == 0 || kArchVariant == kMips64r6) {
1852 double* ptr = reinterpret_cast<double*>(addr); 1852 double* ptr = reinterpret_cast<double*>(addr);
1853 *ptr = value; 1853 *ptr = value;
1854 return; 1854 return;
1855 } 1855 }
1856 PrintF("Unaligned (double) write at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR 1856 PrintF("Unaligned (double) write at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR
1857 "\n", 1857 "\n",
1858 addr, reinterpret_cast<intptr_t>(instr)); 1858 addr, reinterpret_cast<intptr_t>(instr));
1859 DieOrDebug(); 1859 DieOrDebug();
1860 } 1860 }
1861 1861
1862 1862
1863 uint16_t Simulator::ReadHU(int64_t addr, Instruction* instr) { 1863 uint16_t Simulator::ReadHU(int64_t addr, Instruction* instr) {
1864 if ((addr & 1) == 0) { 1864 if ((addr & 1) == 0 || kArchVariant == kMips64r6) {
1865 uint16_t* ptr = reinterpret_cast<uint16_t*>(addr); 1865 uint16_t* ptr = reinterpret_cast<uint16_t*>(addr);
1866 TraceMemRd(addr, static_cast<int64_t>(*ptr)); 1866 TraceMemRd(addr, static_cast<int64_t>(*ptr));
1867 return *ptr; 1867 return *ptr;
1868 } 1868 }
1869 PrintF("Unaligned unsigned halfword read at 0x%08" PRIx64 1869 PrintF("Unaligned unsigned halfword read at 0x%08" PRIx64
1870 " , pc=0x%08" V8PRIxPTR "\n", 1870 " , pc=0x%08" V8PRIxPTR "\n",
1871 addr, reinterpret_cast<intptr_t>(instr)); 1871 addr, reinterpret_cast<intptr_t>(instr));
1872 DieOrDebug(); 1872 DieOrDebug();
1873 return 0; 1873 return 0;
1874 } 1874 }
1875 1875
1876 1876
1877 int16_t Simulator::ReadH(int64_t addr, Instruction* instr) { 1877 int16_t Simulator::ReadH(int64_t addr, Instruction* instr) {
1878 if ((addr & 1) == 0) { 1878 if ((addr & 1) == 0 || kArchVariant == kMips64r6) {
1879 int16_t* ptr = reinterpret_cast<int16_t*>(addr); 1879 int16_t* ptr = reinterpret_cast<int16_t*>(addr);
1880 TraceMemRd(addr, static_cast<int64_t>(*ptr)); 1880 TraceMemRd(addr, static_cast<int64_t>(*ptr));
1881 return *ptr; 1881 return *ptr;
1882 } 1882 }
1883 PrintF("Unaligned signed halfword read at 0x%08" PRIx64 1883 PrintF("Unaligned signed halfword read at 0x%08" PRIx64
1884 " , pc=0x%08" V8PRIxPTR "\n", 1884 " , pc=0x%08" V8PRIxPTR "\n",
1885 addr, reinterpret_cast<intptr_t>(instr)); 1885 addr, reinterpret_cast<intptr_t>(instr));
1886 DieOrDebug(); 1886 DieOrDebug();
1887 return 0; 1887 return 0;
1888 } 1888 }
1889 1889
1890 1890
1891 void Simulator::WriteH(int64_t addr, uint16_t value, Instruction* instr) { 1891 void Simulator::WriteH(int64_t addr, uint16_t value, Instruction* instr) {
1892 if ((addr & 1) == 0) { 1892 if ((addr & 1) == 0 || kArchVariant == kMips64r6) {
1893 TraceMemWr(addr, value, HALF); 1893 TraceMemWr(addr, value, HALF);
1894 uint16_t* ptr = reinterpret_cast<uint16_t*>(addr); 1894 uint16_t* ptr = reinterpret_cast<uint16_t*>(addr);
1895 *ptr = value; 1895 *ptr = value;
1896 return; 1896 return;
1897 } 1897 }
1898 PrintF("Unaligned unsigned halfword write at 0x%08" PRIx64 1898 PrintF("Unaligned unsigned halfword write at 0x%08" PRIx64
1899 " , pc=0x%08" V8PRIxPTR "\n", 1899 " , pc=0x%08" V8PRIxPTR "\n",
1900 addr, reinterpret_cast<intptr_t>(instr)); 1900 addr, reinterpret_cast<intptr_t>(instr));
1901 DieOrDebug(); 1901 DieOrDebug();
1902 } 1902 }
1903 1903
1904 1904
1905 void Simulator::WriteH(int64_t addr, int16_t value, Instruction* instr) { 1905 void Simulator::WriteH(int64_t addr, int16_t value, Instruction* instr) {
1906 if ((addr & 1) == 0) { 1906 if ((addr & 1) == 0 || kArchVariant == kMips64r6) {
1907 TraceMemWr(addr, value, HALF); 1907 TraceMemWr(addr, value, HALF);
1908 int16_t* ptr = reinterpret_cast<int16_t*>(addr); 1908 int16_t* ptr = reinterpret_cast<int16_t*>(addr);
1909 *ptr = value; 1909 *ptr = value;
1910 return; 1910 return;
1911 } 1911 }
1912 PrintF("Unaligned halfword write at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR 1912 PrintF("Unaligned halfword write at 0x%08" PRIx64 " , pc=0x%08" V8PRIxPTR
1913 "\n", 1913 "\n",
1914 addr, reinterpret_cast<intptr_t>(instr)); 1914 addr, reinterpret_cast<intptr_t>(instr));
1915 DieOrDebug(); 1915 DieOrDebug();
1916 } 1916 }
(...skipping 2240 matching lines...) Expand 10 before | Expand all | Expand 10 after
4157 // Used for conditional branch instructions. 4157 // Used for conditional branch instructions.
4158 bool execute_branch_delay_instruction = false; 4158 bool execute_branch_delay_instruction = false;
4159 4159
4160 // Used for arithmetic instructions. 4160 // Used for arithmetic instructions.
4161 int64_t alu_out = 0; 4161 int64_t alu_out = 0;
4162 4162
4163 // Used for memory instructions. 4163 // Used for memory instructions.
4164 int64_t addr = 0x0; 4164 int64_t addr = 0x0;
4165 // Alignment for 32-bit integers used in LWL, LWR, etc. 4165 // Alignment for 32-bit integers used in LWL, LWR, etc.
4166 const int kInt32AlignmentMask = sizeof(uint32_t) - 1; 4166 const int kInt32AlignmentMask = sizeof(uint32_t) - 1;
4167 // Alignment for 64-bit integers used in LDL, LDR, etc.
4168 const int kInt64AlignmentMask = sizeof(uint64_t) - 1;
4167 4169
4168 // Branch instructions common part. 4170 // Branch instructions common part.
4169 auto BranchAndLinkHelper = [this, instr, &next_pc, 4171 auto BranchAndLinkHelper = [this, instr, &next_pc,
4170 &execute_branch_delay_instruction]( 4172 &execute_branch_delay_instruction](
4171 bool do_branch) { 4173 bool do_branch) {
4172 execute_branch_delay_instruction = true; 4174 execute_branch_delay_instruction = true;
4173 int64_t current_pc = get_pc(); 4175 int64_t current_pc = get_pc();
4174 if (do_branch) { 4176 if (do_branch) {
4175 int16_t imm16 = instr->Imm16Value(); 4177 int16_t imm16 = instr->Imm16Value();
4176 next_pc = current_pc + (imm16 << 2) + Instruction::kInstrSize; 4178 next_pc = current_pc + (imm16 << 2) + Instruction::kInstrSize;
(...skipping 281 matching lines...) Expand 10 before | Expand all | Expand 10 after
4458 break; 4460 break;
4459 case LH: 4461 case LH:
4460 set_register(rt_reg, ReadH(rs + se_imm16, instr)); 4462 set_register(rt_reg, ReadH(rs + se_imm16, instr));
4461 break; 4463 break;
4462 case LWL: { 4464 case LWL: {
4463 // al_offset is offset of the effective address within an aligned word. 4465 // al_offset is offset of the effective address within an aligned word.
4464 uint8_t al_offset = (rs + se_imm16) & kInt32AlignmentMask; 4466 uint8_t al_offset = (rs + se_imm16) & kInt32AlignmentMask;
4465 uint8_t byte_shift = kInt32AlignmentMask - al_offset; 4467 uint8_t byte_shift = kInt32AlignmentMask - al_offset;
4466 uint32_t mask = (1 << byte_shift * 8) - 1; 4468 uint32_t mask = (1 << byte_shift * 8) - 1;
4467 addr = rs + se_imm16 - al_offset; 4469 addr = rs + se_imm16 - al_offset;
4468 alu_out = ReadW(addr, instr); 4470 int32_t val = ReadW(addr, instr);
4469 alu_out <<= byte_shift * 8; 4471 val <<= byte_shift * 8;
4470 alu_out |= rt & mask; 4472 val |= rt & mask;
4471 set_register(rt_reg, alu_out); 4473 set_register(rt_reg, static_cast<int64_t>(val));
4472 break; 4474 break;
4473 } 4475 }
4474 case LW: 4476 case LW:
4475 set_register(rt_reg, ReadW(rs + se_imm16, instr)); 4477 set_register(rt_reg, ReadW(rs + se_imm16, instr));
4476 break; 4478 break;
4477 case LWU: 4479 case LWU:
4478 set_register(rt_reg, ReadWU(rs + se_imm16, instr)); 4480 set_register(rt_reg, ReadWU(rs + se_imm16, instr));
4479 break; 4481 break;
4480 case LD: 4482 case LD:
4481 set_register(rt_reg, Read2W(rs + se_imm16, instr)); 4483 set_register(rt_reg, Read2W(rs + se_imm16, instr));
4482 break; 4484 break;
4483 case LBU: 4485 case LBU:
4484 set_register(rt_reg, ReadBU(rs + se_imm16)); 4486 set_register(rt_reg, ReadBU(rs + se_imm16));
4485 break; 4487 break;
4486 case LHU: 4488 case LHU:
4487 set_register(rt_reg, ReadHU(rs + se_imm16, instr)); 4489 set_register(rt_reg, ReadHU(rs + se_imm16, instr));
4488 break; 4490 break;
4489 case LWR: { 4491 case LWR: {
4490 // al_offset is offset of the effective address within an aligned word. 4492 // al_offset is offset of the effective address within an aligned word.
4491 uint8_t al_offset = (rs + se_imm16) & kInt32AlignmentMask; 4493 uint8_t al_offset = (rs + se_imm16) & kInt32AlignmentMask;
4492 uint8_t byte_shift = kInt32AlignmentMask - al_offset; 4494 uint8_t byte_shift = kInt32AlignmentMask - al_offset;
4493 uint32_t mask = al_offset ? (~0 << (byte_shift + 1) * 8) : 0; 4495 uint32_t mask = al_offset ? (~0 << (byte_shift + 1) * 8) : 0;
4494 addr = rs + se_imm16 - al_offset; 4496 addr = rs + se_imm16 - al_offset;
4495 alu_out = ReadW(addr, instr); 4497 alu_out = ReadW(addr, instr);
4496 alu_out = static_cast<uint32_t> (alu_out) >> al_offset * 8; 4498 alu_out = static_cast<uint32_t> (alu_out) >> al_offset * 8;
4497 alu_out |= rt & mask; 4499 alu_out |= rt & mask;
4498 set_register(rt_reg, alu_out); 4500 set_register(rt_reg, alu_out);
4499 break; 4501 break;
4500 } 4502 }
4503 case LDL: {
4504 // al_offset is offset of the effective address within an aligned word.
4505 uint8_t al_offset = (rs + se_imm16) & kInt64AlignmentMask;
4506 uint8_t byte_shift = kInt64AlignmentMask - al_offset;
4507 uint64_t mask = (1UL << byte_shift * 8) - 1;
4508 addr = rs + se_imm16 - al_offset;
4509 alu_out = Read2W(addr, instr);
4510 alu_out <<= byte_shift * 8;
4511 alu_out |= rt & mask;
4512 set_register(rt_reg, alu_out);
4513 break;
4514 }
4515 case LDR: {
4516 // al_offset is offset of the effective address within an aligned word.
4517 uint8_t al_offset = (rs + se_imm16) & kInt64AlignmentMask;
4518 uint8_t byte_shift = kInt64AlignmentMask - al_offset;
4519 uint64_t mask = al_offset ? (~0UL << (byte_shift + 1) * 8) : 0UL;
4520 addr = rs + se_imm16 - al_offset;
4521 alu_out = Read2W(addr, instr);
4522 alu_out = alu_out >> al_offset * 8;
4523 alu_out |= rt & mask;
4524 set_register(rt_reg, alu_out);
4525 break;
4526 }
4501 case SB: 4527 case SB:
4502 WriteB(rs + se_imm16, static_cast<int8_t>(rt)); 4528 WriteB(rs + se_imm16, static_cast<int8_t>(rt));
4503 break; 4529 break;
4504 case SH: 4530 case SH:
4505 WriteH(rs + se_imm16, static_cast<uint16_t>(rt), instr); 4531 WriteH(rs + se_imm16, static_cast<uint16_t>(rt), instr);
4506 break; 4532 break;
4507 case SWL: { 4533 case SWL: {
4508 uint8_t al_offset = (rs + se_imm16) & kInt32AlignmentMask; 4534 uint8_t al_offset = (rs + se_imm16) & kInt32AlignmentMask;
4509 uint8_t byte_shift = kInt32AlignmentMask - al_offset; 4535 uint8_t byte_shift = kInt32AlignmentMask - al_offset;
4510 uint32_t mask = byte_shift ? (~0 << (al_offset + 1) * 8) : 0; 4536 uint32_t mask = byte_shift ? (~0 << (al_offset + 1) * 8) : 0;
(...skipping 11 matching lines...) Expand all
4522 break; 4548 break;
4523 case SWR: { 4549 case SWR: {
4524 uint8_t al_offset = (rs + se_imm16) & kInt32AlignmentMask; 4550 uint8_t al_offset = (rs + se_imm16) & kInt32AlignmentMask;
4525 uint32_t mask = (1 << al_offset * 8) - 1; 4551 uint32_t mask = (1 << al_offset * 8) - 1;
4526 addr = rs + se_imm16 - al_offset; 4552 addr = rs + se_imm16 - al_offset;
4527 uint64_t mem_value = ReadW(addr, instr); 4553 uint64_t mem_value = ReadW(addr, instr);
4528 mem_value = (rt << al_offset * 8) | (mem_value & mask); 4554 mem_value = (rt << al_offset * 8) | (mem_value & mask);
4529 WriteW(addr, static_cast<int32_t>(mem_value), instr); 4555 WriteW(addr, static_cast<int32_t>(mem_value), instr);
4530 break; 4556 break;
4531 } 4557 }
4558 case SDL: {
4559 uint8_t al_offset = (rs + se_imm16) & kInt64AlignmentMask;
4560 uint8_t byte_shift = kInt64AlignmentMask - al_offset;
4561 uint64_t mask = byte_shift ? (~0UL << (al_offset + 1) * 8) : 0;
4562 addr = rs + se_imm16 - al_offset;
4563 uint64_t mem_value = Read2W(addr, instr) & mask;
4564 mem_value |= rt >> byte_shift * 8;
4565 Write2W(addr, mem_value, instr);
4566 break;
4567 }
4568 case SDR: {
4569 uint8_t al_offset = (rs + se_imm16) & kInt64AlignmentMask;
4570 uint64_t mask = (1UL << al_offset * 8) - 1;
4571 addr = rs + se_imm16 - al_offset;
4572 uint64_t mem_value = Read2W(addr, instr);
4573 mem_value = (rt << al_offset * 8) | (mem_value & mask);
4574 Write2W(addr, mem_value, instr);
4575 break;
4576 }
4532 case LWC1: 4577 case LWC1:
4533 set_fpu_register(ft_reg, kFPUInvalidResult); // Trash upper 32 bits. 4578 set_fpu_register(ft_reg, kFPUInvalidResult); // Trash upper 32 bits.
4534 set_fpu_register_word(ft_reg, ReadW(rs + se_imm16, instr)); 4579 set_fpu_register_word(ft_reg, ReadW(rs + se_imm16, instr));
4535 break; 4580 break;
4536 case LDC1: 4581 case LDC1:
4537 set_fpu_register_double(ft_reg, ReadD(rs + se_imm16, instr)); 4582 set_fpu_register_double(ft_reg, ReadD(rs + se_imm16, instr));
4538 break; 4583 break;
4539 case SWC1: { 4584 case SWC1: {
4540 int32_t alu_out_32 = static_cast<int32_t>(get_fpu_register(ft_reg)); 4585 int32_t alu_out_32 = static_cast<int32_t>(get_fpu_register(ft_reg));
4541 WriteW(rs + se_imm16, alu_out_32, instr); 4586 WriteW(rs + se_imm16, alu_out_32, instr);
(...skipping 350 matching lines...) Expand 10 before | Expand all | Expand 10 after
4892 } 4937 }
4893 4938
4894 4939
4895 #undef UNSUPPORTED 4940 #undef UNSUPPORTED
4896 } // namespace internal 4941 } // namespace internal
4897 } // namespace v8 4942 } // namespace v8
4898 4943
4899 #endif // USE_SIMULATOR 4944 #endif // USE_SIMULATOR
4900 4945
4901 #endif // V8_TARGET_ARCH_MIPS64 4946 #endif // V8_TARGET_ARCH_MIPS64
OLDNEW
« no previous file with comments | « src/mips64/macro-assembler-mips64.cc ('k') | test/cctest/test-macro-assembler-mips.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698