| OLD | NEW |
| 1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 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 "src/compiler/code-generator.h" | 5 #include "src/compiler/code-generator.h" |
| 6 | 6 |
| 7 #include <limits> | 7 #include <limits> |
| 8 | 8 |
| 9 #include "src/compilation-info.h" | 9 #include "src/compilation-info.h" |
| 10 #include "src/compiler/code-generator-impl.h" | 10 #include "src/compiler/code-generator-impl.h" |
| (...skipping 251 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 262 Operand const operand_; | 262 Operand const operand_; |
| 263 Register const value_; | 263 Register const value_; |
| 264 Register const scratch0_; | 264 Register const scratch0_; |
| 265 Register const scratch1_; | 265 Register const scratch1_; |
| 266 RecordWriteMode const mode_; | 266 RecordWriteMode const mode_; |
| 267 }; | 267 }; |
| 268 | 268 |
| 269 class WasmOutOfLineTrap final : public OutOfLineCode { | 269 class WasmOutOfLineTrap final : public OutOfLineCode { |
| 270 public: | 270 public: |
| 271 WasmOutOfLineTrap(CodeGenerator* gen, int pc, bool frame_elided, | 271 WasmOutOfLineTrap(CodeGenerator* gen, int pc, bool frame_elided, |
| 272 int32_t position, Instruction* instr) | 272 int32_t position) |
| 273 : OutOfLineCode(gen), | 273 : OutOfLineCode(gen), |
| 274 gen_(gen), | 274 gen_(gen), |
| 275 pc_(pc), | 275 pc_(pc), |
| 276 frame_elided_(frame_elided), | 276 frame_elided_(frame_elided), |
| 277 position_(position), | 277 position_(position) {} |
| 278 instr_(instr) {} | |
| 279 | 278 |
| 280 // TODO(eholk): Refactor this method to take the code generator as a | 279 // TODO(eholk): Refactor this method to take the code generator as a |
| 281 // parameter. | 280 // parameter. |
| 282 void Generate() final { | 281 void Generate() final { |
| 283 Address current_pc = __ pc(); | 282 Address current_pc = __ pc(); |
| 284 | 283 |
| 285 __ RecordProtectedInstruction(pc_, current_pc); | 284 __ RecordProtectedInstruction(pc_, current_pc); |
| 286 | 285 |
| 287 if (frame_elided_) { | 286 if (frame_elided_) { |
| 288 __ EnterFrame(StackFrame::WASM_COMPILED); | 287 __ EnterFrame(StackFrame::WASM_COMPILED); |
| 289 } | 288 } |
| 290 | 289 |
| 291 wasm::TrapReason trap_id = wasm::kTrapMemOutOfBounds; | 290 wasm::TrapReason trap_id = wasm::kTrapMemOutOfBounds; |
| 292 int trap_reason = wasm::WasmOpcodes::TrapReasonToMessageId(trap_id); | 291 int trap_reason = wasm::WasmOpcodes::TrapReasonToMessageId(trap_id); |
| 293 __ Push(Smi::FromInt(trap_reason)); | 292 __ Push(Smi::FromInt(trap_reason)); |
| 294 __ Push(Smi::FromInt(position_)); | 293 __ Push(Smi::FromInt(position_)); |
| 295 __ Move(rsi, gen_->isolate()->native_context()); | 294 __ Move(rsi, gen_->isolate()->native_context()); |
| 296 __ CallRuntime(Runtime::kThrowWasmError); | 295 __ CallRuntime(Runtime::kThrowWasmError); |
| 297 | 296 |
| 298 if (instr_->reference_map() != nullptr) { | 297 ReferenceMap* reference_map = |
| 299 gen_->RecordSafepoint(instr_->reference_map(), Safepoint::kSimple, 0, | 298 new (gen_->code()->zone()) ReferenceMap(gen_->code()->zone()); |
| 300 Safepoint::kNoLazyDeopt); | 299 gen_->RecordSafepoint(reference_map, Safepoint::kSimple, 0, |
| 301 } | 300 Safepoint::kNoLazyDeopt); |
| 302 } | 301 } |
| 303 | 302 |
| 304 private: | 303 private: |
| 305 CodeGenerator* gen_; | 304 CodeGenerator* gen_; |
| 306 int pc_; | 305 int pc_; |
| 307 bool frame_elided_; | 306 bool frame_elided_; |
| 308 int32_t position_; | 307 int32_t position_; |
| 309 Instruction* instr_; | |
| 310 }; | 308 }; |
| 311 | 309 |
| 312 void EmitOOLTrapIfNeeded(Zone* zone, CodeGenerator* codegen, | 310 void EmitOOLTrapIfNeeded(Zone* zone, CodeGenerator* codegen, |
| 313 InstructionCode opcode, size_t input_count, | 311 InstructionCode opcode, size_t input_count, |
| 314 X64OperandConverter& i, int pc, Instruction* instr) { | 312 X64OperandConverter& i, int pc) { |
| 315 const X64MemoryProtection protection = | 313 const X64MemoryProtection protection = |
| 316 static_cast<X64MemoryProtection>(MiscField::decode(opcode)); | 314 static_cast<X64MemoryProtection>(MiscField::decode(opcode)); |
| 317 if (protection == X64MemoryProtection::kProtected) { | 315 if (protection == X64MemoryProtection::kProtected) { |
| 318 const bool frame_elided = !codegen->frame_access_state()->has_frame(); | 316 const bool frame_elided = !codegen->frame_access_state()->has_frame(); |
| 319 const int32_t position = i.InputInt32(input_count - 1); | 317 const int32_t position = i.InputInt32(input_count - 1); |
| 320 new (zone) WasmOutOfLineTrap(codegen, pc, frame_elided, position, instr); | 318 new (zone) WasmOutOfLineTrap(codegen, pc, frame_elided, position); |
| 321 } | 319 } |
| 322 } | 320 } |
| 323 } // namespace | 321 } // namespace |
| 324 | 322 |
| 325 | 323 |
| 326 #define ASSEMBLE_UNOP(asm_instr) \ | 324 #define ASSEMBLE_UNOP(asm_instr) \ |
| 327 do { \ | 325 do { \ |
| 328 if (instr->Output()->IsRegister()) { \ | 326 if (instr->Output()->IsRegister()) { \ |
| 329 __ asm_instr(i.OutputRegister()); \ | 327 __ asm_instr(i.OutputRegister()); \ |
| 330 } else { \ | 328 } else { \ |
| (...skipping 1519 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1850 i.InputOperand(0)); | 1848 i.InputOperand(0)); |
| 1851 } | 1849 } |
| 1852 break; | 1850 break; |
| 1853 } | 1851 } |
| 1854 case kSSEFloat64SilenceNaN: | 1852 case kSSEFloat64SilenceNaN: |
| 1855 __ Xorpd(kScratchDoubleReg, kScratchDoubleReg); | 1853 __ Xorpd(kScratchDoubleReg, kScratchDoubleReg); |
| 1856 __ Subsd(i.InputDoubleRegister(0), kScratchDoubleReg); | 1854 __ Subsd(i.InputDoubleRegister(0), kScratchDoubleReg); |
| 1857 break; | 1855 break; |
| 1858 case kX64Movsxbl: | 1856 case kX64Movsxbl: |
| 1859 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1857 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1860 __ pc_offset(), instr); | 1858 __ pc_offset()); |
| 1861 ASSEMBLE_MOVX(movsxbl); | 1859 ASSEMBLE_MOVX(movsxbl); |
| 1862 __ AssertZeroExtended(i.OutputRegister()); | 1860 __ AssertZeroExtended(i.OutputRegister()); |
| 1863 break; | 1861 break; |
| 1864 case kX64Movzxbl: | 1862 case kX64Movzxbl: |
| 1865 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1863 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1866 __ pc_offset(), instr); | 1864 __ pc_offset()); |
| 1867 ASSEMBLE_MOVX(movzxbl); | 1865 ASSEMBLE_MOVX(movzxbl); |
| 1868 __ AssertZeroExtended(i.OutputRegister()); | 1866 __ AssertZeroExtended(i.OutputRegister()); |
| 1869 break; | 1867 break; |
| 1870 case kX64Movsxbq: | 1868 case kX64Movsxbq: |
| 1871 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1869 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1872 __ pc_offset(), instr); | 1870 __ pc_offset()); |
| 1873 ASSEMBLE_MOVX(movsxbq); | 1871 ASSEMBLE_MOVX(movsxbq); |
| 1874 break; | 1872 break; |
| 1875 case kX64Movzxbq: | 1873 case kX64Movzxbq: |
| 1876 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1874 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1877 __ pc_offset(), instr); | 1875 __ pc_offset()); |
| 1878 ASSEMBLE_MOVX(movzxbq); | 1876 ASSEMBLE_MOVX(movzxbq); |
| 1879 __ AssertZeroExtended(i.OutputRegister()); | 1877 __ AssertZeroExtended(i.OutputRegister()); |
| 1880 break; | 1878 break; |
| 1881 case kX64Movb: { | 1879 case kX64Movb: { |
| 1882 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1880 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1883 __ pc_offset(), instr); | 1881 __ pc_offset()); |
| 1884 size_t index = 0; | 1882 size_t index = 0; |
| 1885 Operand operand = i.MemoryOperand(&index); | 1883 Operand operand = i.MemoryOperand(&index); |
| 1886 if (HasImmediateInput(instr, index)) { | 1884 if (HasImmediateInput(instr, index)) { |
| 1887 __ movb(operand, Immediate(i.InputInt8(index))); | 1885 __ movb(operand, Immediate(i.InputInt8(index))); |
| 1888 } else { | 1886 } else { |
| 1889 __ movb(operand, i.InputRegister(index)); | 1887 __ movb(operand, i.InputRegister(index)); |
| 1890 } | 1888 } |
| 1891 break; | 1889 break; |
| 1892 } | 1890 } |
| 1893 case kX64Movsxwl: | 1891 case kX64Movsxwl: |
| 1894 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1892 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1895 __ pc_offset(), instr); | 1893 __ pc_offset()); |
| 1896 ASSEMBLE_MOVX(movsxwl); | 1894 ASSEMBLE_MOVX(movsxwl); |
| 1897 __ AssertZeroExtended(i.OutputRegister()); | 1895 __ AssertZeroExtended(i.OutputRegister()); |
| 1898 break; | 1896 break; |
| 1899 case kX64Movzxwl: | 1897 case kX64Movzxwl: |
| 1900 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1898 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1901 __ pc_offset(), instr); | 1899 __ pc_offset()); |
| 1902 ASSEMBLE_MOVX(movzxwl); | 1900 ASSEMBLE_MOVX(movzxwl); |
| 1903 __ AssertZeroExtended(i.OutputRegister()); | 1901 __ AssertZeroExtended(i.OutputRegister()); |
| 1904 break; | 1902 break; |
| 1905 case kX64Movsxwq: | 1903 case kX64Movsxwq: |
| 1906 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1904 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1907 __ pc_offset(), instr); | 1905 __ pc_offset()); |
| 1908 ASSEMBLE_MOVX(movsxwq); | 1906 ASSEMBLE_MOVX(movsxwq); |
| 1909 break; | 1907 break; |
| 1910 case kX64Movzxwq: | 1908 case kX64Movzxwq: |
| 1911 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1909 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1912 __ pc_offset(), instr); | 1910 __ pc_offset()); |
| 1913 ASSEMBLE_MOVX(movzxwq); | 1911 ASSEMBLE_MOVX(movzxwq); |
| 1914 __ AssertZeroExtended(i.OutputRegister()); | 1912 __ AssertZeroExtended(i.OutputRegister()); |
| 1915 break; | 1913 break; |
| 1916 case kX64Movw: { | 1914 case kX64Movw: { |
| 1917 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1915 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1918 __ pc_offset(), instr); | 1916 __ pc_offset()); |
| 1919 size_t index = 0; | 1917 size_t index = 0; |
| 1920 Operand operand = i.MemoryOperand(&index); | 1918 Operand operand = i.MemoryOperand(&index); |
| 1921 if (HasImmediateInput(instr, index)) { | 1919 if (HasImmediateInput(instr, index)) { |
| 1922 __ movw(operand, Immediate(i.InputInt16(index))); | 1920 __ movw(operand, Immediate(i.InputInt16(index))); |
| 1923 } else { | 1921 } else { |
| 1924 __ movw(operand, i.InputRegister(index)); | 1922 __ movw(operand, i.InputRegister(index)); |
| 1925 } | 1923 } |
| 1926 break; | 1924 break; |
| 1927 } | 1925 } |
| 1928 case kX64Movl: | 1926 case kX64Movl: |
| 1929 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1927 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1930 __ pc_offset(), instr); | 1928 __ pc_offset()); |
| 1931 if (instr->HasOutput()) { | 1929 if (instr->HasOutput()) { |
| 1932 if (instr->addressing_mode() == kMode_None) { | 1930 if (instr->addressing_mode() == kMode_None) { |
| 1933 if (instr->InputAt(0)->IsRegister()) { | 1931 if (instr->InputAt(0)->IsRegister()) { |
| 1934 __ movl(i.OutputRegister(), i.InputRegister(0)); | 1932 __ movl(i.OutputRegister(), i.InputRegister(0)); |
| 1935 } else { | 1933 } else { |
| 1936 __ movl(i.OutputRegister(), i.InputOperand(0)); | 1934 __ movl(i.OutputRegister(), i.InputOperand(0)); |
| 1937 } | 1935 } |
| 1938 } else { | 1936 } else { |
| 1939 __ movl(i.OutputRegister(), i.MemoryOperand()); | 1937 __ movl(i.OutputRegister(), i.MemoryOperand()); |
| 1940 } | 1938 } |
| 1941 __ AssertZeroExtended(i.OutputRegister()); | 1939 __ AssertZeroExtended(i.OutputRegister()); |
| 1942 } else { | 1940 } else { |
| 1943 size_t index = 0; | 1941 size_t index = 0; |
| 1944 Operand operand = i.MemoryOperand(&index); | 1942 Operand operand = i.MemoryOperand(&index); |
| 1945 if (HasImmediateInput(instr, index)) { | 1943 if (HasImmediateInput(instr, index)) { |
| 1946 __ movl(operand, i.InputImmediate(index)); | 1944 __ movl(operand, i.InputImmediate(index)); |
| 1947 } else { | 1945 } else { |
| 1948 __ movl(operand, i.InputRegister(index)); | 1946 __ movl(operand, i.InputRegister(index)); |
| 1949 } | 1947 } |
| 1950 } | 1948 } |
| 1951 break; | 1949 break; |
| 1952 case kX64Movsxlq: | 1950 case kX64Movsxlq: |
| 1953 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1951 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1954 __ pc_offset(), instr); | 1952 __ pc_offset()); |
| 1955 ASSEMBLE_MOVX(movsxlq); | 1953 ASSEMBLE_MOVX(movsxlq); |
| 1956 break; | 1954 break; |
| 1957 case kX64Movq: | 1955 case kX64Movq: |
| 1958 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1956 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1959 __ pc_offset(), instr); | 1957 __ pc_offset()); |
| 1960 if (instr->HasOutput()) { | 1958 if (instr->HasOutput()) { |
| 1961 __ movq(i.OutputRegister(), i.MemoryOperand()); | 1959 __ movq(i.OutputRegister(), i.MemoryOperand()); |
| 1962 } else { | 1960 } else { |
| 1963 size_t index = 0; | 1961 size_t index = 0; |
| 1964 Operand operand = i.MemoryOperand(&index); | 1962 Operand operand = i.MemoryOperand(&index); |
| 1965 if (HasImmediateInput(instr, index)) { | 1963 if (HasImmediateInput(instr, index)) { |
| 1966 __ movq(operand, i.InputImmediate(index)); | 1964 __ movq(operand, i.InputImmediate(index)); |
| 1967 } else { | 1965 } else { |
| 1968 __ movq(operand, i.InputRegister(index)); | 1966 __ movq(operand, i.InputRegister(index)); |
| 1969 } | 1967 } |
| 1970 } | 1968 } |
| 1971 break; | 1969 break; |
| 1972 case kX64Movss: | 1970 case kX64Movss: |
| 1973 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1971 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1974 __ pc_offset(), instr); | 1972 __ pc_offset()); |
| 1975 if (instr->HasOutput()) { | 1973 if (instr->HasOutput()) { |
| 1976 __ movss(i.OutputDoubleRegister(), i.MemoryOperand()); | 1974 __ movss(i.OutputDoubleRegister(), i.MemoryOperand()); |
| 1977 } else { | 1975 } else { |
| 1978 size_t index = 0; | 1976 size_t index = 0; |
| 1979 Operand operand = i.MemoryOperand(&index); | 1977 Operand operand = i.MemoryOperand(&index); |
| 1980 __ movss(operand, i.InputDoubleRegister(index)); | 1978 __ movss(operand, i.InputDoubleRegister(index)); |
| 1981 } | 1979 } |
| 1982 break; | 1980 break; |
| 1983 case kX64Movsd: | 1981 case kX64Movsd: |
| 1984 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1982 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
| 1985 __ pc_offset(), instr); | 1983 __ pc_offset()); |
| 1986 if (instr->HasOutput()) { | 1984 if (instr->HasOutput()) { |
| 1987 __ Movsd(i.OutputDoubleRegister(), i.MemoryOperand()); | 1985 __ Movsd(i.OutputDoubleRegister(), i.MemoryOperand()); |
| 1988 } else { | 1986 } else { |
| 1989 size_t index = 0; | 1987 size_t index = 0; |
| 1990 Operand operand = i.MemoryOperand(&index); | 1988 Operand operand = i.MemoryOperand(&index); |
| 1991 __ Movsd(operand, i.InputDoubleRegister(index)); | 1989 __ Movsd(operand, i.InputDoubleRegister(index)); |
| 1992 } | 1990 } |
| 1993 break; | 1991 break; |
| 1994 case kX64BitcastFI: | 1992 case kX64BitcastFI: |
| 1995 if (instr->InputAt(0)->IsFPStackSlot()) { | 1993 if (instr->InputAt(0)->IsFPStackSlot()) { |
| (...skipping 858 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2854 int padding_size = last_lazy_deopt_pc_ + space_needed - current_pc; | 2852 int padding_size = last_lazy_deopt_pc_ + space_needed - current_pc; |
| 2855 __ Nop(padding_size); | 2853 __ Nop(padding_size); |
| 2856 } | 2854 } |
| 2857 } | 2855 } |
| 2858 | 2856 |
| 2859 #undef __ | 2857 #undef __ |
| 2860 | 2858 |
| 2861 } // namespace compiler | 2859 } // namespace compiler |
| 2862 } // namespace internal | 2860 } // namespace internal |
| 2863 } // namespace v8 | 2861 } // namespace v8 |
| OLD | NEW |