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 __ RecordProtectedInstructionLanding(pc_); | 282 __ RecordProtectedInstructionLanding(pc_); |
284 | 283 |
285 if (frame_elided_) { | 284 if (frame_elided_) { |
286 __ EnterFrame(StackFrame::WASM_COMPILED); | 285 __ EnterFrame(StackFrame::WASM_COMPILED); |
287 } | 286 } |
288 | 287 |
289 wasm::TrapReason trap_id = wasm::kTrapMemOutOfBounds; | 288 wasm::TrapReason trap_id = wasm::kTrapMemOutOfBounds; |
290 int trap_reason = wasm::WasmOpcodes::TrapReasonToMessageId(trap_id); | 289 int trap_reason = wasm::WasmOpcodes::TrapReasonToMessageId(trap_id); |
291 __ Push(Smi::FromInt(trap_reason)); | 290 __ Push(Smi::FromInt(trap_reason)); |
292 __ Push(Smi::FromInt(position_)); | 291 __ Push(Smi::FromInt(position_)); |
ahaas
2017/02/20 09:27:24
I think it would be better to pass in the instruct
Eric Holk
2017/02/23 02:16:55
I added a TODO. It looks like we can and should re
| |
293 __ Move(rsi, gen_->isolate()->native_context()); | 292 __ Move(rsi, Smi::kZero); |
294 __ CallRuntime(Runtime::kThrowWasmError); | 293 __ CallRuntime(Runtime::kThrowWasmError); |
295 | 294 |
296 if (instr_->reference_map() != nullptr) { | 295 ReferenceMap* reference_map = |
titzer
2017/02/20 09:50:08
I don't think we always want to generate a referen
Eric Holk
2017/02/23 02:16:55
Is there a way to call RecordSafepoint without a r
| |
297 gen_->RecordSafepoint(instr_->reference_map(), Safepoint::kSimple, 0, | 296 new (gen_->code()->zone()) ReferenceMap(gen_->code()->zone()); |
298 Safepoint::kNoLazyDeopt); | 297 gen_->RecordSafepoint(reference_map, Safepoint::kSimple, 0, |
299 } | 298 Safepoint::kNoLazyDeopt); |
300 } | 299 } |
301 | 300 |
302 private: | 301 private: |
303 CodeGenerator* gen_; | 302 CodeGenerator* gen_; |
304 int pc_; | 303 int pc_; |
305 bool frame_elided_; | 304 bool frame_elided_; |
306 int32_t position_; | 305 int32_t position_; |
307 Instruction* instr_; | |
308 }; | 306 }; |
309 | 307 |
310 void EmitOOLTrapIfNeeded(Zone* zone, CodeGenerator* codegen, | 308 void EmitOOLTrapIfNeeded(Zone* zone, CodeGenerator* codegen, |
311 InstructionCode opcode, size_t input_count, | 309 InstructionCode opcode, size_t input_count, |
312 X64OperandConverter& i, int pc, Instruction* instr) { | 310 X64OperandConverter& i, int pc) { |
313 const X64MemoryProtection protection = | 311 const X64MemoryProtection protection = |
314 static_cast<X64MemoryProtection>(MiscField::decode(opcode)); | 312 static_cast<X64MemoryProtection>(MiscField::decode(opcode)); |
315 if (protection == X64MemoryProtection::kProtected) { | 313 if (protection == X64MemoryProtection::kProtected) { |
316 const bool frame_elided = !codegen->frame_access_state()->has_frame(); | 314 const bool frame_elided = !codegen->frame_access_state()->has_frame(); |
317 const int32_t position = i.InputInt32(input_count - 1); | 315 const int32_t position = i.InputInt32(input_count - 1); |
318 new (zone) WasmOutOfLineTrap(codegen, pc, frame_elided, position, instr); | 316 new (zone) WasmOutOfLineTrap(codegen, pc, frame_elided, position); |
319 } | 317 } |
320 } | 318 } |
321 } // namespace | 319 } // namespace |
322 | 320 |
323 | 321 |
324 #define ASSEMBLE_UNOP(asm_instr) \ | 322 #define ASSEMBLE_UNOP(asm_instr) \ |
325 do { \ | 323 do { \ |
326 if (instr->Output()->IsRegister()) { \ | 324 if (instr->Output()->IsRegister()) { \ |
327 __ asm_instr(i.OutputRegister()); \ | 325 __ asm_instr(i.OutputRegister()); \ |
328 } else { \ | 326 } else { \ |
(...skipping 1517 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1846 i.InputOperand(0)); | 1844 i.InputOperand(0)); |
1847 } | 1845 } |
1848 break; | 1846 break; |
1849 } | 1847 } |
1850 case kSSEFloat64SilenceNaN: | 1848 case kSSEFloat64SilenceNaN: |
1851 __ Xorpd(kScratchDoubleReg, kScratchDoubleReg); | 1849 __ Xorpd(kScratchDoubleReg, kScratchDoubleReg); |
1852 __ Subsd(i.InputDoubleRegister(0), kScratchDoubleReg); | 1850 __ Subsd(i.InputDoubleRegister(0), kScratchDoubleReg); |
1853 break; | 1851 break; |
1854 case kX64Movsxbl: | 1852 case kX64Movsxbl: |
1855 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1853 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1856 __ pc_offset(), instr); | 1854 __ pc_offset()); |
1857 ASSEMBLE_MOVX(movsxbl); | 1855 ASSEMBLE_MOVX(movsxbl); |
1858 __ AssertZeroExtended(i.OutputRegister()); | 1856 __ AssertZeroExtended(i.OutputRegister()); |
1859 break; | 1857 break; |
1860 case kX64Movzxbl: | 1858 case kX64Movzxbl: |
1861 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1859 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1862 __ pc_offset(), instr); | 1860 __ pc_offset()); |
1863 ASSEMBLE_MOVX(movzxbl); | 1861 ASSEMBLE_MOVX(movzxbl); |
1864 __ AssertZeroExtended(i.OutputRegister()); | 1862 __ AssertZeroExtended(i.OutputRegister()); |
1865 break; | 1863 break; |
1866 case kX64Movsxbq: | 1864 case kX64Movsxbq: |
1867 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1865 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1868 __ pc_offset(), instr); | 1866 __ pc_offset()); |
1869 ASSEMBLE_MOVX(movsxbq); | 1867 ASSEMBLE_MOVX(movsxbq); |
1870 break; | 1868 break; |
1871 case kX64Movzxbq: | 1869 case kX64Movzxbq: |
1872 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1870 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1873 __ pc_offset(), instr); | 1871 __ pc_offset()); |
1874 ASSEMBLE_MOVX(movzxbq); | 1872 ASSEMBLE_MOVX(movzxbq); |
1875 __ AssertZeroExtended(i.OutputRegister()); | 1873 __ AssertZeroExtended(i.OutputRegister()); |
1876 break; | 1874 break; |
1877 case kX64Movb: { | 1875 case kX64Movb: { |
1878 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1876 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1879 __ pc_offset(), instr); | 1877 __ pc_offset()); |
1880 size_t index = 0; | 1878 size_t index = 0; |
1881 Operand operand = i.MemoryOperand(&index); | 1879 Operand operand = i.MemoryOperand(&index); |
1882 if (HasImmediateInput(instr, index)) { | 1880 if (HasImmediateInput(instr, index)) { |
1883 __ movb(operand, Immediate(i.InputInt8(index))); | 1881 __ movb(operand, Immediate(i.InputInt8(index))); |
1884 } else { | 1882 } else { |
1885 __ movb(operand, i.InputRegister(index)); | 1883 __ movb(operand, i.InputRegister(index)); |
1886 } | 1884 } |
1887 break; | 1885 break; |
1888 } | 1886 } |
1889 case kX64Movsxwl: | 1887 case kX64Movsxwl: |
1890 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1888 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1891 __ pc_offset(), instr); | 1889 __ pc_offset()); |
1892 ASSEMBLE_MOVX(movsxwl); | 1890 ASSEMBLE_MOVX(movsxwl); |
1893 __ AssertZeroExtended(i.OutputRegister()); | 1891 __ AssertZeroExtended(i.OutputRegister()); |
1894 break; | 1892 break; |
1895 case kX64Movzxwl: | 1893 case kX64Movzxwl: |
1896 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1894 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1897 __ pc_offset(), instr); | 1895 __ pc_offset()); |
1898 ASSEMBLE_MOVX(movzxwl); | 1896 ASSEMBLE_MOVX(movzxwl); |
1899 __ AssertZeroExtended(i.OutputRegister()); | 1897 __ AssertZeroExtended(i.OutputRegister()); |
1900 break; | 1898 break; |
1901 case kX64Movsxwq: | 1899 case kX64Movsxwq: |
1902 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1900 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1903 __ pc_offset(), instr); | 1901 __ pc_offset()); |
1904 ASSEMBLE_MOVX(movsxwq); | 1902 ASSEMBLE_MOVX(movsxwq); |
1905 break; | 1903 break; |
1906 case kX64Movzxwq: | 1904 case kX64Movzxwq: |
1907 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1905 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1908 __ pc_offset(), instr); | 1906 __ pc_offset()); |
1909 ASSEMBLE_MOVX(movzxwq); | 1907 ASSEMBLE_MOVX(movzxwq); |
1910 __ AssertZeroExtended(i.OutputRegister()); | 1908 __ AssertZeroExtended(i.OutputRegister()); |
1911 break; | 1909 break; |
1912 case kX64Movw: { | 1910 case kX64Movw: { |
1913 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1911 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1914 __ pc_offset(), instr); | 1912 __ pc_offset()); |
1915 size_t index = 0; | 1913 size_t index = 0; |
1916 Operand operand = i.MemoryOperand(&index); | 1914 Operand operand = i.MemoryOperand(&index); |
1917 if (HasImmediateInput(instr, index)) { | 1915 if (HasImmediateInput(instr, index)) { |
1918 __ movw(operand, Immediate(i.InputInt16(index))); | 1916 __ movw(operand, Immediate(i.InputInt16(index))); |
1919 } else { | 1917 } else { |
1920 __ movw(operand, i.InputRegister(index)); | 1918 __ movw(operand, i.InputRegister(index)); |
1921 } | 1919 } |
1922 break; | 1920 break; |
1923 } | 1921 } |
1924 case kX64Movl: | 1922 case kX64Movl: |
1925 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1923 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1926 __ pc_offset(), instr); | 1924 __ pc_offset()); |
1927 if (instr->HasOutput()) { | 1925 if (instr->HasOutput()) { |
1928 if (instr->addressing_mode() == kMode_None) { | 1926 if (instr->addressing_mode() == kMode_None) { |
1929 if (instr->InputAt(0)->IsRegister()) { | 1927 if (instr->InputAt(0)->IsRegister()) { |
1930 __ movl(i.OutputRegister(), i.InputRegister(0)); | 1928 __ movl(i.OutputRegister(), i.InputRegister(0)); |
1931 } else { | 1929 } else { |
1932 __ movl(i.OutputRegister(), i.InputOperand(0)); | 1930 __ movl(i.OutputRegister(), i.InputOperand(0)); |
1933 } | 1931 } |
1934 } else { | 1932 } else { |
1935 __ movl(i.OutputRegister(), i.MemoryOperand()); | 1933 __ movl(i.OutputRegister(), i.MemoryOperand()); |
1936 } | 1934 } |
1937 __ AssertZeroExtended(i.OutputRegister()); | 1935 __ AssertZeroExtended(i.OutputRegister()); |
1938 } else { | 1936 } else { |
1939 size_t index = 0; | 1937 size_t index = 0; |
1940 Operand operand = i.MemoryOperand(&index); | 1938 Operand operand = i.MemoryOperand(&index); |
1941 if (HasImmediateInput(instr, index)) { | 1939 if (HasImmediateInput(instr, index)) { |
1942 __ movl(operand, i.InputImmediate(index)); | 1940 __ movl(operand, i.InputImmediate(index)); |
1943 } else { | 1941 } else { |
1944 __ movl(operand, i.InputRegister(index)); | 1942 __ movl(operand, i.InputRegister(index)); |
1945 } | 1943 } |
1946 } | 1944 } |
1947 break; | 1945 break; |
1948 case kX64Movsxlq: | 1946 case kX64Movsxlq: |
1949 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1947 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1950 __ pc_offset(), instr); | 1948 __ pc_offset()); |
1951 ASSEMBLE_MOVX(movsxlq); | 1949 ASSEMBLE_MOVX(movsxlq); |
1952 break; | 1950 break; |
1953 case kX64Movq: | 1951 case kX64Movq: |
1954 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1952 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1955 __ pc_offset(), instr); | 1953 __ pc_offset()); |
1956 if (instr->HasOutput()) { | 1954 if (instr->HasOutput()) { |
1957 __ movq(i.OutputRegister(), i.MemoryOperand()); | 1955 __ movq(i.OutputRegister(), i.MemoryOperand()); |
1958 } else { | 1956 } else { |
1959 size_t index = 0; | 1957 size_t index = 0; |
1960 Operand operand = i.MemoryOperand(&index); | 1958 Operand operand = i.MemoryOperand(&index); |
1961 if (HasImmediateInput(instr, index)) { | 1959 if (HasImmediateInput(instr, index)) { |
1962 __ movq(operand, i.InputImmediate(index)); | 1960 __ movq(operand, i.InputImmediate(index)); |
1963 } else { | 1961 } else { |
1964 __ movq(operand, i.InputRegister(index)); | 1962 __ movq(operand, i.InputRegister(index)); |
1965 } | 1963 } |
1966 } | 1964 } |
1967 break; | 1965 break; |
1968 case kX64Movss: | 1966 case kX64Movss: |
1969 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1967 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1970 __ pc_offset(), instr); | 1968 __ pc_offset()); |
1971 if (instr->HasOutput()) { | 1969 if (instr->HasOutput()) { |
1972 __ movss(i.OutputDoubleRegister(), i.MemoryOperand()); | 1970 __ movss(i.OutputDoubleRegister(), i.MemoryOperand()); |
1973 } else { | 1971 } else { |
1974 size_t index = 0; | 1972 size_t index = 0; |
1975 Operand operand = i.MemoryOperand(&index); | 1973 Operand operand = i.MemoryOperand(&index); |
1976 __ movss(operand, i.InputDoubleRegister(index)); | 1974 __ movss(operand, i.InputDoubleRegister(index)); |
1977 } | 1975 } |
1978 break; | 1976 break; |
1979 case kX64Movsd: | 1977 case kX64Movsd: |
1980 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, | 1978 EmitOOLTrapIfNeeded(zone(), this, opcode, instr->InputCount(), i, |
1981 __ pc_offset(), instr); | 1979 __ pc_offset()); |
1982 if (instr->HasOutput()) { | 1980 if (instr->HasOutput()) { |
1983 __ Movsd(i.OutputDoubleRegister(), i.MemoryOperand()); | 1981 __ Movsd(i.OutputDoubleRegister(), i.MemoryOperand()); |
1984 } else { | 1982 } else { |
1985 size_t index = 0; | 1983 size_t index = 0; |
1986 Operand operand = i.MemoryOperand(&index); | 1984 Operand operand = i.MemoryOperand(&index); |
1987 __ Movsd(operand, i.InputDoubleRegister(index)); | 1985 __ Movsd(operand, i.InputDoubleRegister(index)); |
1988 } | 1986 } |
1989 break; | 1987 break; |
1990 case kX64BitcastFI: | 1988 case kX64BitcastFI: |
1991 if (instr->InputAt(0)->IsFPStackSlot()) { | 1989 if (instr->InputAt(0)->IsFPStackSlot()) { |
(...skipping 868 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2860 int padding_size = last_lazy_deopt_pc_ + space_needed - current_pc; | 2858 int padding_size = last_lazy_deopt_pc_ + space_needed - current_pc; |
2861 __ Nop(padding_size); | 2859 __ Nop(padding_size); |
2862 } | 2860 } |
2863 } | 2861 } |
2864 | 2862 |
2865 #undef __ | 2863 #undef __ |
2866 | 2864 |
2867 } // namespace compiler | 2865 } // namespace compiler |
2868 } // namespace internal | 2866 } // namespace internal |
2869 } // namespace v8 | 2867 } // namespace v8 |
OLD | NEW |