OLD | NEW |
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #include "vm/isolate.h" | 5 #include "vm/isolate.h" |
6 | 6 |
7 #include "include/dart_api.h" | 7 #include "include/dart_api.h" |
8 #include "platform/assert.h" | 8 #include "platform/assert.h" |
9 #include "platform/json.h" | 9 #include "platform/json.h" |
10 #include "vm/code_observers.h" | 10 #include "vm/code_observers.h" |
(...skipping 26 matching lines...) Expand all Loading... |
37 #include "vm/tags.h" | 37 #include "vm/tags.h" |
38 #include "vm/thread_interrupter.h" | 38 #include "vm/thread_interrupter.h" |
39 #include "vm/thread_registry.h" | 39 #include "vm/thread_registry.h" |
40 #include "vm/timeline.h" | 40 #include "vm/timeline.h" |
41 #include "vm/timer.h" | 41 #include "vm/timer.h" |
42 #include "vm/visitor.h" | 42 #include "vm/visitor.h" |
43 | 43 |
44 | 44 |
45 namespace dart { | 45 namespace dart { |
46 | 46 |
| 47 DECLARE_FLAG(charp, timeline_trace_dir); |
| 48 |
47 DEFINE_FLAG(bool, trace_isolates, false, | 49 DEFINE_FLAG(bool, trace_isolates, false, |
48 "Trace isolate creation and shut down."); | 50 "Trace isolate creation and shut down."); |
49 DEFINE_FLAG(bool, pause_isolates_on_start, false, | 51 DEFINE_FLAG(bool, pause_isolates_on_start, false, |
50 "Pause isolates before starting."); | 52 "Pause isolates before starting."); |
51 DEFINE_FLAG(bool, pause_isolates_on_exit, false, | 53 DEFINE_FLAG(bool, pause_isolates_on_exit, false, |
52 "Pause isolates exiting."); | 54 "Pause isolates exiting."); |
53 DEFINE_FLAG(bool, break_at_isolate_spawn, false, | 55 DEFINE_FLAG(bool, break_at_isolate_spawn, false, |
54 "Insert a one-time breakpoint at the entrypoint for all spawned " | 56 "Insert a one-time breakpoint at the entrypoint for all spawned " |
55 "isolates"); | 57 "isolates"); |
56 DEFINE_FLAG(charp, isolate_log_filter, NULL, | 58 DEFINE_FLAG(charp, isolate_log_filter, NULL, |
57 "Log isolates whose name include the filter. " | 59 "Log isolates whose name include the filter. " |
58 "Default: service isolate log messages are suppressed."); | 60 "Default: service isolate log messages are suppressed."); |
59 | 61 |
60 DEFINE_FLAG(charp, timeline_trace_dir, NULL, | |
61 "Enable all timeline trace streams and output traces " | |
62 "into specified directory."); | |
63 DEFINE_FLAG(int, new_gen_semi_max_size, (kWordSize <= 4) ? 16 : 32, | 62 DEFINE_FLAG(int, new_gen_semi_max_size, (kWordSize <= 4) ? 16 : 32, |
64 "Max size of new gen semi space in MB"); | 63 "Max size of new gen semi space in MB"); |
65 DEFINE_FLAG(int, old_gen_heap_size, 0, | 64 DEFINE_FLAG(int, old_gen_heap_size, 0, |
66 "Max size of old gen heap size in MB, or 0 for unlimited," | 65 "Max size of old gen heap size in MB, or 0 for unlimited," |
67 "e.g: --old_gen_heap_size=1024 allows up to 1024MB old gen heap"); | 66 "e.g: --old_gen_heap_size=1024 allows up to 1024MB old gen heap"); |
68 DEFINE_FLAG(int, external_max_size, (kWordSize <= 4) ? 512 : 1024, | 67 DEFINE_FLAG(int, external_max_size, (kWordSize <= 4) ? 512 : 1024, |
69 "Max total size of external allocations in MB, or 0 for unlimited," | 68 "Max total size of external allocations in MB, or 0 for unlimited," |
70 "e.g: --external_max_size=1024 allows up to 1024MB of externals"); | 69 "e.g: --external_max_size=1024 allows up to 1024MB of externals"); |
71 | 70 |
72 // TODO(iposva): Make these isolate specific flags inaccessible using the | 71 // TODO(iposva): Make these isolate specific flags inaccessible using the |
(...skipping 304 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
377 // Allow the embedder to handle message notification. | 376 // Allow the embedder to handle message notification. |
378 (*callback)(Api::CastIsolate(I)); | 377 (*callback)(Api::CastIsolate(I)); |
379 } | 378 } |
380 } | 379 } |
381 | 380 |
382 | 381 |
383 bool IsolateMessageHandler::HandleMessage(Message* message) { | 382 bool IsolateMessageHandler::HandleMessage(Message* message) { |
384 StackZone zone(I); | 383 StackZone zone(I); |
385 HandleScope handle_scope(I); | 384 HandleScope handle_scope(I); |
386 TimelineDurationScope tds(I, I->GetIsolateStream(), "HandleMessage"); | 385 TimelineDurationScope tds(I, I->GetIsolateStream(), "HandleMessage"); |
| 386 tds.SetNumArguments(1); |
| 387 tds.CopyArgument(0, "isolateName", I->name()); |
387 | 388 |
388 // TODO(turnidge): Rework collection total dart execution. This can | 389 // TODO(turnidge): Rework collection total dart execution. This can |
389 // overcount when other things (gc, compilation) are active. | 390 // overcount when other things (gc, compilation) are active. |
390 TIMERSCOPE(isolate_, time_dart_execution); | 391 TIMERSCOPE(isolate_, time_dart_execution); |
391 | 392 |
392 // If the message is in band we lookup the handler to dispatch to. If the | 393 // If the message is in band we lookup the handler to dispatch to. If the |
393 // receive port was closed, we drop the message without deserializing it. | 394 // receive port was closed, we drop the message without deserializing it. |
394 // Illegal port is a special case for artificially enqueued isolate library | 395 // Illegal port is a special case for artificially enqueued isolate library |
395 // messages which are handled in C++ code below. | 396 // messages which are handled in C++ code below. |
396 Object& msg_handler = Object::Handle(I); | 397 Object& msg_handler = Object::Handle(I); |
(...skipping 282 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
679 edge_counter_increment_size_(-1), | 680 edge_counter_increment_size_(-1), |
680 compiler_stats_(NULL), | 681 compiler_stats_(NULL), |
681 is_service_isolate_(false), | 682 is_service_isolate_(false), |
682 log_(new class Log()), | 683 log_(new class Log()), |
683 stacktrace_(NULL), | 684 stacktrace_(NULL), |
684 stack_frame_index_(-1), | 685 stack_frame_index_(-1), |
685 last_allocationprofile_accumulator_reset_timestamp_(0), | 686 last_allocationprofile_accumulator_reset_timestamp_(0), |
686 last_allocationprofile_gc_timestamp_(0), | 687 last_allocationprofile_gc_timestamp_(0), |
687 object_id_ring_(NULL), | 688 object_id_ring_(NULL), |
688 trace_buffer_(NULL), | 689 trace_buffer_(NULL), |
689 timeline_event_recorder_(NULL), | |
690 profiler_data_(NULL), | 690 profiler_data_(NULL), |
691 tag_table_(GrowableObjectArray::null()), | 691 tag_table_(GrowableObjectArray::null()), |
692 current_tag_(UserTag::null()), | 692 current_tag_(UserTag::null()), |
693 default_tag_(UserTag::null()), | 693 default_tag_(UserTag::null()), |
694 collected_closures_(GrowableObjectArray::null()), | 694 collected_closures_(GrowableObjectArray::null()), |
695 deoptimized_code_array_(GrowableObjectArray::null()), | 695 deoptimized_code_array_(GrowableObjectArray::null()), |
696 metrics_list_head_(NULL), | 696 metrics_list_head_(NULL), |
697 compilation_allowed_(true), | 697 compilation_allowed_(true), |
698 cha_(NULL), | 698 cha_(NULL), |
699 next_(NULL), | 699 next_(NULL), |
(...skipping 29 matching lines...) Expand all Loading... |
729 delete log_; | 729 delete log_; |
730 log_ = NULL; | 730 log_ = NULL; |
731 delete object_id_ring_; | 731 delete object_id_ring_; |
732 object_id_ring_ = NULL; | 732 object_id_ring_ = NULL; |
733 delete pause_loop_monitor_; | 733 delete pause_loop_monitor_; |
734 pause_loop_monitor_ = NULL; | 734 pause_loop_monitor_ = NULL; |
735 if (compiler_stats_ != NULL) { | 735 if (compiler_stats_ != NULL) { |
736 delete compiler_stats_; | 736 delete compiler_stats_; |
737 compiler_stats_ = NULL; | 737 compiler_stats_ = NULL; |
738 } | 738 } |
739 RemoveTimelineEventRecorder(); | |
740 delete thread_registry_; | 739 delete thread_registry_; |
741 } | 740 } |
742 | 741 |
743 | 742 |
744 #if defined(DEBUG) | 743 #if defined(DEBUG) |
745 bool Isolate::IsIsolateOf(Thread* thread) { | 744 bool Isolate::IsIsolateOf(Thread* thread) { |
746 return this == thread->isolate(); | 745 return this == thread->isolate(); |
747 } | 746 } |
748 #endif // DEBUG | 747 #endif // DEBUG |
749 | 748 |
(...skipping 10 matching lines...) Expand all Loading... |
760 bool is_vm_isolate) { | 759 bool is_vm_isolate) { |
761 Isolate* result = new Isolate(api_flags); | 760 Isolate* result = new Isolate(api_flags); |
762 ASSERT(result != NULL); | 761 ASSERT(result != NULL); |
763 | 762 |
764 // Initialize metrics. | 763 // Initialize metrics. |
765 #define ISOLATE_METRIC_INIT(type, variable, name, unit) \ | 764 #define ISOLATE_METRIC_INIT(type, variable, name, unit) \ |
766 result->metric_##variable##_.Init(result, name, NULL, Metric::unit); | 765 result->metric_##variable##_.Init(result, name, NULL, Metric::unit); |
767 ISOLATE_METRIC_LIST(ISOLATE_METRIC_INIT); | 766 ISOLATE_METRIC_LIST(ISOLATE_METRIC_INIT); |
768 #undef ISOLATE_METRIC_INIT | 767 #undef ISOLATE_METRIC_INIT |
769 | 768 |
770 const bool force_streams = FLAG_timeline_trace_dir != NULL; | |
771 | |
772 // Initialize Timeline streams. | 769 // Initialize Timeline streams. |
773 #define ISOLATE_TIMELINE_STREAM_INIT(name, enabled_by_default) \ | 770 #define ISOLATE_TIMELINE_STREAM_INIT(name, enabled_by_default) \ |
774 result->stream_##name##_.Init(#name, force_streams || enabled_by_default); | 771 result->stream_##name##_.Init(#name, \ |
| 772 Timeline::EnableStreamByDefault(#name) || \ |
| 773 enabled_by_default); |
775 ISOLATE_TIMELINE_STREAM_LIST(ISOLATE_TIMELINE_STREAM_INIT); | 774 ISOLATE_TIMELINE_STREAM_LIST(ISOLATE_TIMELINE_STREAM_INIT); |
776 #undef ISOLATE_TIMELINE_STREAM_INIT | 775 #undef ISOLATE_TIMELINE_STREAM_INIT |
777 | 776 |
778 Heap::Init(result, | 777 Heap::Init(result, |
779 is_vm_isolate | 778 is_vm_isolate |
780 ? 0 // New gen size 0; VM isolate should only allocate in old. | 779 ? 0 // New gen size 0; VM isolate should only allocate in old. |
781 : FLAG_new_gen_semi_max_size * MBInWords, | 780 : FLAG_new_gen_semi_max_size * MBInWords, |
782 FLAG_old_gen_heap_size * MBInWords, | 781 FLAG_old_gen_heap_size * MBInWords, |
783 FLAG_external_max_size * MBInWords); | 782 FLAG_external_max_size * MBInWords); |
784 | 783 |
(...skipping 684 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1469 #endif // DEBUG | 1468 #endif // DEBUG |
1470 | 1469 |
1471 // First, perform higher-level cleanup that may need to allocate. | 1470 // First, perform higher-level cleanup that may need to allocate. |
1472 { | 1471 { |
1473 // Ensure we have a zone and handle scope so that we can call VM functions. | 1472 // Ensure we have a zone and handle scope so that we can call VM functions. |
1474 StackZone stack_zone(this); | 1473 StackZone stack_zone(this); |
1475 HandleScope handle_scope(this); | 1474 HandleScope handle_scope(this); |
1476 | 1475 |
1477 // Write out the coverage data if collection has been enabled. | 1476 // Write out the coverage data if collection has been enabled. |
1478 CodeCoverage::Write(this); | 1477 CodeCoverage::Write(this); |
1479 | |
1480 if ((timeline_event_recorder_ != NULL) && | |
1481 (FLAG_timeline_trace_dir != NULL)) { | |
1482 timeline_event_recorder_->WriteTo(FLAG_timeline_trace_dir); | |
1483 } | |
1484 } | 1478 } |
1485 | 1479 |
1486 // Remove this isolate from the list *before* we start tearing it down, to | 1480 // Remove this isolate from the list *before* we start tearing it down, to |
1487 // avoid exposing it in a state of decay. | 1481 // avoid exposing it in a state of decay. |
1488 RemoveIsolateFromList(this); | 1482 RemoveIsolateFromList(this); |
1489 | 1483 |
1490 if (heap_ != NULL) { | 1484 if (heap_ != NULL) { |
1491 // Wait for any concurrent GC tasks to finish before shutting down. | 1485 // Wait for any concurrent GC tasks to finish before shutting down. |
1492 // TODO(koda): Support faster sweeper shutdown (e.g., after current page). | 1486 // TODO(koda): Support faster sweeper shutdown (e.g., after current page). |
1493 PageSpace* old_space = heap_->old_space(); | 1487 PageSpace* old_space = heap_->old_space(); |
(...skipping 150 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1644 } | 1638 } |
1645 | 1639 |
1646 | 1640 |
1647 void Isolate::VisitPrologueWeakPersistentHandles(HandleVisitor* visitor) { | 1641 void Isolate::VisitPrologueWeakPersistentHandles(HandleVisitor* visitor) { |
1648 if (api_state() != NULL) { | 1642 if (api_state() != NULL) { |
1649 api_state()->VisitPrologueWeakHandles(visitor); | 1643 api_state()->VisitPrologueWeakHandles(visitor); |
1650 } | 1644 } |
1651 } | 1645 } |
1652 | 1646 |
1653 | 1647 |
1654 void Isolate::SetTimelineEventRecorder( | |
1655 TimelineEventRecorder* timeline_event_recorder) { | |
1656 #define ISOLATE_TIMELINE_STREAM_SET_BUFFER(name, enabled_by_default) \ | |
1657 stream_##name##_.set_recorder(timeline_event_recorder); | |
1658 ISOLATE_TIMELINE_STREAM_LIST(ISOLATE_TIMELINE_STREAM_SET_BUFFER) | |
1659 #undef ISOLATE_TIMELINE_STREAM_SET_BUFFER | |
1660 timeline_event_recorder_ = timeline_event_recorder; | |
1661 } | |
1662 | |
1663 void Isolate::RemoveTimelineEventRecorder() { | |
1664 SetTimelineEventRecorder(NULL); | |
1665 delete timeline_event_recorder_; | |
1666 } | |
1667 | |
1668 | |
1669 void Isolate::PrintJSON(JSONStream* stream, bool ref) { | 1648 void Isolate::PrintJSON(JSONStream* stream, bool ref) { |
1670 JSONObject jsobj(stream); | 1649 JSONObject jsobj(stream); |
1671 jsobj.AddProperty("type", (ref ? "@Isolate" : "Isolate")); | 1650 jsobj.AddProperty("type", (ref ? "@Isolate" : "Isolate")); |
1672 jsobj.AddFixedServiceId("isolates/%" Pd "", | 1651 jsobj.AddFixedServiceId("isolates/%" Pd "", |
1673 static_cast<intptr_t>(main_port())); | 1652 static_cast<intptr_t>(main_port())); |
1674 | 1653 |
1675 jsobj.AddProperty("name", debugger_name()); | 1654 jsobj.AddProperty("name", debugger_name()); |
1676 jsobj.AddPropertyF("number", "%" Pd "", | 1655 jsobj.AddPropertyF("number", "%" Pd "", |
1677 static_cast<intptr_t>(main_port())); | 1656 static_cast<intptr_t>(main_port())); |
1678 if (ref) { | 1657 if (ref) { |
(...skipping 485 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2164 serialized_message_, serialized_message_len_); | 2143 serialized_message_, serialized_message_len_); |
2165 } | 2144 } |
2166 | 2145 |
2167 | 2146 |
2168 void IsolateSpawnState::Cleanup() { | 2147 void IsolateSpawnState::Cleanup() { |
2169 SwitchIsolateScope switch_scope(I); | 2148 SwitchIsolateScope switch_scope(I); |
2170 Dart::ShutdownIsolate(); | 2149 Dart::ShutdownIsolate(); |
2171 } | 2150 } |
2172 | 2151 |
2173 } // namespace dart | 2152 } // namespace dart |
OLD | NEW |