Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 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 #ifndef V8_CCTEST_COMPILER_FUNCTION_TESTER_H_ | 5 #ifndef V8_CCTEST_COMPILER_FUNCTION_TESTER_H_ |
| 6 #define V8_CCTEST_COMPILER_FUNCTION_TESTER_H_ | 6 #define V8_CCTEST_COMPILER_FUNCTION_TESTER_H_ |
| 7 | 7 |
| 8 #include "src/v8.h" | 8 #include "src/v8.h" |
| 9 #include "test/cctest/cctest.h" | 9 #include "test/cctest/cctest.h" |
| 10 | 10 |
| 11 #include "src/compiler.h" | 11 #include "src/compiler.h" |
| 12 #include "src/compiler/linkage.h" | |
| 12 #include "src/compiler/pipeline.h" | 13 #include "src/compiler/pipeline.h" |
| 13 #include "src/execution.h" | 14 #include "src/execution.h" |
| 14 #include "src/full-codegen.h" | 15 #include "src/full-codegen.h" |
| 15 #include "src/handles.h" | 16 #include "src/handles.h" |
| 16 #include "src/objects-inl.h" | 17 #include "src/objects-inl.h" |
| 17 #include "src/parser.h" | 18 #include "src/parser.h" |
| 18 #include "src/rewriter.h" | 19 #include "src/rewriter.h" |
| 19 #include "src/scopes.h" | 20 #include "src/scopes.h" |
| 20 | 21 |
| 21 #define USE_CRANKSHAFT 0 | 22 #define USE_CRANKSHAFT 0 |
| 22 | 23 |
| 23 namespace v8 { | 24 namespace v8 { |
| 24 namespace internal { | 25 namespace internal { |
| 25 namespace compiler { | 26 namespace compiler { |
| 26 | 27 |
| 27 class FunctionTester : public InitializedHandleScope { | 28 class FunctionTester : public InitializedHandleScope { |
| 28 public: | 29 public: |
| 29 explicit FunctionTester(const char* source, uint32_t flags = 0) | 30 explicit FunctionTester(const char* source, uint32_t flags = 0) |
| 30 : isolate(main_isolate()), | 31 : isolate(main_isolate()), |
| 31 function((FLAG_allow_natives_syntax = true, NewFunction(source))), | 32 function((FLAG_allow_natives_syntax = true, NewFunction(source))), |
| 32 flags_(flags) { | 33 flags_(flags) { |
| 33 Compile(function); | 34 Compile(function); |
| 34 const uint32_t supported_flags = CompilationInfo::kContextSpecializing | | 35 const uint32_t supported_flags = CompilationInfo::kContextSpecializing | |
| 35 CompilationInfo::kInliningEnabled | | 36 CompilationInfo::kInliningEnabled | |
| 36 CompilationInfo::kTypingEnabled; | 37 CompilationInfo::kTypingEnabled; |
| 37 CHECK_EQ(0, flags_ & ~supported_flags); | 38 CHECK_EQ(0, flags_ & ~supported_flags); |
| 38 } | 39 } |
| 39 | 40 |
| 41 explicit FunctionTester(Graph* graph) | |
| 42 : isolate(main_isolate()), | |
| 43 function(NewFunction("(function(a,b){'use strict'; return 0;})")), | |
|
Michael Starzinger
2014/10/08 09:08:10
nit: Just use the empty function ... it looks conf
titzer
2014/10/08 09:22:54
Done.
| |
| 44 flags_(0) { | |
| 45 CompileGraph(graph); | |
| 46 } | |
| 47 | |
| 40 Isolate* isolate; | 48 Isolate* isolate; |
| 41 Handle<JSFunction> function; | 49 Handle<JSFunction> function; |
| 42 | 50 |
| 43 Handle<JSFunction> Compile(Handle<JSFunction> function) { | |
| 44 #if V8_TURBOFAN_TARGET | |
| 45 CompilationInfoWithZone info(function); | |
| 46 | |
| 47 CHECK(Parser::Parse(&info)); | |
| 48 info.SetOptimizing(BailoutId::None(), Handle<Code>(function->code())); | |
| 49 if (flags_ & CompilationInfo::kContextSpecializing) { | |
| 50 info.MarkAsContextSpecializing(); | |
| 51 } | |
| 52 if (flags_ & CompilationInfo::kInliningEnabled) { | |
| 53 info.MarkAsInliningEnabled(); | |
| 54 } | |
| 55 if (flags_ & CompilationInfo::kTypingEnabled) { | |
| 56 info.MarkAsTypingEnabled(); | |
| 57 } | |
| 58 CHECK(Rewriter::Rewrite(&info)); | |
| 59 CHECK(Scope::Analyze(&info)); | |
| 60 CHECK(Compiler::EnsureDeoptimizationSupport(&info)); | |
| 61 | |
| 62 Pipeline pipeline(&info); | |
| 63 Handle<Code> code = pipeline.GenerateCode(); | |
| 64 if (FLAG_turbo_deoptimization) { | |
| 65 info.context()->native_context()->AddOptimizedCode(*code); | |
| 66 } | |
| 67 | |
| 68 CHECK(!code.is_null()); | |
| 69 function->ReplaceCode(*code); | |
| 70 #elif USE_CRANKSHAFT | |
| 71 Handle<Code> unoptimized = Handle<Code>(function->code()); | |
| 72 Handle<Code> code = Compiler::GetOptimizedCode(function, unoptimized, | |
| 73 Compiler::NOT_CONCURRENT); | |
| 74 CHECK(!code.is_null()); | |
| 75 #if ENABLE_DISASSEMBLER | |
| 76 if (FLAG_print_opt_code) { | |
| 77 CodeTracer::Scope tracing_scope(isolate->GetCodeTracer()); | |
| 78 code->Disassemble("test code", tracing_scope.file()); | |
| 79 } | |
| 80 #endif | |
| 81 function->ReplaceCode(*code); | |
| 82 #endif | |
| 83 return function; | |
| 84 } | |
| 85 | |
| 86 MaybeHandle<Object> Call(Handle<Object> a, Handle<Object> b) { | 51 MaybeHandle<Object> Call(Handle<Object> a, Handle<Object> b) { |
| 87 Handle<Object> args[] = {a, b}; | 52 Handle<Object> args[] = {a, b}; |
| 88 return Execution::Call(isolate, function, undefined(), 2, args, false); | 53 return Execution::Call(isolate, function, undefined(), 2, args, false); |
| 89 } | 54 } |
| 90 | 55 |
| 91 void CheckThrows(Handle<Object> a, Handle<Object> b) { | 56 void CheckThrows(Handle<Object> a, Handle<Object> b) { |
| 92 TryCatch try_catch; | 57 TryCatch try_catch; |
| 93 MaybeHandle<Object> no_result = Call(a, b); | 58 MaybeHandle<Object> no_result = Call(a, b); |
| 94 CHECK(isolate->has_pending_exception()); | 59 CHECK(isolate->has_pending_exception()); |
| 95 CHECK(try_catch.HasCaught()); | 60 CHECK(try_catch.HasCaught()); |
| (...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 176 Handle<Object> nan() { return isolate->factory()->nan_value(); } | 141 Handle<Object> nan() { return isolate->factory()->nan_value(); } |
| 177 | 142 |
| 178 Handle<Object> undefined() { return isolate->factory()->undefined_value(); } | 143 Handle<Object> undefined() { return isolate->factory()->undefined_value(); } |
| 179 | 144 |
| 180 Handle<Object> null() { return isolate->factory()->null_value(); } | 145 Handle<Object> null() { return isolate->factory()->null_value(); } |
| 181 | 146 |
| 182 Handle<Object> true_value() { return isolate->factory()->true_value(); } | 147 Handle<Object> true_value() { return isolate->factory()->true_value(); } |
| 183 | 148 |
| 184 Handle<Object> false_value() { return isolate->factory()->false_value(); } | 149 Handle<Object> false_value() { return isolate->factory()->false_value(); } |
| 185 | 150 |
| 151 Handle<JSFunction> Compile(Handle<JSFunction> function) { | |
| 152 // foo me | |
|
Michael Starzinger
2014/10/08 09:08:10
nit: Hmm, it looks foo'ed already. :)
titzer
2014/10/08 09:22:55
Done.
| |
| 153 #if V8_TURBOFAN_TARGET | |
| 154 CompilationInfoWithZone info(function); | |
| 155 | |
| 156 CHECK(Parser::Parse(&info)); | |
| 157 info.SetOptimizing(BailoutId::None(), Handle<Code>(function->code())); | |
| 158 if (flags_ & CompilationInfo::kContextSpecializing) { | |
| 159 info.MarkAsContextSpecializing(); | |
| 160 } | |
| 161 if (flags_ & CompilationInfo::kInliningEnabled) { | |
| 162 info.MarkAsInliningEnabled(); | |
| 163 } | |
| 164 if (flags_ & CompilationInfo::kTypingEnabled) { | |
| 165 info.MarkAsTypingEnabled(); | |
| 166 } | |
| 167 CHECK(Rewriter::Rewrite(&info)); | |
| 168 CHECK(Scope::Analyze(&info)); | |
| 169 CHECK(Compiler::EnsureDeoptimizationSupport(&info)); | |
| 170 | |
| 171 Pipeline pipeline(&info); | |
| 172 Handle<Code> code = pipeline.GenerateCode(); | |
| 173 if (FLAG_turbo_deoptimization) { | |
| 174 info.context()->native_context()->AddOptimizedCode(*code); | |
| 175 } | |
| 176 | |
| 177 CHECK(!code.is_null()); | |
| 178 function->ReplaceCode(*code); | |
| 179 #elif USE_CRANKSHAFT | |
| 180 Handle<Code> unoptimized = Handle<Code>(function->code()); | |
| 181 Handle<Code> code = Compiler::GetOptimizedCode(function, unoptimized, | |
| 182 Compiler::NOT_CONCURRENT); | |
| 183 CHECK(!code.is_null()); | |
| 184 #if ENABLE_DISASSEMBLER | |
| 185 if (FLAG_print_opt_code) { | |
| 186 CodeTracer::Scope tracing_scope(isolate->GetCodeTracer()); | |
| 187 code->Disassemble("test code", tracing_scope.file()); | |
| 188 } | |
| 189 #endif | |
| 190 function->ReplaceCode(*code); | |
| 191 #endif | |
| 192 return function; | |
| 193 } | |
| 194 | |
| 195 static Handle<JSFunction> ForMachineGraph(Graph* graph) { | |
| 196 JSFunction* p = NULL; | |
| 197 { // because of the implicit handle scope of FunctionTester. | |
| 198 FunctionTester f(graph); | |
| 199 p = *f.function; | |
| 200 } | |
| 201 return Handle<JSFunction>(p); // allocated in outer handle scope. | |
| 202 } | |
| 203 | |
| 186 private: | 204 private: |
| 187 uint32_t flags_; | 205 uint32_t flags_; |
| 206 | |
| 207 // Compile the given machine graph instead of the source of the function | |
| 208 // and replace the JSFunction's code with the result. | |
| 209 Handle<JSFunction> CompileGraph(Graph* graph) { | |
| 210 CHECK(Pipeline::SupportedTarget()); | |
| 211 CompilationInfoWithZone info(function); | |
| 212 | |
| 213 CHECK(Parser::Parse(&info)); | |
| 214 info.SetOptimizing(BailoutId::None(), | |
| 215 Handle<Code>(function->shared()->code())); | |
| 216 CHECK(Rewriter::Rewrite(&info)); | |
| 217 CHECK(Scope::Analyze(&info)); | |
| 218 CHECK(Compiler::EnsureDeoptimizationSupport(&info)); | |
| 219 | |
| 220 Pipeline pipeline(&info); | |
| 221 Linkage linkage(&info); | |
| 222 Handle<Code> code = pipeline.GenerateCodeForMachineGraph(&linkage, graph); | |
| 223 CHECK(!code.is_null()); | |
| 224 function->ReplaceCode(*code); | |
| 225 return function; | |
| 226 } | |
| 188 }; | 227 }; |
| 189 } | 228 } |
| 190 } | 229 } |
| 191 } // namespace v8::internal::compiler | 230 } // namespace v8::internal::compiler |
| 192 | 231 |
| 193 #endif // V8_CCTEST_COMPILER_FUNCTION_TESTER_H_ | 232 #endif // V8_CCTEST_COMPILER_FUNCTION_TESTER_H_ |
| OLD | NEW |