| 117 | // Internal private methods that the watchdog thread uses. |
| 118 | |
| 119 | void Watchdog::ThreadDelegate::ThreadMain() { |
| 120 | SetThreadName(); |
| 121 | TimeDelta remaining_duration; |
| 122 | StaticData* static_data = g_static_data.Pointer(); |
| 123 | while (1) { |
| 124 | AutoLock lock(watchdog_->lock_); |
| 125 | while (DISARMED == watchdog_->state_) |
| 126 | watchdog_->condition_variable_.Wait(); |
| 127 | if (SHUTDOWN == watchdog_->state_) { |
| 128 | watchdog_->state_ = JOINABLE; |
| 129 | return; |
| 130 | } |
| 131 | DCHECK(ARMED == watchdog_->state_); |
| 132 | remaining_duration = watchdog_->duration_ - |
| 133 | (TimeTicks::Now() - watchdog_->start_time_); |
| 134 | if (remaining_duration.InMilliseconds() > 0) { |
| 135 | // Spurios wake? Timer drifts? Go back to sleep for remaining time. |
| 136 | watchdog_->condition_variable_.TimedWait(remaining_duration); |
| 137 | continue; |
| 138 | } |
| 139 | // We overslept, so this seems like a real alarm. |
| 140 | // Watch out for a user that stopped the debugger on a different alarm! |
| 141 | { |
| 142 | AutoLock static_lock(static_data->lock); |
| 143 | if (static_data->last_debugged_alarm_time > watchdog_->start_time_) { |
| 144 | // False alarm: we started our clock before the debugger break (last |
| 145 | // alarm time). |
| 146 | watchdog_->start_time_ += static_data->last_debugged_alarm_delay; |
| 147 | if (static_data->last_debugged_alarm_time > watchdog_->start_time_) |
| 148 | // Too many alarms must have taken place. |
| 149 | watchdog_->state_ = DISARMED; |
| 150 | continue; |
| 151 | } |
| 152 | } |
| 153 | watchdog_->state_ = DISARMED; // Only alarm at most once. |
| 154 | TimeTicks last_alarm_time = TimeTicks::Now(); |
| 155 | { |
| 156 | AutoUnlock lock(watchdog_->lock_); |
| 157 | watchdog_->Alarm(); // Set a break point here to debug on alarms. |
| 158 | } |
| 159 | TimeDelta last_alarm_delay = TimeTicks::Now() - last_alarm_time; |
| 160 | if (last_alarm_delay <= TimeDelta::FromMilliseconds(2)) |
| 161 | continue; |
| 162 | // Ignore race of two alarms/breaks going off at roughly the same time. |
| 163 | AutoLock static_lock(static_data->lock); |
| 164 | // This was a real debugger break. |
| 165 | static_data->last_debugged_alarm_time = last_alarm_time; |
| 166 | static_data->last_debugged_alarm_delay = last_alarm_delay; |
| 167 | } |
| 168 | } |
| 169 | |
| 170 | void Watchdog::ThreadDelegate::SetThreadName() const { |
| 171 | std::string name = watchdog_->thread_watched_name_ + " Watchdog"; |
no test coverage detected