Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2015 the V8 project authors. All rights reserved. | 1 // Copyright 2015 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/interpreter/interpreter.h" | 5 #include "src/interpreter/interpreter.h" |
| 6 | 6 |
| 7 #include "src/ast/prettyprinter.h" | 7 #include "src/ast/prettyprinter.h" |
| 8 #include "src/code-factory.h" | 8 #include "src/code-factory.h" |
| 9 #include "src/compiler.h" | 9 #include "src/compiler.h" |
| 10 #include "src/compiler/interpreter-assembler.h" | 10 #include "src/compiler/interpreter-assembler.h" |
| 11 #include "src/factory.h" | 11 #include "src/factory.h" |
| 12 #include "src/interpreter/bytecode-generator.h" | 12 #include "src/interpreter/bytecode-generator.h" |
| 13 #include "src/interpreter/bytecodes.h" | 13 #include "src/interpreter/bytecodes.h" |
| 14 #include "src/zone.h" | 14 #include "src/zone.h" |
| 15 | 15 |
| 16 namespace v8 { | 16 namespace v8 { |
| 17 namespace internal { | 17 namespace internal { |
| 18 namespace interpreter { | 18 namespace interpreter { |
| 19 | 19 |
| 20 using compiler::Node; | 20 using compiler::Node; |
| 21 | 21 |
| 22 #define __ assembler-> | 22 #define __ assembler-> |
| 23 | 23 |
| 24 | 24 Interpreter::Interpreter(Isolate* isolate) : isolate_(isolate) { |
| 25 Interpreter::Interpreter(Isolate* isolate) | 25 for (int i = 0; i < kDispatchTableSize; i++) dispatch_table_[i] = nullptr; |
|
Michael Starzinger
2016/02/05 11:42:16
nit: memset(&dispatch_table_, 0, sizeof(dispatch_t
Yang
2016/02/05 11:51:01
Done.
| |
| 26 : isolate_(isolate) {} | |
| 27 | |
| 28 | |
| 29 // static | |
| 30 Handle<FixedArray> Interpreter::CreateUninitializedInterpreterTable( | |
| 31 Isolate* isolate) { | |
| 32 Handle<FixedArray> handler_table = isolate->factory()->NewFixedArray( | |
| 33 static_cast<int>(Bytecode::kLast) + 1, TENURED); | |
| 34 // We rely on the interpreter handler table being immovable, so check that | |
| 35 // it was allocated on the first page (which is always immovable). | |
| 36 DCHECK(isolate->heap()->old_space()->FirstPage()->Contains( | |
| 37 handler_table->address())); | |
| 38 return handler_table; | |
| 39 } | 26 } |
| 40 | 27 |
| 41 | 28 |
| 42 void Interpreter::Initialize() { | 29 void Interpreter::Initialize() { |
| 43 DCHECK(FLAG_ignition); | 30 DCHECK(FLAG_ignition); |
| 44 Handle<FixedArray> handler_table = isolate_->factory()->interpreter_table(); | 31 if (IsDispatchTableInitialized()) return; |
| 45 if (!IsInterpreterTableInitialized(handler_table)) { | 32 Zone zone; |
| 46 Zone zone; | 33 HandleScope scope(isolate_); |
| 47 HandleScope scope(isolate_); | |
| 48 | 34 |
| 49 #define GENERATE_CODE(Name, ...) \ | 35 #define GENERATE_CODE(Name, ...) \ |
| 50 { \ | 36 { \ |
| 51 compiler::InterpreterAssembler assembler(isolate_, &zone, \ | 37 compiler::InterpreterAssembler assembler(isolate_, &zone, \ |
| 52 Bytecode::k##Name); \ | 38 Bytecode::k##Name); \ |
| 53 Do##Name(&assembler); \ | 39 Do##Name(&assembler); \ |
| 54 Handle<Code> code = assembler.GenerateCode(); \ | 40 Handle<Code> code = assembler.GenerateCode(); \ |
| 55 handler_table->set(static_cast<int>(Bytecode::k##Name), *code); \ | 41 int index = static_cast<int>(Bytecode::k##Name); \ |
| 56 } | 42 dispatch_table_[index] = *code; \ |
| 57 BYTECODE_LIST(GENERATE_CODE) | 43 } |
| 44 BYTECODE_LIST(GENERATE_CODE) | |
| 58 #undef GENERATE_CODE | 45 #undef GENERATE_CODE |
| 59 } | 46 } |
| 47 | |
| 48 void Interpreter::IterateDispatchTable(ObjectVisitor* v) { | |
| 49 v->VisitPointers(&dispatch_table_[0], | |
| 50 &dispatch_table_[0] + kDispatchTableSize); | |
| 60 } | 51 } |
| 61 | 52 |
| 62 | 53 |
| 63 bool Interpreter::MakeBytecode(CompilationInfo* info) { | 54 bool Interpreter::MakeBytecode(CompilationInfo* info) { |
| 64 if (FLAG_print_bytecode || FLAG_print_source || FLAG_print_ast) { | 55 if (FLAG_print_bytecode || FLAG_print_source || FLAG_print_ast) { |
| 65 OFStream os(stdout); | 56 OFStream os(stdout); |
| 66 base::SmartArrayPointer<char> name = info->GetDebugName(); | 57 base::SmartArrayPointer<char> name = info->GetDebugName(); |
| 67 os << "[generating bytecode for function: " << info->GetDebugName().get() | 58 os << "[generating bytecode for function: " << info->GetDebugName().get() |
| 68 << "]" << std::endl | 59 << "]" << std::endl |
| 69 << std::flush; | 60 << std::flush; |
| (...skipping 23 matching lines...) Expand all Loading... | |
| 93 OFStream os(stdout); | 84 OFStream os(stdout); |
| 94 bytecodes->Print(os); | 85 bytecodes->Print(os); |
| 95 os << std::flush; | 86 os << std::flush; |
| 96 } | 87 } |
| 97 | 88 |
| 98 info->SetBytecodeArray(bytecodes); | 89 info->SetBytecodeArray(bytecodes); |
| 99 info->SetCode(info->isolate()->builtins()->InterpreterEntryTrampoline()); | 90 info->SetCode(info->isolate()->builtins()->InterpreterEntryTrampoline()); |
| 100 return true; | 91 return true; |
| 101 } | 92 } |
| 102 | 93 |
| 103 | 94 bool Interpreter::IsDispatchTableInitialized() { |
| 104 bool Interpreter::IsInterpreterTableInitialized( | |
| 105 Handle<FixedArray> handler_table) { | |
| 106 if (FLAG_trace_ignition) { | 95 if (FLAG_trace_ignition) { |
| 107 // Regenerate table to add bytecode tracing operations. | 96 // Regenerate table to add bytecode tracing operations. |
| 108 return false; | 97 return false; |
| 109 } | 98 } |
| 110 DCHECK(handler_table->length() == static_cast<int>(Bytecode::kLast) + 1); | 99 return dispatch_table_[0] != nullptr; |
| 111 return handler_table->get(0) != isolate_->heap()->undefined_value(); | |
| 112 } | 100 } |
| 113 | 101 |
| 114 // LdaZero | 102 // LdaZero |
| 115 // | 103 // |
| 116 // Load literal '0' into the accumulator. | 104 // Load literal '0' into the accumulator. |
| 117 void Interpreter::DoLdaZero(compiler::InterpreterAssembler* assembler) { | 105 void Interpreter::DoLdaZero(compiler::InterpreterAssembler* assembler) { |
| 118 Node* zero_value = __ NumberConstant(0.0); | 106 Node* zero_value = __ NumberConstant(0.0); |
| 119 __ SetAccumulator(zero_value); | 107 __ SetAccumulator(zero_value); |
| 120 __ Dispatch(); | 108 __ Dispatch(); |
| 121 } | 109 } |
| (...skipping 1806 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1928 Node* index_reg = __ BytecodeOperandReg(0); | 1916 Node* index_reg = __ BytecodeOperandReg(0); |
| 1929 Node* index = __ LoadRegister(index_reg); | 1917 Node* index = __ LoadRegister(index_reg); |
| 1930 Node* result = __ CallRuntime(Runtime::kForInStep, index); | 1918 Node* result = __ CallRuntime(Runtime::kForInStep, index); |
| 1931 __ SetAccumulator(result); | 1919 __ SetAccumulator(result); |
| 1932 __ Dispatch(); | 1920 __ Dispatch(); |
| 1933 } | 1921 } |
| 1934 | 1922 |
| 1935 } // namespace interpreter | 1923 } // namespace interpreter |
| 1936 } // namespace internal | 1924 } // namespace internal |
| 1937 } // namespace v8 | 1925 } // namespace v8 |
| OLD | NEW |