| 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/thread_interrupter.h" | 5 #include "vm/thread_interrupter.h" |
| 6 | 6 |
| 7 #include "vm/flags.h" | 7 #include "vm/flags.h" |
| 8 #include "vm/lockers.h" | 8 #include "vm/lockers.h" |
| 9 #include "vm/os.h" | 9 #include "vm/os.h" |
| 10 #include "vm/simulator.h" | 10 #include "vm/simulator.h" |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 52 bool ThreadInterrupter::initialized_ = false; | 52 bool ThreadInterrupter::initialized_ = false; |
| 53 bool ThreadInterrupter::shutdown_ = false; | 53 bool ThreadInterrupter::shutdown_ = false; |
| 54 bool ThreadInterrupter::thread_running_ = false; | 54 bool ThreadInterrupter::thread_running_ = false; |
| 55 bool ThreadInterrupter::woken_up_ = false; | 55 bool ThreadInterrupter::woken_up_ = false; |
| 56 ThreadJoinId ThreadInterrupter::interrupter_thread_id_ = | 56 ThreadJoinId ThreadInterrupter::interrupter_thread_id_ = |
| 57 OSThread::kInvalidThreadJoinId; | 57 OSThread::kInvalidThreadJoinId; |
| 58 Monitor* ThreadInterrupter::monitor_ = NULL; | 58 Monitor* ThreadInterrupter::monitor_ = NULL; |
| 59 intptr_t ThreadInterrupter::interrupt_period_ = 1000; | 59 intptr_t ThreadInterrupter::interrupt_period_ = 1000; |
| 60 intptr_t ThreadInterrupter::current_wait_time_ = Monitor::kNoTimeout; | 60 intptr_t ThreadInterrupter::current_wait_time_ = Monitor::kNoTimeout; |
| 61 | 61 |
| 62 | |
| 63 void ThreadInterrupter::InitOnce() { | 62 void ThreadInterrupter::InitOnce() { |
| 64 ASSERT(!initialized_); | 63 ASSERT(!initialized_); |
| 65 monitor_ = new Monitor(); | 64 monitor_ = new Monitor(); |
| 66 ASSERT(monitor_ != NULL); | 65 ASSERT(monitor_ != NULL); |
| 67 initialized_ = true; | 66 initialized_ = true; |
| 68 } | 67 } |
| 69 | 68 |
| 70 | |
| 71 void ThreadInterrupter::Startup() { | 69 void ThreadInterrupter::Startup() { |
| 72 ASSERT(initialized_); | 70 ASSERT(initialized_); |
| 73 if (IsDebuggerAttached()) { | 71 if (IsDebuggerAttached()) { |
| 74 MonitorLocker shutdown_ml(monitor_); | 72 MonitorLocker shutdown_ml(monitor_); |
| 75 shutdown_ = true; | 73 shutdown_ = true; |
| 76 if (FLAG_trace_thread_interrupter) { | 74 if (FLAG_trace_thread_interrupter) { |
| 77 OS::PrintErr( | 75 OS::PrintErr( |
| 78 "ThreadInterrupter disabled because a debugger is attached.\n"); | 76 "ThreadInterrupter disabled because a debugger is attached.\n"); |
| 79 } | 77 } |
| 80 return; | 78 return; |
| 81 } | 79 } |
| 82 if (FLAG_trace_thread_interrupter) { | 80 if (FLAG_trace_thread_interrupter) { |
| 83 OS::PrintErr("ThreadInterrupter starting up.\n"); | 81 OS::PrintErr("ThreadInterrupter starting up.\n"); |
| 84 } | 82 } |
| 85 ASSERT(interrupter_thread_id_ == OSThread::kInvalidThreadJoinId); | 83 ASSERT(interrupter_thread_id_ == OSThread::kInvalidThreadJoinId); |
| 86 { | 84 { |
| 87 MonitorLocker startup_ml(monitor_); | 85 MonitorLocker startup_ml(monitor_); |
| 88 OSThread::Start("ThreadInterrupter", ThreadMain, 0); | 86 OSThread::Start("ThreadInterrupter", ThreadMain, 0); |
| 89 while (!thread_running_) { | 87 while (!thread_running_) { |
| 90 startup_ml.Wait(); | 88 startup_ml.Wait(); |
| 91 } | 89 } |
| 92 } | 90 } |
| 93 ASSERT(interrupter_thread_id_ != OSThread::kInvalidThreadJoinId); | 91 ASSERT(interrupter_thread_id_ != OSThread::kInvalidThreadJoinId); |
| 94 if (FLAG_trace_thread_interrupter) { | 92 if (FLAG_trace_thread_interrupter) { |
| 95 OS::PrintErr("ThreadInterrupter running.\n"); | 93 OS::PrintErr("ThreadInterrupter running.\n"); |
| 96 } | 94 } |
| 97 } | 95 } |
| 98 | 96 |
| 99 | |
| 100 void ThreadInterrupter::Shutdown() { | 97 void ThreadInterrupter::Shutdown() { |
| 101 { | 98 { |
| 102 MonitorLocker shutdown_ml(monitor_); | 99 MonitorLocker shutdown_ml(monitor_); |
| 103 if (shutdown_) { | 100 if (shutdown_) { |
| 104 // Already shutdown. | 101 // Already shutdown. |
| 105 return; | 102 return; |
| 106 } | 103 } |
| 107 shutdown_ = true; | 104 shutdown_ = true; |
| 108 // Notify. | 105 // Notify. |
| 109 shutdown_ml.Notify(); | 106 shutdown_ml.Notify(); |
| 110 ASSERT(initialized_); | 107 ASSERT(initialized_); |
| 111 if (FLAG_trace_thread_interrupter) { | 108 if (FLAG_trace_thread_interrupter) { |
| 112 OS::PrintErr("ThreadInterrupter shutting down.\n"); | 109 OS::PrintErr("ThreadInterrupter shutting down.\n"); |
| 113 } | 110 } |
| 114 } | 111 } |
| 115 | 112 |
| 116 // Join the thread. | 113 // Join the thread. |
| 117 ASSERT(interrupter_thread_id_ != OSThread::kInvalidThreadJoinId); | 114 ASSERT(interrupter_thread_id_ != OSThread::kInvalidThreadJoinId); |
| 118 OSThread::Join(interrupter_thread_id_); | 115 OSThread::Join(interrupter_thread_id_); |
| 119 interrupter_thread_id_ = OSThread::kInvalidThreadJoinId; | 116 interrupter_thread_id_ = OSThread::kInvalidThreadJoinId; |
| 120 | 117 |
| 121 if (FLAG_trace_thread_interrupter) { | 118 if (FLAG_trace_thread_interrupter) { |
| 122 OS::PrintErr("ThreadInterrupter shut down.\n"); | 119 OS::PrintErr("ThreadInterrupter shut down.\n"); |
| 123 } | 120 } |
| 124 } | 121 } |
| 125 | 122 |
| 126 | |
| 127 // Delay between interrupts. | 123 // Delay between interrupts. |
| 128 void ThreadInterrupter::SetInterruptPeriod(intptr_t period) { | 124 void ThreadInterrupter::SetInterruptPeriod(intptr_t period) { |
| 129 if (shutdown_) { | 125 if (shutdown_) { |
| 130 return; | 126 return; |
| 131 } | 127 } |
| 132 ASSERT(initialized_); | 128 ASSERT(initialized_); |
| 133 ASSERT(period > 0); | 129 ASSERT(period > 0); |
| 134 interrupt_period_ = period; | 130 interrupt_period_ = period; |
| 135 } | 131 } |
| 136 | 132 |
| 137 | |
| 138 void ThreadInterrupter::WakeUp() { | 133 void ThreadInterrupter::WakeUp() { |
| 139 if (!initialized_) { | 134 if (!initialized_) { |
| 140 // Early call. | 135 // Early call. |
| 141 return; | 136 return; |
| 142 } | 137 } |
| 143 ASSERT(initialized_); | 138 ASSERT(initialized_); |
| 144 { | 139 { |
| 145 MonitorLocker ml(monitor_); | 140 MonitorLocker ml(monitor_); |
| 146 woken_up_ = true; | 141 woken_up_ = true; |
| 147 if (!InDeepSleep()) { | 142 if (!InDeepSleep()) { |
| 148 // No need to notify, regularly waking up. | 143 // No need to notify, regularly waking up. |
| 149 return; | 144 return; |
| 150 } | 145 } |
| 151 // Notify the interrupter to wake it from its deep sleep. | 146 // Notify the interrupter to wake it from its deep sleep. |
| 152 ml.Notify(); | 147 ml.Notify(); |
| 153 } | 148 } |
| 154 } | 149 } |
| 155 | 150 |
| 156 | |
| 157 void ThreadInterrupter::ThreadMain(uword parameters) { | 151 void ThreadInterrupter::ThreadMain(uword parameters) { |
| 158 ASSERT(initialized_); | 152 ASSERT(initialized_); |
| 159 InstallSignalHandler(); | 153 InstallSignalHandler(); |
| 160 if (FLAG_trace_thread_interrupter) { | 154 if (FLAG_trace_thread_interrupter) { |
| 161 OS::PrintErr("ThreadInterrupter thread running.\n"); | 155 OS::PrintErr("ThreadInterrupter thread running.\n"); |
| 162 } | 156 } |
| 163 { | 157 { |
| 164 // Signal to main thread we are ready. | 158 // Signal to main thread we are ready. |
| 165 MonitorLocker startup_ml(monitor_); | 159 MonitorLocker startup_ml(monitor_); |
| 166 OSThread* os_thread = OSThread::Current(); | 160 OSThread* os_thread = OSThread::Current(); |
| (...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 230 // Signal to main thread we are exiting. | 224 // Signal to main thread we are exiting. |
| 231 MonitorLocker shutdown_ml(monitor_); | 225 MonitorLocker shutdown_ml(monitor_); |
| 232 thread_running_ = false; | 226 thread_running_ = false; |
| 233 shutdown_ml.Notify(); | 227 shutdown_ml.Notify(); |
| 234 } | 228 } |
| 235 } | 229 } |
| 236 | 230 |
| 237 #endif // !PRODUCT | 231 #endif // !PRODUCT |
| 238 | 232 |
| 239 } // namespace dart | 233 } // namespace dart |
| OLD | NEW |