Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1145)

Side by Side Diff: chrome/browser/chromeos/policy/active_directory_policy_manager.cc

Issue 2954293002: Chromad: Prevent session from starting without policy (Closed)
Patch Set: Move MockAuthPolicyClient into unittest Created 3 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 The Chromium 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 "chrome/browser/chromeos/policy/active_directory_policy_manager.h" 5 #include "chrome/browser/chromeos/policy/active_directory_policy_manager.h"
6 6
7 #include <string> 7 #include <string>
8 #include <utility> 8 #include <utility>
9 9
10 #include "base/logging.h" 10 #include "base/logging.h"
(...skipping 13 matching lines...) Expand all
24 } // namespace 24 } // namespace
25 25
26 namespace policy { 26 namespace policy {
27 27
28 ActiveDirectoryPolicyManager::~ActiveDirectoryPolicyManager() {} 28 ActiveDirectoryPolicyManager::~ActiveDirectoryPolicyManager() {}
29 29
30 // static 30 // static
31 std::unique_ptr<ActiveDirectoryPolicyManager> 31 std::unique_ptr<ActiveDirectoryPolicyManager>
32 ActiveDirectoryPolicyManager::CreateForDevicePolicy( 32 ActiveDirectoryPolicyManager::CreateForDevicePolicy(
33 std::unique_ptr<CloudPolicyStore> store) { 33 std::unique_ptr<CloudPolicyStore> store) {
34 // Can't use MakeUnique<> because the constructor is private.
34 return base::WrapUnique( 35 return base::WrapUnique(
35 new ActiveDirectoryPolicyManager(EmptyAccountId(), std::move(store))); 36 new ActiveDirectoryPolicyManager(EmptyAccountId(), base::TimeDelta(),
37 base::OnceClosure(), std::move(store)));
36 } 38 }
37 39
38 // static 40 // static
39 std::unique_ptr<ActiveDirectoryPolicyManager> 41 std::unique_ptr<ActiveDirectoryPolicyManager>
40 ActiveDirectoryPolicyManager::CreateForUserPolicy( 42 ActiveDirectoryPolicyManager::CreateForUserPolicy(
41 const AccountId& account_id, 43 const AccountId& account_id,
44 base::TimeDelta initial_policy_fetch_timeout,
45 base::OnceClosure exit_session,
42 std::unique_ptr<CloudPolicyStore> store) { 46 std::unique_ptr<CloudPolicyStore> store) {
43 return base::WrapUnique( 47 // Can't use MakeUnique<> because the constructor is private.
44 new ActiveDirectoryPolicyManager(account_id, std::move(store))); 48 return base::WrapUnique(new ActiveDirectoryPolicyManager(
49 account_id, initial_policy_fetch_timeout, std::move(exit_session),
50 std::move(store)));
45 } 51 }
46 52
47 void ActiveDirectoryPolicyManager::Init(SchemaRegistry* registry) { 53 void ActiveDirectoryPolicyManager::Init(SchemaRegistry* registry) {
48 ConfigurationPolicyProvider::Init(registry); 54 ConfigurationPolicyProvider::Init(registry);
49 55
50 store_->AddObserver(this); 56 store_->AddObserver(this);
51 if (!store_->is_initialized()) { 57 if (!store_->is_initialized()) {
52 store_->Load(); 58 store_->Load();
53 } 59 }
54 60
55 // Does nothing if |store_| hasn't yet initialized. 61 // Does nothing if |store_| hasn't yet initialized.
56 PublishPolicy(); 62 PublishPolicy();
57 63
58 scheduler_ = base::MakeUnique<PolicyScheduler>( 64 scheduler_ = base::MakeUnique<PolicyScheduler>(
59 base::BindRepeating(&ActiveDirectoryPolicyManager::DoFetch, 65 base::BindRepeating(&ActiveDirectoryPolicyManager::DoPolicyFetch,
60 weak_ptr_factory_.GetWeakPtr()), 66 weak_ptr_factory_.GetWeakPtr()),
61 base::BindRepeating(&ActiveDirectoryPolicyManager::OnPolicyFetched, 67 base::BindRepeating(&ActiveDirectoryPolicyManager::OnPolicyFetched,
62 weak_ptr_factory_.GetWeakPtr()), 68 weak_ptr_factory_.GetWeakPtr()),
63 kFetchInterval); 69 kFetchInterval);
64 } 70 }
65 71
66 void ActiveDirectoryPolicyManager::Shutdown() { 72 void ActiveDirectoryPolicyManager::Shutdown() {
67 store_->RemoveObserver(this); 73 store_->RemoveObserver(this);
68 ConfigurationPolicyProvider::Shutdown(); 74 ConfigurationPolicyProvider::Shutdown();
69 } 75 }
70 76
71 bool ActiveDirectoryPolicyManager::IsInitializationComplete( 77 bool ActiveDirectoryPolicyManager::IsInitializationComplete(
72 PolicyDomain domain) const { 78 PolicyDomain domain) const {
79 if (waiting_for_initial_policy_fetch_) {
80 return false;
81 }
73 if (domain == POLICY_DOMAIN_CHROME) { 82 if (domain == POLICY_DOMAIN_CHROME) {
74 return store_->is_initialized(); 83 return store_->is_initialized();
75 } 84 }
76 return true; 85 return true;
77 } 86 }
78 87
79 void ActiveDirectoryPolicyManager::RefreshPolicies() { 88 void ActiveDirectoryPolicyManager::RefreshPolicies() {
80 scheduler_->ScheduleTaskNow(); 89 scheduler_->ScheduleTaskNow();
81 } 90 }
82 91
83 void ActiveDirectoryPolicyManager::OnStoreLoaded( 92 void ActiveDirectoryPolicyManager::OnStoreLoaded(
84 CloudPolicyStore* cloud_policy_store) { 93 CloudPolicyStore* cloud_policy_store) {
85 DCHECK_EQ(store_.get(), cloud_policy_store); 94 DCHECK_EQ(store_.get(), cloud_policy_store);
86 PublishPolicy(); 95 PublishPolicy();
96 if (fetch_ever_completed_) {
97 // Policy is guaranteed to be up to date with the previous fetch result
98 // because OnPolicyFetched() cancels any potentially running Load()
99 // operations.
100 CancelWaitForInitialPolicy(fetch_ever_succeeded_ /* success */);
101 }
87 } 102 }
88 103
89 void ActiveDirectoryPolicyManager::OnStoreError( 104 void ActiveDirectoryPolicyManager::OnStoreError(
90 CloudPolicyStore* cloud_policy_store) { 105 CloudPolicyStore* cloud_policy_store) {
91 DCHECK_EQ(store_.get(), cloud_policy_store); 106 DCHECK_EQ(store_.get(), cloud_policy_store);
92 // Publish policy (even though it hasn't changed) in order to signal load 107 // Publish policy (even though it hasn't changed) in order to signal load
93 // complete on the ConfigurationPolicyProvider interface. Technically, this is 108 // complete on the ConfigurationPolicyProvider interface. Technically, this is
94 // only required on the first load, but doesn't hurt in any case. 109 // only required on the first load, but doesn't hurt in any case.
95 PublishPolicy(); 110 PublishPolicy();
111 if (fetch_ever_completed_) {
112 CancelWaitForInitialPolicy(false /* success */);
113 }
114 }
115
116 void ActiveDirectoryPolicyManager::ForceTimeoutForTest() {
117 DCHECK(initial_policy_timeout_.IsRunning());
118 // Stop the timer to mimic what happens when a real timer fires, then invoke
119 // the timer callback directly.
120 initial_policy_timeout_.Stop();
121 OnBlockingFetchTimeout();
96 } 122 }
97 123
98 ActiveDirectoryPolicyManager::ActiveDirectoryPolicyManager( 124 ActiveDirectoryPolicyManager::ActiveDirectoryPolicyManager(
99 const AccountId& account_id, 125 const AccountId& account_id,
126 base::TimeDelta initial_policy_fetch_timeout,
127 base::OnceClosure exit_session,
100 std::unique_ptr<CloudPolicyStore> store) 128 std::unique_ptr<CloudPolicyStore> store)
101 : account_id_(account_id), store_(std::move(store)) {} 129 : account_id_(account_id),
130 waiting_for_initial_policy_fetch_(
131 !initial_policy_fetch_timeout.is_zero()),
132 initial_policy_fetch_may_fail_(!initial_policy_fetch_timeout.is_max()),
133 exit_session_(std::move(exit_session)),
134 store_(std::move(store)) {
135 // Delaying initialization complete is intended for user policy only.
136 DCHECK(account_id != EmptyAccountId() || !waiting_for_initial_policy_fetch_);
137 if (waiting_for_initial_policy_fetch_ && initial_policy_fetch_may_fail_) {
138 initial_policy_timeout_.Start(
139 FROM_HERE, initial_policy_fetch_timeout,
140 base::Bind(&ActiveDirectoryPolicyManager::OnBlockingFetchTimeout,
141 weak_ptr_factory_.GetWeakPtr()));
142 }
143 }
102 144
103 void ActiveDirectoryPolicyManager::PublishPolicy() { 145 void ActiveDirectoryPolicyManager::PublishPolicy() {
104 if (!store_->is_initialized()) { 146 if (!store_->is_initialized()) {
105 return; 147 return;
106 } 148 }
107 std::unique_ptr<PolicyBundle> bundle = base::MakeUnique<PolicyBundle>(); 149 std::unique_ptr<PolicyBundle> bundle = base::MakeUnique<PolicyBundle>();
108 PolicyMap& policy_map = 150 PolicyMap& policy_map =
109 bundle->Get(PolicyNamespace(POLICY_DOMAIN_CHROME, std::string())); 151 bundle->Get(PolicyNamespace(POLICY_DOMAIN_CHROME, std::string()));
110 policy_map.CopyFrom(store_->policy_map()); 152 policy_map.CopyFrom(store_->policy_map());
111 153
112 // Overwrite the source which is POLICY_SOURCE_CLOUD by default. 154 // Overwrite the source which is POLICY_SOURCE_CLOUD by default.
113 // TODO(tnagel): Rename CloudPolicyStore to PolicyStore and make the source 155 // TODO(tnagel): Rename CloudPolicyStore to PolicyStore and make the source
114 // configurable, then drop PolicyMap::SetSourceForAll(). 156 // configurable, then drop PolicyMap::SetSourceForAll().
115 policy_map.SetSourceForAll(POLICY_SOURCE_ACTIVE_DIRECTORY); 157 policy_map.SetSourceForAll(POLICY_SOURCE_ACTIVE_DIRECTORY);
116 SetEnterpriseUsersDefaults(&policy_map); 158 SetEnterpriseUsersDefaults(&policy_map);
117 UpdatePolicy(std::move(bundle)); 159 UpdatePolicy(std::move(bundle));
118 } 160 }
119 161
120 void ActiveDirectoryPolicyManager::DoFetch( 162 void ActiveDirectoryPolicyManager::DoPolicyFetch(
121 base::OnceCallback<void(bool success)> callback) { 163 base::OnceCallback<void(bool success)> callback) {
122 chromeos::DBusThreadManager* thread_manager = 164 chromeos::DBusThreadManager* thread_manager =
123 chromeos::DBusThreadManager::Get(); 165 chromeos::DBusThreadManager::Get();
124 DCHECK(thread_manager); 166 DCHECK(thread_manager);
125 chromeos::AuthPolicyClient* auth_policy_client = 167 chromeos::AuthPolicyClient* auth_policy_client =
126 thread_manager->GetAuthPolicyClient(); 168 thread_manager->GetAuthPolicyClient();
127 DCHECK(auth_policy_client); 169 DCHECK(auth_policy_client);
128 if (account_id_ == EmptyAccountId()) { 170 if (account_id_ == EmptyAccountId()) {
129 auth_policy_client->RefreshDevicePolicy(std::move(callback)); 171 auth_policy_client->RefreshDevicePolicy(std::move(callback));
130 } else { 172 } else {
131 auth_policy_client->RefreshUserPolicy(account_id_, std::move(callback)); 173 auth_policy_client->RefreshUserPolicy(account_id_, std::move(callback));
132 } 174 }
133 } 175 }
134 176
135 void ActiveDirectoryPolicyManager::OnPolicyFetched(bool success) { 177 void ActiveDirectoryPolicyManager::OnPolicyFetched(bool success) {
136 if (!success) { 178 fetch_ever_completed_ = true;
179 if (success) {
180 fetch_ever_succeeded_ = true;
181 } else {
137 LOG(ERROR) << "Active Directory policy fetch failed."; 182 LOG(ERROR) << "Active Directory policy fetch failed.";
183 if (store_->is_initialized()) {
184 CancelWaitForInitialPolicy(false /* success */);
185 }
138 } 186 }
139 // Load independently of success or failure to keep up to date with whatever 187 // Load independently of success or failure to keep in sync with the state in
140 // has happened on the authpolicyd / session manager side. 188 // session manager. This cancels any potentially running Load() operations
189 // thus it is guaranteed that at the next OnStoreLoaded() invocation the
190 // policy is up-to-date with what was fetched.
141 store_->Load(); 191 store_->Load();
142 } 192 }
143 193
194 void ActiveDirectoryPolicyManager::OnBlockingFetchTimeout() {
195 DCHECK(waiting_for_initial_policy_fetch_);
196 LOG(WARNING) << "Timed out while waiting for the policy fetch. "
197 << "The session will start with the cached policy.";
198 CancelWaitForInitialPolicy(false);
199 }
200
201 void ActiveDirectoryPolicyManager::CancelWaitForInitialPolicy(bool success) {
202 if (!waiting_for_initial_policy_fetch_)
203 return;
204
205 initial_policy_timeout_.Stop();
206
207 // If the conditions to continue profile initialization are not met, the user
208 // session is exited and initialization is not set as completed.
209 // TODO(tnagel): Maybe add code to retry policy fetch?
210 if (!store_->has_policy()) {
211 // If there's no policy at all (not even cached) the user session must not
212 // continue.
213 LOG(ERROR) << "Policy could not be obtained. "
214 << "Aborting profile initialization";
215 // Prevent duplicate exit session calls.
216 if (exit_session_) {
217 std::move(exit_session_).Run();
218 }
219 return;
220 }
221 if (!success && !initial_policy_fetch_may_fail_) {
222 LOG(ERROR) << "Policy fetch failed for the user. "
223 << "Aborting profile initialization";
224 // Prevent duplicate exit session calls.
225 if (exit_session_) {
226 std::move(exit_session_).Run();
227 }
228 return;
229 }
230
231 // Set initialization complete.
232 waiting_for_initial_policy_fetch_ = false;
233
234 // Publish policy (even though it hasn't changed) in order to signal load
235 // complete on the ConfigurationPolicyProvider interface.
236 PublishPolicy();
237 }
238
144 } // namespace policy 239 } // namespace policy
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698