evaluation_context.cc revision 39910dcd1d68987ccee7c3031dc269233a8490bb
1aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// 2aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// Copyright (C) 2014 The Android Open Source Project 3aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// 4aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// Licensed under the Apache License, Version 2.0 (the "License"); 5aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// you may not use this file except in compliance with the License. 6aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// You may obtain a copy of the License at 7aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// 8aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// http://www.apache.org/licenses/LICENSE-2.0 9aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// 10aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// Unless required by applicable law or agreed to in writing, software 11aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// distributed under the License is distributed on an "AS IS" BASIS, 12aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// See the License for the specific language governing permissions and 14aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// limitations under the License. 15aea4c1cea20dda7ae7e85fc8924a2d784f70d806Alex Deymo// 1623949d4e086ca984ca2ce07efb6d4ae2bc5daf42Alex Deymo 1763784a578dd26880454d70797519358a2326291bAlex Deymo#include "update_engine/update_manager/evaluation_context.h" 1823949d4e086ca984ca2ce07efb6d4ae2bc5daf42Alex Deymo 19f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold#include <algorithm> 2002f7c1dee242f490143791dbb73fa23fa3007cfaBen Chan#include <memory> 21c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen#include <string> 22c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen 2353556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo#include <base/bind.h> 24c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen#include <base/json/json_writer.h> 250bb234147ea8f0247b733375fcf1685eaf329aacAlex Deymo#include <base/location.h> 266e5ab5c011a214aa345ecbba3d910c2ffaec3c83Gilad Arnold#include <base/strings/string_util.h> 27c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen#include <base/values.h> 28c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen 2939910dcd1d68987ccee7c3031dc269233a8490bbAlex Deymo#include "update_engine/common/utils.h" 3053556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo 3183ffddaa3b09ceb4361e5c01ba300d57ab697a7eGilad Arnoldusing base::Callback; 3253556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymousing base::Closure; 3341a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymousing base::Time; 3423949d4e086ca984ca2ce07efb6d4ae2bc5daf42Alex Deymousing base::TimeDelta; 353f39d5cc753905874d8d93bef94f857b8808f19eAlex Vakulenkousing brillo::MessageLoop; 3641a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymousing chromeos_update_engine::ClockInterface; 37c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthenusing std::string; 3802f7c1dee242f490143791dbb73fa23fa3007cfaBen Chanusing std::unique_ptr; 3923949d4e086ca984ca2ce07efb6d4ae2bc5daf42Alex Deymo 40a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnoldnamespace { 41a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold 42a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold// Returns whether |curr_time| surpassed |ref_time|; if not, also checks whether 43a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold// |ref_time| is sooner than the current value of |*reeval_time|, in which case 44a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold// the latter is updated to the former. 45f329b933db41d26644a97afef928eb1b319d6d99Alex Deymobool IsTimeGreaterThanHelper(Time ref_time, Time curr_time, 46f329b933db41d26644a97afef928eb1b319d6d99Alex Deymo Time* reeval_time) { 47a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold if (curr_time > ref_time) 48a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold return true; 49a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold // Remember the nearest reference we've checked against in this evaluation. 50a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold if (*reeval_time > ref_time) 51a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold *reeval_time = ref_time; 52a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold return false; 53a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold} 54a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold 55a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold// If |expires| never happens (maximal value), returns the maximal interval; 56a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold// otherwise, returns the difference between |expires| and |curr|. 57f329b933db41d26644a97afef928eb1b319d6d99Alex DeymoTimeDelta GetTimeout(Time curr, Time expires) { 58a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold if (expires.is_max()) 59a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold return TimeDelta::Max(); 60a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold return expires - curr; 61a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold} 62a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold 63a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold} // namespace 64a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold 6563784a578dd26880454d70797519358a2326291bAlex Deymonamespace chromeos_update_manager { 6623949d4e086ca984ca2ce07efb6d4ae2bc5daf42Alex Deymo 6783ffddaa3b09ceb4361e5c01ba300d57ab697a7eGilad ArnoldEvaluationContext::EvaluationContext( 6883ffddaa3b09ceb4361e5c01ba300d57ab697a7eGilad Arnold ClockInterface* clock, 6983ffddaa3b09ceb4361e5c01ba300d57ab697a7eGilad Arnold TimeDelta evaluation_timeout, 7083ffddaa3b09ceb4361e5c01ba300d57ab697a7eGilad Arnold TimeDelta expiration_timeout, 7102f7c1dee242f490143791dbb73fa23fa3007cfaBen Chan unique_ptr<Callback<void(EvaluationContext*)>> unregister_cb) 7241a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo : clock_(clock), 73b227199133f2d694414293697c67599a761f23beGilad Arnold evaluation_timeout_(evaluation_timeout), 74fd45a731d9f9176ce134b34e2a84acc0cf403d1dGilad Arnold expiration_timeout_(expiration_timeout), 7502f7c1dee242f490143791dbb73fa23fa3007cfaBen Chan unregister_cb_(std::move(unregister_cb)), 7641a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo weak_ptr_factory_(this) { 7741a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo ResetEvaluation(); 78fd45a731d9f9176ce134b34e2a84acc0cf403d1dGilad Arnold ResetExpiration(); 7941a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo} 8041a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo 8153556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex DeymoEvaluationContext::~EvaluationContext() { 8253556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo RemoveObserversAndTimeout(); 8383ffddaa3b09ceb4361e5c01ba300d57ab697a7eGilad Arnold if (unregister_cb_.get()) 8483ffddaa3b09ceb4361e5c01ba300d57ab697a7eGilad Arnold unregister_cb_->Run(this); 8553556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo} 8653556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo 8702f7c1dee242f490143791dbb73fa23fa3007cfaBen Chanunique_ptr<Closure> EvaluationContext::RemoveObserversAndTimeout() { 8853556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo for (auto& it : value_cache_) { 8953556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo if (it.first->GetMode() == kVariableModeAsync) 9053556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo it.first->RemoveObserver(this); 9153556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo } 92509dd5376f47e38d18fe7d29da776e3dc9a9786dAlex Deymo MessageLoop::current()->CancelTask(timeout_event_); 93509dd5376f47e38d18fe7d29da776e3dc9a9786dAlex Deymo timeout_event_ = MessageLoop::kTaskIdNull; 9483ffddaa3b09ceb4361e5c01ba300d57ab697a7eGilad Arnold 9502f7c1dee242f490143791dbb73fa23fa3007cfaBen Chan return unique_ptr<Closure>(callback_.release()); 9653556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo} 9753556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo 98f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad ArnoldTimeDelta EvaluationContext::RemainingTime(Time monotonic_deadline) const { 99f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold if (monotonic_deadline.is_max()) 100f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold return TimeDelta::Max(); 101f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold TimeDelta remaining = monotonic_deadline - clock_->GetMonotonicTime(); 102f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold return std::max(remaining, TimeDelta()); 103f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold} 104f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold 105f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad ArnoldTime EvaluationContext::MonotonicDeadline(TimeDelta timeout) { 106f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold return (timeout.is_max() ? Time::Max() : 107f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold clock_->GetMonotonicTime() + timeout); 10823949d4e086ca984ca2ce07efb6d4ae2bc5daf42Alex Deymo} 10923949d4e086ca984ca2ce07efb6d4ae2bc5daf42Alex Deymo 11053556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymovoid EvaluationContext::ValueChanged(BaseVariable* var) { 111f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold DLOG(INFO) << "ValueChanged() called for variable " << var->GetName(); 112f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold OnValueChangedOrTimeout(); 11353556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo} 11453556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo 115f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnoldvoid EvaluationContext::OnTimeout() { 116f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold DLOG(INFO) << "OnTimeout() called due to " 117f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold << (timeout_marks_expiration_ ? "expiration" : "poll interval"); 118509dd5376f47e38d18fe7d29da776e3dc9a9786dAlex Deymo timeout_event_ = MessageLoop::kTaskIdNull; 119f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold is_expired_ = timeout_marks_expiration_; 120f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold OnValueChangedOrTimeout(); 12153556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo} 12253556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo 123f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnoldvoid EvaluationContext::OnValueChangedOrTimeout() { 124f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold // Copy the callback handle locally, allowing it to be reassigned. 12502f7c1dee242f490143791dbb73fa23fa3007cfaBen Chan unique_ptr<Closure> callback = RemoveObserversAndTimeout(); 126f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold 127f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold if (callback.get()) 128fb794f4b7274576e10b0df291655ad6c88a97df4Gilad Arnold callback->Run(); 12941a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo} 13041a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo 131f329b933db41d26644a97afef928eb1b319d6d99Alex Deymobool EvaluationContext::IsWallclockTimeGreaterThan(Time timestamp) { 132a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold return IsTimeGreaterThanHelper(timestamp, evaluation_start_wallclock_, 133a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold &reevaluation_time_wallclock_); 134a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold} 135a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold 136f329b933db41d26644a97afef928eb1b319d6d99Alex Deymobool EvaluationContext::IsMonotonicTimeGreaterThan(Time timestamp) { 137a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold return IsTimeGreaterThanHelper(timestamp, evaluation_start_monotonic_, 138a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold &reevaluation_time_monotonic_); 13941a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo} 14041a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo 14141a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymovoid EvaluationContext::ResetEvaluation() { 142a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold evaluation_start_wallclock_ = clock_->GetWallclockTime(); 143a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold evaluation_start_monotonic_ = clock_->GetMonotonicTime(); 144a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold reevaluation_time_wallclock_ = Time::Max(); 145a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold reevaluation_time_monotonic_ = Time::Max(); 146f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold evaluation_monotonic_deadline_ = MonotonicDeadline(evaluation_timeout_); 14741a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo 14853556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo // Remove the cached values of non-const variables 14953556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo for (auto it = value_cache_.begin(); it != value_cache_.end(); ) { 15053556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo if (it->first->GetMode() == kVariableModeConst) { 15153556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo ++it; 15253556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo } else { 15353556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo it = value_cache_.erase(it); 15453556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo } 15553556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo } 15653556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo} 15753556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo 158fd45a731d9f9176ce134b34e2a84acc0cf403d1dGilad Arnoldvoid EvaluationContext::ResetExpiration() { 159fd45a731d9f9176ce134b34e2a84acc0cf403d1dGilad Arnold expiration_monotonic_deadline_ = MonotonicDeadline(expiration_timeout_); 160fd45a731d9f9176ce134b34e2a84acc0cf403d1dGilad Arnold is_expired_ = false; 161fd45a731d9f9176ce134b34e2a84acc0cf403d1dGilad Arnold} 162fd45a731d9f9176ce134b34e2a84acc0cf403d1dGilad Arnold 16353556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymobool EvaluationContext::RunOnValueChangeOrTimeout(Closure callback) { 164f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold // Check that the method was not called more than once. 16588b591f24cb3f94f982d7024c2e8ed25c2cc26a2Alex Vakulenko if (callback_.get()) { 166f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold LOG(ERROR) << "RunOnValueChangeOrTimeout called more than once."; 167f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold return false; 16841a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo } 16941a75a7ca3f0252f2c9f991dd465aa332e7ce4d1Alex Deymo 170f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold // Check that the context did not yet expire. 171f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold if (is_expired()) { 172f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold LOG(ERROR) << "RunOnValueChangeOrTimeout called on an expired context."; 17353556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo return false; 17453556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo } 17553556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo 176a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold // Handle reevaluation due to a Is{Wallclock,Monotonic}TimeGreaterThan(). We 177a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold // choose the smaller of the differences between evaluation start time and 178a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold // reevaluation time among the wallclock and monotonic scales. 179a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold TimeDelta timeout = std::min( 180a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold GetTimeout(evaluation_start_wallclock_, reevaluation_time_wallclock_), 181a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold GetTimeout(evaluation_start_monotonic_, reevaluation_time_monotonic_)); 182f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold 183f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold // Handle reevaluation due to async or poll variables. 184a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold bool waiting_for_value_change = false; 18553556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo for (auto& it : value_cache_) { 18653556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo switch (it.first->GetMode()) { 18753556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo case kVariableModeAsync: 18853556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo DLOG(INFO) << "Waiting for value on " << it.first->GetName(); 18953556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo it.first->AddObserver(this); 190f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold waiting_for_value_change = true; 19153556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo break; 19253556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo case kVariableModePoll: 193f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold timeout = std::min(timeout, it.first->GetPollInterval()); 19453556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo break; 19553556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo case kVariableModeConst: 19653556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo // Ignored. 19753556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo break; 19853556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo } 19953556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo } 200f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold 20153556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo // Check if the re-evaluation is actually being scheduled. If there are no 20253556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo // events waited for, this function should return false. 203f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold if (!waiting_for_value_change && timeout.is_max()) 20453556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo return false; 205f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold 206f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold // Ensure that we take into account the expiration timeout. 207f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold TimeDelta expiration = RemainingTime(expiration_monotonic_deadline_); 208f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold timeout_marks_expiration_ = expiration < timeout; 209f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold if (timeout_marks_expiration_) 210f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold timeout = expiration; 211f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold 212f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold // Store the reevaluation callback. 213f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold callback_.reset(new Closure(callback)); 214f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold 215f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold // Schedule a timeout event, if one is set. 216f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold if (!timeout.is_max()) { 217f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold DLOG(INFO) << "Waiting for timeout in " 218f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold << chromeos_update_engine::utils::FormatTimeDelta(timeout); 219509dd5376f47e38d18fe7d29da776e3dc9a9786dAlex Deymo timeout_event_ = MessageLoop::current()->PostDelayedTask( 2200bb234147ea8f0247b733375fcf1685eaf329aacAlex Deymo FROM_HERE, 221f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold base::Bind(&EvaluationContext::OnTimeout, 222db799534a8f6ae061ed6d6a46ed800f55d50325bAlex Deymo weak_ptr_factory_.GetWeakPtr()), 223f9f85d6680164064648ce3ed1d31589e1f1b7a29Gilad Arnold timeout); 22453556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo } 22553556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo 22653556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo return true; 22753556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo} 22853556eccd206bacd5c9c8bb6605bcceb1bcb6190Alex Deymo 229c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthenstring EvaluationContext::DumpContext() const { 230c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen base::DictionaryValue* variables = new base::DictionaryValue(); 231c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen for (auto& it : value_cache_) { 232c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen variables->SetString(it.first->GetName(), it.second.ToString()); 233c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen } 234c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen 235c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen base::DictionaryValue value; 236c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen value.Set("variables", variables); // Adopts |variables|. 237a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold value.SetString( 238a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold "evaluation_start_wallclock", 239a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold chromeos_update_engine::utils::ToString(evaluation_start_wallclock_)); 240a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold value.SetString( 241a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold "evaluation_start_monotonic", 242a65fced5f4c2b551616b26ee90a800b44090735fGilad Arnold chromeos_update_engine::utils::ToString(evaluation_start_monotonic_)); 243c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen 244c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen string json_str; 2456a9d3497bcf57b8b9f5765a2909a51c9f8119cd1Alex Vakulenko base::JSONWriter::WriteWithOptions( 2466a9d3497bcf57b8b9f5765a2909a51c9f8119cd1Alex Vakulenko value, base::JSONWriter::OPTIONS_PRETTY_PRINT, &json_str); 2476e5ab5c011a214aa345ecbba3d910c2ffaec3c83Gilad Arnold base::TrimWhitespaceASCII(json_str, base::TRIM_TRAILING, &json_str); 248c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen 249c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen return json_str; 250c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen} 251c14902888be0b8d41759e6ff0a7100af4097fd09David Zeuthen 25263784a578dd26880454d70797519358a2326291bAlex Deymo} // namespace chromeos_update_manager 253