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 #include "src/compiler/pipeline.h" | 5 #include "src/compiler/pipeline.h" |
6 | 6 |
7 #include <sstream> | 7 #include <sstream> |
8 | 8 |
9 #include "src/base/platform/elapsed-timer.h" | 9 #include "src/base/platform/elapsed-timer.h" |
10 #include "src/compiler/ast-graph-builder.h" | 10 #include "src/compiler/ast-graph-builder.h" |
(...skipping 12 matching lines...) Expand all Loading... |
23 #include "src/compiler/machine-operator-reducer.h" | 23 #include "src/compiler/machine-operator-reducer.h" |
24 #include "src/compiler/phi-reducer.h" | 24 #include "src/compiler/phi-reducer.h" |
25 #include "src/compiler/register-allocator.h" | 25 #include "src/compiler/register-allocator.h" |
26 #include "src/compiler/schedule.h" | 26 #include "src/compiler/schedule.h" |
27 #include "src/compiler/scheduler.h" | 27 #include "src/compiler/scheduler.h" |
28 #include "src/compiler/simplified-lowering.h" | 28 #include "src/compiler/simplified-lowering.h" |
29 #include "src/compiler/simplified-operator-reducer.h" | 29 #include "src/compiler/simplified-operator-reducer.h" |
30 #include "src/compiler/typer.h" | 30 #include "src/compiler/typer.h" |
31 #include "src/compiler/value-numbering-reducer.h" | 31 #include "src/compiler/value-numbering-reducer.h" |
32 #include "src/compiler/verifier.h" | 32 #include "src/compiler/verifier.h" |
| 33 #include "src/compiler/zone-pool.h" |
33 #include "src/hydrogen.h" | 34 #include "src/hydrogen.h" |
34 #include "src/ostreams.h" | 35 #include "src/ostreams.h" |
35 #include "src/utils.h" | 36 #include "src/utils.h" |
36 | 37 |
37 namespace v8 { | 38 namespace v8 { |
38 namespace internal { | 39 namespace internal { |
39 namespace compiler { | 40 namespace compiler { |
40 | 41 |
41 class PhaseStats { | 42 class PhaseStats { |
42 public: | 43 public: |
43 enum PhaseKind { CREATE_GRAPH, OPTIMIZATION, CODEGEN }; | 44 enum PhaseKind { CREATE_GRAPH, OPTIMIZATION, CODEGEN }; |
44 | 45 |
45 PhaseStats(CompilationInfo* info, PhaseKind kind, const char* name) | 46 PhaseStats(CompilationInfo* info, ZonePool* zone_pool, PhaseKind kind, |
| 47 const char* name) |
46 : info_(info), | 48 : info_(info), |
| 49 stats_scope_(zone_pool), |
47 kind_(kind), | 50 kind_(kind), |
48 name_(name), | 51 name_(name), |
49 size_(info->zone()->allocation_size()) { | 52 size_(0) { |
50 if (FLAG_turbo_stats) { | 53 if (FLAG_turbo_stats) { |
51 timer_.Start(); | 54 timer_.Start(); |
| 55 size_ = info_->zone()->allocation_size(); |
52 } | 56 } |
53 } | 57 } |
54 | 58 |
55 ~PhaseStats() { | 59 ~PhaseStats() { |
56 if (FLAG_turbo_stats) { | 60 if (FLAG_turbo_stats) { |
57 base::TimeDelta delta = timer_.Elapsed(); | 61 base::TimeDelta delta = timer_.Elapsed(); |
58 size_t bytes = info_->zone()->allocation_size() - size_; | 62 size_t bytes = info_->zone()->allocation_size() + |
| 63 stats_scope_.GetMaxAllocatedBytes() - size_; |
59 HStatistics* stats = info_->isolate()->GetTStatistics(); | 64 HStatistics* stats = info_->isolate()->GetTStatistics(); |
60 stats->SaveTiming(name_, delta, static_cast<int>(bytes)); | 65 stats->SaveTiming(name_, delta, static_cast<int>(bytes)); |
61 | 66 |
62 switch (kind_) { | 67 switch (kind_) { |
63 case CREATE_GRAPH: | 68 case CREATE_GRAPH: |
64 stats->IncrementCreateGraph(delta); | 69 stats->IncrementCreateGraph(delta); |
65 break; | 70 break; |
66 case OPTIMIZATION: | 71 case OPTIMIZATION: |
67 stats->IncrementOptimizeGraph(delta); | 72 stats->IncrementOptimizeGraph(delta); |
68 break; | 73 break; |
69 case CODEGEN: | 74 case CODEGEN: |
70 stats->IncrementGenerateCode(delta); | 75 stats->IncrementGenerateCode(delta); |
71 break; | 76 break; |
72 } | 77 } |
73 } | 78 } |
74 } | 79 } |
75 | 80 |
76 private: | 81 private: |
77 CompilationInfo* info_; | 82 CompilationInfo* info_; |
| 83 ZonePool::StatsScope stats_scope_; |
78 PhaseKind kind_; | 84 PhaseKind kind_; |
79 const char* name_; | 85 const char* name_; |
80 size_t size_; | 86 size_t size_; |
81 base::ElapsedTimer timer_; | 87 base::ElapsedTimer timer_; |
82 }; | 88 }; |
83 | 89 |
84 | 90 |
85 static inline bool VerifyGraphs() { | 91 static inline bool VerifyGraphs() { |
86 #ifdef DEBUG | 92 #ifdef DEBUG |
87 return true; | 93 return true; |
(...skipping 134 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
222 | 228 |
223 if (FLAG_trace_turbo) { | 229 if (FLAG_trace_turbo) { |
224 OFStream os(stdout); | 230 OFStream os(stdout); |
225 os << "---------------------------------------------------\n" | 231 os << "---------------------------------------------------\n" |
226 << "Begin compiling method " | 232 << "Begin compiling method " |
227 << info()->function()->debug_name()->ToCString().get() | 233 << info()->function()->debug_name()->ToCString().get() |
228 << " using Turbofan" << std::endl; | 234 << " using Turbofan" << std::endl; |
229 PrintCompilationStart(); | 235 PrintCompilationStart(); |
230 } | 236 } |
231 | 237 |
| 238 ZonePool zone_pool(isolate()); |
| 239 |
232 // Build the graph. | 240 // Build the graph. |
233 Graph graph(zone()); | 241 Graph graph(zone()); |
234 SourcePositionTable source_positions(&graph); | 242 SourcePositionTable source_positions(&graph); |
235 source_positions.AddDecorator(); | 243 source_positions.AddDecorator(); |
236 // TODO(turbofan): there is no need to type anything during initial graph | 244 // TODO(turbofan): there is no need to type anything during initial graph |
237 // construction. This is currently only needed for the node cache, which the | 245 // construction. This is currently only needed for the node cache, which the |
238 // typer could sweep over later. | 246 // typer could sweep over later. |
239 Typer typer(&graph, info()->context()); | 247 Typer typer(&graph, info()->context()); |
240 MachineOperatorBuilder machine; | 248 MachineOperatorBuilder machine; |
241 CommonOperatorBuilder common(zone()); | 249 CommonOperatorBuilder common(zone()); |
242 JSOperatorBuilder javascript(zone()); | 250 JSOperatorBuilder javascript(zone()); |
243 JSGraph jsgraph(&graph, &common, &javascript, &machine); | 251 JSGraph jsgraph(&graph, &common, &javascript, &machine); |
244 Node* context_node; | 252 Node* context_node; |
245 { | 253 { |
246 PhaseStats graph_builder_stats(info(), PhaseStats::CREATE_GRAPH, | 254 PhaseStats graph_builder_stats(info(), &zone_pool, PhaseStats::CREATE_GRAPH, |
247 "graph builder"); | 255 "graph builder"); |
248 AstGraphBuilderWithPositions graph_builder(info(), &jsgraph, | 256 AstGraphBuilderWithPositions graph_builder(info(), &jsgraph, |
249 &source_positions); | 257 &source_positions); |
250 graph_builder.CreateGraph(); | 258 graph_builder.CreateGraph(); |
251 context_node = graph_builder.GetFunctionContext(); | 259 context_node = graph_builder.GetFunctionContext(); |
252 } | 260 } |
253 { | 261 { |
254 PhaseStats phi_reducer_stats(info(), PhaseStats::CREATE_GRAPH, | 262 PhaseStats phi_reducer_stats(info(), &zone_pool, PhaseStats::CREATE_GRAPH, |
255 "phi reduction"); | 263 "phi reduction"); |
256 PhiReducer phi_reducer; | 264 PhiReducer phi_reducer; |
257 GraphReducer graph_reducer(&graph); | 265 GraphReducer graph_reducer(&graph); |
258 graph_reducer.AddReducer(&phi_reducer); | 266 graph_reducer.AddReducer(&phi_reducer); |
259 graph_reducer.ReduceGraph(); | 267 graph_reducer.ReduceGraph(); |
260 // TODO(mstarzinger): Running reducer once ought to be enough for everyone. | 268 // TODO(mstarzinger): Running reducer once ought to be enough for everyone. |
261 graph_reducer.ReduceGraph(); | 269 graph_reducer.ReduceGraph(); |
262 graph_reducer.ReduceGraph(); | 270 graph_reducer.ReduceGraph(); |
263 } | 271 } |
264 | 272 |
(...skipping 20 matching lines...) Expand all Loading... |
285 if (FLAG_print_turbo_replay) { | 293 if (FLAG_print_turbo_replay) { |
286 GraphReplayPrinter::PrintReplay(&graph); | 294 GraphReplayPrinter::PrintReplay(&graph); |
287 } | 295 } |
288 | 296 |
289 // Bailout here in case target architecture is not supported. | 297 // Bailout here in case target architecture is not supported. |
290 if (!SupportedTarget()) return Handle<Code>::null(); | 298 if (!SupportedTarget()) return Handle<Code>::null(); |
291 | 299 |
292 if (info()->is_typing_enabled()) { | 300 if (info()->is_typing_enabled()) { |
293 { | 301 { |
294 // Type the graph. | 302 // Type the graph. |
295 PhaseStats typer_stats(info(), PhaseStats::CREATE_GRAPH, "typer"); | 303 PhaseStats typer_stats(info(), &zone_pool, PhaseStats::CREATE_GRAPH, |
| 304 "typer"); |
296 typer.Run(); | 305 typer.Run(); |
297 VerifyAndPrintGraph(&graph, "Typed"); | 306 VerifyAndPrintGraph(&graph, "Typed"); |
298 } | 307 } |
299 { | 308 { |
300 // Lower JSOperators where we can determine types. | 309 // Lower JSOperators where we can determine types. |
301 PhaseStats lowering_stats(info(), PhaseStats::CREATE_GRAPH, | 310 PhaseStats lowering_stats(info(), &zone_pool, PhaseStats::CREATE_GRAPH, |
302 "typed lowering"); | 311 "typed lowering"); |
303 SourcePositionTable::Scope pos(&source_positions, | 312 SourcePositionTable::Scope pos(&source_positions, |
304 SourcePosition::Unknown()); | 313 SourcePosition::Unknown()); |
305 ValueNumberingReducer vn_reducer(zone()); | 314 ValueNumberingReducer vn_reducer(zone()); |
306 JSTypedLowering lowering(&jsgraph); | 315 JSTypedLowering lowering(&jsgraph); |
307 SimplifiedOperatorReducer simple_reducer(&jsgraph); | 316 SimplifiedOperatorReducer simple_reducer(&jsgraph); |
308 GraphReducer graph_reducer(&graph); | 317 GraphReducer graph_reducer(&graph); |
309 graph_reducer.AddReducer(&vn_reducer); | 318 graph_reducer.AddReducer(&vn_reducer); |
310 graph_reducer.AddReducer(&lowering); | 319 graph_reducer.AddReducer(&lowering); |
311 graph_reducer.AddReducer(&simple_reducer); | 320 graph_reducer.AddReducer(&simple_reducer); |
312 graph_reducer.ReduceGraph(); | 321 graph_reducer.ReduceGraph(); |
313 | 322 |
314 VerifyAndPrintGraph(&graph, "Lowered typed"); | 323 VerifyAndPrintGraph(&graph, "Lowered typed"); |
315 } | 324 } |
316 { | 325 { |
317 // Lower simplified operators and insert changes. | 326 // Lower simplified operators and insert changes. |
318 PhaseStats lowering_stats(info(), PhaseStats::CREATE_GRAPH, | 327 PhaseStats lowering_stats(info(), &zone_pool, PhaseStats::CREATE_GRAPH, |
319 "simplified lowering"); | 328 "simplified lowering"); |
320 SourcePositionTable::Scope pos(&source_positions, | 329 SourcePositionTable::Scope pos(&source_positions, |
321 SourcePosition::Unknown()); | 330 SourcePosition::Unknown()); |
322 SimplifiedLowering lowering(&jsgraph); | 331 SimplifiedLowering lowering(&jsgraph); |
323 lowering.LowerAllNodes(); | 332 lowering.LowerAllNodes(); |
324 ValueNumberingReducer vn_reducer(zone()); | 333 ValueNumberingReducer vn_reducer(zone()); |
325 SimplifiedOperatorReducer simple_reducer(&jsgraph); | 334 SimplifiedOperatorReducer simple_reducer(&jsgraph); |
326 GraphReducer graph_reducer(&graph); | 335 GraphReducer graph_reducer(&graph); |
327 graph_reducer.AddReducer(&vn_reducer); | 336 graph_reducer.AddReducer(&vn_reducer); |
328 graph_reducer.AddReducer(&simple_reducer); | 337 graph_reducer.AddReducer(&simple_reducer); |
329 graph_reducer.ReduceGraph(); | 338 graph_reducer.ReduceGraph(); |
330 | 339 |
331 VerifyAndPrintGraph(&graph, "Lowered simplified"); | 340 VerifyAndPrintGraph(&graph, "Lowered simplified"); |
332 } | 341 } |
333 { | 342 { |
334 // Lower changes that have been inserted before. | 343 // Lower changes that have been inserted before. |
335 PhaseStats lowering_stats(info(), PhaseStats::OPTIMIZATION, | 344 PhaseStats lowering_stats(info(), &zone_pool, PhaseStats::OPTIMIZATION, |
336 "change lowering"); | 345 "change lowering"); |
337 SourcePositionTable::Scope pos(&source_positions, | 346 SourcePositionTable::Scope pos(&source_positions, |
338 SourcePosition::Unknown()); | 347 SourcePosition::Unknown()); |
339 Linkage linkage(info()); | 348 Linkage linkage(info()); |
340 ValueNumberingReducer vn_reducer(zone()); | 349 ValueNumberingReducer vn_reducer(zone()); |
341 SimplifiedOperatorReducer simple_reducer(&jsgraph); | 350 SimplifiedOperatorReducer simple_reducer(&jsgraph); |
342 ChangeLowering lowering(&jsgraph, &linkage); | 351 ChangeLowering lowering(&jsgraph, &linkage); |
343 MachineOperatorReducer mach_reducer(&jsgraph); | 352 MachineOperatorReducer mach_reducer(&jsgraph); |
344 GraphReducer graph_reducer(&graph); | 353 GraphReducer graph_reducer(&graph); |
345 // TODO(titzer): Figure out if we should run all reducers at once here. | 354 // TODO(titzer): Figure out if we should run all reducers at once here. |
346 graph_reducer.AddReducer(&vn_reducer); | 355 graph_reducer.AddReducer(&vn_reducer); |
347 graph_reducer.AddReducer(&simple_reducer); | 356 graph_reducer.AddReducer(&simple_reducer); |
348 graph_reducer.AddReducer(&lowering); | 357 graph_reducer.AddReducer(&lowering); |
349 graph_reducer.AddReducer(&mach_reducer); | 358 graph_reducer.AddReducer(&mach_reducer); |
350 graph_reducer.ReduceGraph(); | 359 graph_reducer.ReduceGraph(); |
351 | 360 |
352 // TODO(jarin, rossberg): Remove UNTYPED once machine typing works. | 361 // TODO(jarin, rossberg): Remove UNTYPED once machine typing works. |
353 VerifyAndPrintGraph(&graph, "Lowered changes", true); | 362 VerifyAndPrintGraph(&graph, "Lowered changes", true); |
354 } | 363 } |
355 | 364 |
356 { | 365 { |
357 SourcePositionTable::Scope pos(&source_positions, | 366 SourcePositionTable::Scope pos(&source_positions, |
358 SourcePosition::Unknown()); | 367 SourcePosition::Unknown()); |
359 PhaseStats control_reducer_stats(info(), PhaseStats::CREATE_GRAPH, | 368 PhaseStats control_reducer_stats( |
360 "control reduction"); | 369 info(), &zone_pool, PhaseStats::CREATE_GRAPH, "control reduction"); |
361 ControlReducer::ReduceGraph(&jsgraph, &common); | 370 ControlReducer::ReduceGraph(&jsgraph, &common); |
362 | 371 |
363 VerifyAndPrintGraph(&graph, "Control reduced"); | 372 VerifyAndPrintGraph(&graph, "Control reduced"); |
364 } | 373 } |
365 } | 374 } |
366 | 375 |
367 { | 376 { |
368 // Lower any remaining generic JSOperators. | 377 // Lower any remaining generic JSOperators. |
369 PhaseStats lowering_stats(info(), PhaseStats::CREATE_GRAPH, | 378 PhaseStats lowering_stats(info(), &zone_pool, PhaseStats::CREATE_GRAPH, |
370 "generic lowering"); | 379 "generic lowering"); |
371 SourcePositionTable::Scope pos(&source_positions, | 380 SourcePositionTable::Scope pos(&source_positions, |
372 SourcePosition::Unknown()); | 381 SourcePosition::Unknown()); |
373 JSGenericLowering lowering(info(), &jsgraph); | 382 JSGenericLowering lowering(info(), &jsgraph); |
374 GraphReducer graph_reducer(&graph); | 383 GraphReducer graph_reducer(&graph); |
375 graph_reducer.AddReducer(&lowering); | 384 graph_reducer.AddReducer(&lowering); |
376 graph_reducer.ReduceGraph(); | 385 graph_reducer.ReduceGraph(); |
377 | 386 |
378 // TODO(jarin, rossberg): Remove UNTYPED once machine typing works. | 387 // TODO(jarin, rossberg): Remove UNTYPED once machine typing works. |
379 VerifyAndPrintGraph(&graph, "Lowered generic", true); | 388 VerifyAndPrintGraph(&graph, "Lowered generic", true); |
380 } | 389 } |
381 | 390 |
382 source_positions.RemoveDecorator(); | 391 source_positions.RemoveDecorator(); |
383 | 392 |
384 Handle<Code> code = Handle<Code>::null(); | 393 Handle<Code> code = Handle<Code>::null(); |
385 { | 394 { |
386 // Compute a schedule. | 395 // Compute a schedule. |
387 Schedule* schedule = ComputeSchedule(&graph); | 396 Schedule* schedule = ComputeSchedule(&zone_pool, &graph); |
388 // Generate optimized code. | 397 // Generate optimized code. |
389 PhaseStats codegen_stats(info(), PhaseStats::CODEGEN, "codegen"); | 398 PhaseStats codegen_stats(info(), &zone_pool, PhaseStats::CODEGEN, |
| 399 "codegen"); |
390 Linkage linkage(info()); | 400 Linkage linkage(info()); |
391 code = GenerateCode(&linkage, &graph, schedule, &source_positions); | 401 code = GenerateCode(&linkage, &graph, schedule, &source_positions); |
392 info()->SetCode(code); | 402 info()->SetCode(code); |
393 } | 403 } |
394 | 404 |
395 // Print optimized code. | 405 // Print optimized code. |
396 v8::internal::CodeGenerator::PrintCode(code, info()); | 406 v8::internal::CodeGenerator::PrintCode(code, info()); |
397 | 407 |
398 if (FLAG_trace_turbo) { | 408 if (FLAG_trace_turbo) { |
399 OFStream os(stdout); | 409 OFStream os(stdout); |
400 os << "--------------------------------------------------\n" | 410 os << "--------------------------------------------------\n" |
401 << "Finished compiling method " | 411 << "Finished compiling method " |
402 << info()->function()->debug_name()->ToCString().get() | 412 << info()->function()->debug_name()->ToCString().get() |
403 << " using Turbofan" << std::endl; | 413 << " using Turbofan" << std::endl; |
404 } | 414 } |
405 | 415 |
406 return code; | 416 return code; |
407 } | 417 } |
408 | 418 |
409 | 419 |
410 Schedule* Pipeline::ComputeSchedule(Graph* graph) { | 420 Schedule* Pipeline::ComputeSchedule(ZonePool* zone_pool, Graph* graph) { |
411 PhaseStats schedule_stats(info(), PhaseStats::CODEGEN, "scheduling"); | 421 PhaseStats schedule_stats(info(), zone_pool, PhaseStats::CODEGEN, |
412 Schedule* schedule = Scheduler::ComputeSchedule(graph); | 422 "scheduling"); |
| 423 Schedule* schedule = Scheduler::ComputeSchedule(zone_pool, graph); |
413 TraceSchedule(schedule); | 424 TraceSchedule(schedule); |
414 if (VerifyGraphs()) ScheduleVerifier::Run(schedule); | 425 if (VerifyGraphs()) ScheduleVerifier::Run(schedule); |
415 return schedule; | 426 return schedule; |
416 } | 427 } |
417 | 428 |
418 | 429 |
419 Handle<Code> Pipeline::GenerateCodeForMachineGraph(Linkage* linkage, | 430 Handle<Code> Pipeline::GenerateCodeForMachineGraph(Linkage* linkage, |
420 Graph* graph, | 431 Graph* graph, |
421 Schedule* schedule) { | 432 Schedule* schedule) { |
422 CHECK(SupportedBackend()); | 433 CHECK(SupportedBackend()); |
423 if (schedule == NULL) { | 434 if (schedule == NULL) { |
424 // TODO(rossberg): Should this really be untyped? | 435 // TODO(rossberg): Should this really be untyped? |
425 VerifyAndPrintGraph(graph, "Machine", true); | 436 VerifyAndPrintGraph(graph, "Machine", true); |
426 schedule = ComputeSchedule(graph); | 437 ZonePool zone_pool(isolate()); |
| 438 schedule = ComputeSchedule(&zone_pool, graph); |
427 } | 439 } |
428 TraceSchedule(schedule); | 440 TraceSchedule(schedule); |
429 | 441 |
430 SourcePositionTable source_positions(graph); | 442 SourcePositionTable source_positions(graph); |
431 Handle<Code> code = GenerateCode(linkage, graph, schedule, &source_positions); | 443 Handle<Code> code = GenerateCode(linkage, graph, schedule, &source_positions); |
432 #if ENABLE_DISASSEMBLER | 444 #if ENABLE_DISASSEMBLER |
433 if (!code.is_null() && FLAG_print_opt_code) { | 445 if (!code.is_null() && FLAG_print_opt_code) { |
434 CodeTracer::Scope tracing_scope(isolate()->GetCodeTracer()); | 446 CodeTracer::Scope tracing_scope(isolate()->GetCodeTracer()); |
435 OFStream os(tracing_scope.file()); | 447 OFStream os(tracing_scope.file()); |
436 code->Disassemble("test code", os); | 448 code->Disassemble("test code", os); |
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
514 } | 526 } |
515 | 527 |
516 | 528 |
517 void Pipeline::TearDown() { | 529 void Pipeline::TearDown() { |
518 InstructionOperand::TearDownCaches(); | 530 InstructionOperand::TearDownCaches(); |
519 } | 531 } |
520 | 532 |
521 } // namespace compiler | 533 } // namespace compiler |
522 } // namespace internal | 534 } // namespace internal |
523 } // namespace v8 | 535 } // namespace v8 |
OLD | NEW |