OLD | NEW |
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 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 // Most of this code is copied from: | 5 // Most of this code is copied from: |
6 // src/chrome/browser/policy/asynchronous_policy_loader.{h,cc} | 6 // src/chrome/browser/policy/asynchronous_policy_loader.{h,cc} |
7 | 7 |
8 #include "remoting/host/policy_watcher.h" | 8 #include "remoting/host/policy_watcher.h" |
9 | 9 |
10 #include <utility> | 10 #include <utility> |
(...skipping 29 matching lines...) Expand all Loading... |
40 #elif defined(OS_POSIX) && !defined(OS_ANDROID) | 40 #elif defined(OS_POSIX) && !defined(OS_ANDROID) |
41 #include "components/policy/core/common/config_dir_policy_loader.h" | 41 #include "components/policy/core/common/config_dir_policy_loader.h" |
42 #endif | 42 #endif |
43 | 43 |
44 namespace remoting { | 44 namespace remoting { |
45 | 45 |
46 namespace key = ::policy::key; | 46 namespace key = ::policy::key; |
47 | 47 |
48 namespace { | 48 namespace { |
49 | 49 |
| 50 // Watches for changes to the managed remote access host policies. |
| 51 class PolicyWatcherImpl : public PolicyWatcher, |
| 52 private policy::PolicyService::Observer { |
| 53 public: |
| 54 // |policy_service_task_runner| is the task runner where it is safe |
| 55 // to call |policy_service_| methods and where we expect to get callbacks |
| 56 // from |policy_service_|. |
| 57 PolicyWatcherImpl( |
| 58 policy::PolicyService* policy_service, |
| 59 std::unique_ptr<policy::PolicyService> owned_policy_service, |
| 60 std::unique_ptr<policy::ConfigurationPolicyProvider> |
| 61 owned_policy_provider, |
| 62 std::unique_ptr<policy::SchemaRegistry> owned_schema_registry); |
| 63 |
| 64 ~PolicyWatcherImpl() override; |
| 65 |
| 66 void StartWatching(const PolicyUpdatedCallback& policy_updated_callback, |
| 67 const PolicyErrorCallback& policy_error_callback) override; |
| 68 |
| 69 private: |
| 70 friend class PolicyWatcherTest; |
| 71 |
| 72 const policy::Schema* GetPolicySchema() const override; |
| 73 const base::DictionaryValue* GetDefaultValues() const override; |
| 74 |
| 75 // Simplifying wrapper around Schema::Normalize. |
| 76 // - Returns false if |dict| is invalid (i.e. contains mistyped policy |
| 77 // values). |
| 78 // - Returns true if |dict| was valid or got normalized. |
| 79 bool NormalizePolicies(base::DictionaryValue* dict); |
| 80 |
| 81 // Stores |new_policies| into |old_policies_|. Returns dictionary with items |
| 82 // from |new_policies| that are different from the old |old_policies_|. |
| 83 std::unique_ptr<base::DictionaryValue> StoreNewAndReturnChangedPolicies( |
| 84 std::unique_ptr<base::DictionaryValue> new_policies); |
| 85 |
| 86 // Signals policy error to the registered |PolicyErrorCallback|. |
| 87 void SignalPolicyError(); |
| 88 |
| 89 // PolicyService::Observer interface. |
| 90 void OnPolicyUpdated(const policy::PolicyNamespace& ns, |
| 91 const policy::PolicyMap& previous, |
| 92 const policy::PolicyMap& current) override; |
| 93 void OnPolicyServiceInitialized(policy::PolicyDomain domain) override; |
| 94 |
| 95 PolicyUpdatedCallback policy_updated_callback_; |
| 96 PolicyErrorCallback policy_error_callback_; |
| 97 |
| 98 std::unique_ptr<base::DictionaryValue> old_policies_; |
| 99 std::unique_ptr<base::DictionaryValue> default_values_; |
| 100 |
| 101 policy::PolicyService* policy_service_; |
| 102 |
| 103 // Order of fields below is important to ensure destruction takes object |
| 104 // dependencies into account: |
| 105 // - |owned_policy_service_| uses |owned_policy_provider_| |
| 106 // - |owned_policy_provider_| uses |owned_schema_registry_| |
| 107 std::unique_ptr<policy::SchemaRegistry> owned_schema_registry_; |
| 108 std::unique_ptr<policy::ConfigurationPolicyProvider> owned_policy_provider_; |
| 109 std::unique_ptr<policy::PolicyService> owned_policy_service_; |
| 110 |
| 111 DISALLOW_COPY_AND_ASSIGN(PolicyWatcherImpl); |
| 112 }; |
| 113 |
50 // Copies all policy values from one dictionary to another, using values from | 114 // Copies all policy values from one dictionary to another, using values from |
51 // |default_values| if they are not set in |from|. | 115 // |default_values| if they are not set in |from|. |
52 std::unique_ptr<base::DictionaryValue> CopyValuesAndAddDefaults( | 116 std::unique_ptr<base::DictionaryValue> CopyValuesAndAddDefaults( |
53 const base::DictionaryValue& from, | 117 const base::DictionaryValue& from, |
54 const base::DictionaryValue& default_values) { | 118 const base::DictionaryValue& default_values) { |
55 std::unique_ptr<base::DictionaryValue> to(default_values.CreateDeepCopy()); | 119 std::unique_ptr<base::DictionaryValue> to(default_values.CreateDeepCopy()); |
56 for (base::DictionaryValue::Iterator i(default_values); !i.IsAtEnd(); | 120 for (base::DictionaryValue::Iterator i(default_values); !i.IsAtEnd(); |
57 i.Advance()) { | 121 i.Advance()) { |
58 const base::Value* value = nullptr; | 122 const base::Value* value = nullptr; |
59 | 123 |
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
129 &udp_port_range_string)) { | 193 &udp_port_range_string)) { |
130 if (!PortRange::Parse(udp_port_range_string, &udp_port_range)) { | 194 if (!PortRange::Parse(udp_port_range_string, &udp_port_range)) { |
131 return false; | 195 return false; |
132 } | 196 } |
133 } | 197 } |
134 | 198 |
135 // Report that all the policies were well-formed. | 199 // Report that all the policies were well-formed. |
136 return true; | 200 return true; |
137 } | 201 } |
138 | 202 |
139 } // namespace | 203 void CopyDictionaryValue(const base::DictionaryValue& from, |
| 204 base::DictionaryValue& to, |
| 205 std::string key) { |
| 206 const base::Value* value; |
| 207 if (from.Get(key, &value)) { |
| 208 to.Set(key, value->CreateDeepCopy()); |
| 209 } |
| 210 } |
140 | 211 |
141 void PolicyWatcher::StartWatching( | 212 void PolicyWatcherImpl::StartWatching( |
142 const PolicyUpdatedCallback& policy_updated_callback, | 213 const PolicyUpdatedCallback& policy_updated_callback, |
143 const PolicyErrorCallback& policy_error_callback) { | 214 const PolicyErrorCallback& policy_error_callback) { |
144 DCHECK(CalledOnValidThread()); | 215 DCHECK(CalledOnValidThread()); |
145 DCHECK(!policy_updated_callback.is_null()); | 216 DCHECK(!policy_updated_callback.is_null()); |
146 DCHECK(!policy_error_callback.is_null()); | 217 DCHECK(!policy_error_callback.is_null()); |
147 DCHECK(policy_updated_callback_.is_null()); | 218 DCHECK(policy_updated_callback_.is_null()); |
148 | 219 |
149 policy_updated_callback_ = policy_updated_callback; | 220 policy_updated_callback_ = policy_updated_callback; |
150 policy_error_callback_ = policy_error_callback; | 221 policy_error_callback_ = policy_error_callback; |
151 | 222 |
152 // Listen for future policy changes. | 223 // Listen for future policy changes. |
153 policy_service_->AddObserver(policy::POLICY_DOMAIN_CHROME, this); | 224 policy_service_->AddObserver(policy::POLICY_DOMAIN_CHROME, this); |
154 | 225 |
155 // Process current policy state. | 226 // Process current policy state. |
156 if (policy_service_->IsInitializationComplete(policy::POLICY_DOMAIN_CHROME)) { | 227 if (policy_service_->IsInitializationComplete(policy::POLICY_DOMAIN_CHROME)) { |
157 OnPolicyServiceInitialized(policy::POLICY_DOMAIN_CHROME); | 228 OnPolicyServiceInitialized(policy::POLICY_DOMAIN_CHROME); |
158 } | 229 } |
159 } | 230 } |
160 | 231 |
161 void PolicyWatcher::SignalPolicyError() { | 232 void PolicyWatcherImpl::SignalPolicyError() { |
162 old_policies_->Clear(); | 233 old_policies_->Clear(); |
163 policy_error_callback_.Run(); | 234 policy_error_callback_.Run(); |
164 } | 235 } |
165 | 236 |
166 PolicyWatcher::PolicyWatcher( | 237 PolicyWatcherImpl::PolicyWatcherImpl( |
167 policy::PolicyService* policy_service, | 238 policy::PolicyService* policy_service, |
168 std::unique_ptr<policy::PolicyService> owned_policy_service, | 239 std::unique_ptr<policy::PolicyService> owned_policy_service, |
169 std::unique_ptr<policy::ConfigurationPolicyProvider> owned_policy_provider, | 240 std::unique_ptr<policy::ConfigurationPolicyProvider> owned_policy_provider, |
170 std::unique_ptr<policy::SchemaRegistry> owned_schema_registry) | 241 std::unique_ptr<policy::SchemaRegistry> owned_schema_registry) |
171 : old_policies_(new base::DictionaryValue()), | 242 : old_policies_(new base::DictionaryValue()), |
172 default_values_(new base::DictionaryValue()), | 243 default_values_(new base::DictionaryValue()), |
173 policy_service_(policy_service), | 244 policy_service_(policy_service), |
174 owned_schema_registry_(std::move(owned_schema_registry)), | 245 owned_schema_registry_(std::move(owned_schema_registry)), |
175 owned_policy_provider_(std::move(owned_policy_provider)), | 246 owned_policy_provider_(std::move(owned_policy_provider)), |
176 owned_policy_service_(std::move(owned_policy_service)) { | 247 owned_policy_service_(std::move(owned_policy_service)) { |
(...skipping 15 matching lines...) Expand all Loading... |
192 key::kRemoteAccessHostTokenValidationCertificateIssuer, std::string()); | 263 key::kRemoteAccessHostTokenValidationCertificateIssuer, std::string()); |
193 default_values_->SetBoolean(key::kRemoteAccessHostAllowClientPairing, true); | 264 default_values_->SetBoolean(key::kRemoteAccessHostAllowClientPairing, true); |
194 default_values_->SetBoolean(key::kRemoteAccessHostAllowGnubbyAuth, true); | 265 default_values_->SetBoolean(key::kRemoteAccessHostAllowGnubbyAuth, true); |
195 default_values_->SetBoolean(key::kRemoteAccessHostAllowRelayedConnection, | 266 default_values_->SetBoolean(key::kRemoteAccessHostAllowRelayedConnection, |
196 true); | 267 true); |
197 default_values_->SetString(key::kRemoteAccessHostUdpPortRange, ""); | 268 default_values_->SetString(key::kRemoteAccessHostUdpPortRange, ""); |
198 default_values_->SetBoolean( | 269 default_values_->SetBoolean( |
199 key::kRemoteAccessHostAllowUiAccessForRemoteAssistance, false); | 270 key::kRemoteAccessHostAllowUiAccessForRemoteAssistance, false); |
200 } | 271 } |
201 | 272 |
202 PolicyWatcher::~PolicyWatcher() { | 273 PolicyWatcherImpl::~PolicyWatcherImpl() { |
203 // Stop observing |policy_service_| if StartWatching() has been called. | 274 // Stop observing |policy_service_| if StartWatching() has been called. |
204 if (!policy_updated_callback_.is_null()) { | 275 if (!policy_updated_callback_.is_null()) { |
205 policy_service_->RemoveObserver(policy::POLICY_DOMAIN_CHROME, this); | 276 policy_service_->RemoveObserver(policy::POLICY_DOMAIN_CHROME, this); |
206 } | 277 } |
207 | 278 |
208 if (owned_policy_provider_) { | 279 if (owned_policy_provider_) { |
209 owned_policy_provider_->Shutdown(); | 280 owned_policy_provider_->Shutdown(); |
210 } | 281 } |
211 } | 282 } |
212 | 283 |
213 const policy::Schema* PolicyWatcher::GetPolicySchema() const { | 284 const policy::Schema* PolicyWatcherImpl::GetPolicySchema() const { |
214 return owned_schema_registry_->schema_map()->GetSchema(GetPolicyNamespace()); | 285 return owned_schema_registry_->schema_map()->GetSchema(GetPolicyNamespace()); |
215 } | 286 } |
216 | 287 |
217 bool PolicyWatcher::NormalizePolicies(base::DictionaryValue* policy_dict) { | 288 const base::DictionaryValue* PolicyWatcherImpl::GetDefaultValues() const { |
| 289 return default_values_.get(); |
| 290 } |
| 291 |
| 292 bool PolicyWatcherImpl::NormalizePolicies(base::DictionaryValue* policy_dict) { |
218 // Allowing unrecognized policy names allows presence of | 293 // Allowing unrecognized policy names allows presence of |
219 // 1) comments (i.e. JSON of the form: { "_comment": "blah", ... }), | 294 // 1) comments (i.e. JSON of the form: { "_comment": "blah", ... }), |
220 // 2) policies intended for future/newer versions of the host, | 295 // 2) policies intended for future/newer versions of the host, |
221 // 3) policies not supported on all OS-s (i.e. RemoteAccessHostMatchUsername | 296 // 3) policies not supported on all OS-s (i.e. RemoteAccessHostMatchUsername |
222 // is not supported on Windows and therefore policy_templates.json omits | 297 // is not supported on Windows and therefore policy_templates.json omits |
223 // schema for this policy on this particular platform). | 298 // schema for this policy on this particular platform). |
224 auto strategy = policy::SCHEMA_ALLOW_UNKNOWN_TOPLEVEL; | 299 auto strategy = policy::SCHEMA_ALLOW_UNKNOWN_TOPLEVEL; |
225 | 300 |
226 std::string path; | 301 std::string path; |
227 std::string error; | 302 std::string error; |
228 bool changed = false; | 303 bool changed = false; |
229 const policy::Schema* schema = GetPolicySchema(); | 304 const policy::Schema* schema = GetPolicySchema(); |
230 if (schema->Normalize(policy_dict, strategy, &path, &error, &changed)) { | 305 if (schema->Normalize(policy_dict, strategy, &path, &error, &changed)) { |
231 if (changed) { | 306 if (changed) { |
232 LOG(WARNING) << "Unknown (unrecognized or unsupported) policy: " << path | 307 LOG(WARNING) << "Unknown (unrecognized or unsupported) policy: " << path |
233 << ": " << error; | 308 << ": " << error; |
234 } | 309 } |
235 return true; | 310 return true; |
236 } else { | 311 } else { |
237 LOG(ERROR) << "Invalid policy contents: " << path << ": " << error; | 312 LOG(ERROR) << "Invalid policy contents: " << path << ": " << error; |
238 return false; | 313 return false; |
239 } | 314 } |
240 } | 315 } |
241 | 316 |
242 namespace { | |
243 void CopyDictionaryValue(const base::DictionaryValue& from, | |
244 base::DictionaryValue& to, | |
245 std::string key) { | |
246 const base::Value* value; | |
247 if (from.Get(key, &value)) { | |
248 to.Set(key, value->CreateDeepCopy()); | |
249 } | |
250 } | |
251 } // namespace | |
252 | |
253 std::unique_ptr<base::DictionaryValue> | 317 std::unique_ptr<base::DictionaryValue> |
254 PolicyWatcher::StoreNewAndReturnChangedPolicies( | 318 PolicyWatcherImpl::StoreNewAndReturnChangedPolicies( |
255 std::unique_ptr<base::DictionaryValue> new_policies) { | 319 std::unique_ptr<base::DictionaryValue> new_policies) { |
256 // Find the changed policies. | 320 // Find the changed policies. |
257 std::unique_ptr<base::DictionaryValue> changed_policies( | 321 std::unique_ptr<base::DictionaryValue> changed_policies( |
258 new base::DictionaryValue()); | 322 new base::DictionaryValue()); |
259 base::DictionaryValue::Iterator iter(*new_policies); | 323 base::DictionaryValue::Iterator iter(*new_policies); |
260 while (!iter.IsAtEnd()) { | 324 while (!iter.IsAtEnd()) { |
261 base::Value* old_policy; | 325 base::Value* old_policy; |
262 if (!(old_policies_->Get(iter.key(), &old_policy) && | 326 if (!(old_policies_->Get(iter.key(), &old_policy) && |
263 old_policy->Equals(&iter.value()))) { | 327 old_policy->Equals(&iter.value()))) { |
264 changed_policies->Set(iter.key(), iter.value().CreateDeepCopy()); | 328 changed_policies->Set(iter.key(), iter.value().CreateDeepCopy()); |
(...skipping 13 matching lines...) Expand all Loading... |
278 CopyDictionaryValue(*new_policies, *changed_policies, | 342 CopyDictionaryValue(*new_policies, *changed_policies, |
279 key::kRemoteAccessHostTokenValidationCertificateIssuer); | 343 key::kRemoteAccessHostTokenValidationCertificateIssuer); |
280 } | 344 } |
281 | 345 |
282 // Save the new policies. | 346 // Save the new policies. |
283 old_policies_.swap(new_policies); | 347 old_policies_.swap(new_policies); |
284 | 348 |
285 return changed_policies; | 349 return changed_policies; |
286 } | 350 } |
287 | 351 |
288 void PolicyWatcher::OnPolicyUpdated(const policy::PolicyNamespace& ns, | 352 void PolicyWatcherImpl::OnPolicyUpdated(const policy::PolicyNamespace& ns, |
289 const policy::PolicyMap& previous, | 353 const policy::PolicyMap& previous, |
290 const policy::PolicyMap& current) { | 354 const policy::PolicyMap& current) { |
291 std::unique_ptr<base::DictionaryValue> new_policies = | 355 std::unique_ptr<base::DictionaryValue> new_policies = |
292 CopyChromotingPoliciesIntoDictionary(current); | 356 CopyChromotingPoliciesIntoDictionary(current); |
293 | 357 |
294 // Check for mistyped values and get rid of unknown policies. | 358 // Check for mistyped values and get rid of unknown policies. |
295 if (!NormalizePolicies(new_policies.get())) { | 359 if (!NormalizePolicies(new_policies.get())) { |
296 SignalPolicyError(); | 360 SignalPolicyError(); |
297 return; | 361 return; |
298 } | 362 } |
299 | 363 |
300 // Use default values for any missing policies. | 364 // Use default values for any missing policies. |
(...skipping 10 matching lines...) Expand all Loading... |
311 // Verify that we are calling the callback with valid policies. | 375 // Verify that we are calling the callback with valid policies. |
312 if (!VerifyWellformedness(*changed_policies)) { | 376 if (!VerifyWellformedness(*changed_policies)) { |
313 SignalPolicyError(); | 377 SignalPolicyError(); |
314 return; | 378 return; |
315 } | 379 } |
316 | 380 |
317 // Notify our client of the changed policies. | 381 // Notify our client of the changed policies. |
318 policy_updated_callback_.Run(std::move(changed_policies)); | 382 policy_updated_callback_.Run(std::move(changed_policies)); |
319 } | 383 } |
320 | 384 |
321 void PolicyWatcher::OnPolicyServiceInitialized(policy::PolicyDomain domain) { | 385 void PolicyWatcherImpl::OnPolicyServiceInitialized( |
| 386 policy::PolicyDomain domain) { |
322 policy::PolicyNamespace ns = GetPolicyNamespace(); | 387 policy::PolicyNamespace ns = GetPolicyNamespace(); |
323 const policy::PolicyMap& current = policy_service_->GetPolicies(ns); | 388 const policy::PolicyMap& current = policy_service_->GetPolicies(ns); |
324 OnPolicyUpdated(ns, current, current); | 389 OnPolicyUpdated(ns, current, current); |
325 } | 390 } |
326 | 391 |
| 392 } // namespace |
| 393 |
| 394 PolicyWatcher::PolicyWatcher() {} |
| 395 PolicyWatcher::~PolicyWatcher() {} |
| 396 |
327 std::unique_ptr<PolicyWatcher> PolicyWatcher::CreateFromPolicyLoader( | 397 std::unique_ptr<PolicyWatcher> PolicyWatcher::CreateFromPolicyLoader( |
328 std::unique_ptr<policy::AsyncPolicyLoader> async_policy_loader) { | 398 std::unique_ptr<policy::AsyncPolicyLoader> async_policy_loader) { |
329 std::unique_ptr<policy::SchemaRegistry> schema_registry = | 399 std::unique_ptr<policy::SchemaRegistry> schema_registry = |
330 CreateSchemaRegistry(); | 400 CreateSchemaRegistry(); |
331 std::unique_ptr<policy::AsyncPolicyProvider> policy_provider( | 401 std::unique_ptr<policy::AsyncPolicyProvider> policy_provider( |
332 new policy::AsyncPolicyProvider(schema_registry.get(), | 402 new policy::AsyncPolicyProvider(schema_registry.get(), |
333 std::move(async_policy_loader))); | 403 std::move(async_policy_loader))); |
334 policy_provider->Init(schema_registry.get()); | 404 policy_provider->Init(schema_registry.get()); |
335 | 405 |
336 policy::PolicyServiceImpl::Providers providers; | 406 policy::PolicyServiceImpl::Providers providers; |
337 providers.push_back(policy_provider.get()); | 407 providers.push_back(policy_provider.get()); |
338 std::unique_ptr<policy::PolicyService> policy_service( | 408 std::unique_ptr<policy::PolicyService> policy_service( |
339 new policy::PolicyServiceImpl(providers)); | 409 new policy::PolicyServiceImpl(providers)); |
340 | 410 |
341 policy::PolicyService* borrowed_policy_service = policy_service.get(); | 411 policy::PolicyService* borrowed_policy_service = policy_service.get(); |
342 return base::WrapUnique(new PolicyWatcher( | 412 return base::WrapUnique(new PolicyWatcherImpl( |
343 borrowed_policy_service, std::move(policy_service), | 413 borrowed_policy_service, std::move(policy_service), |
344 std::move(policy_provider), std::move(schema_registry))); | 414 std::move(policy_provider), std::move(schema_registry))); |
345 } | 415 } |
346 | 416 |
347 std::unique_ptr<PolicyWatcher> PolicyWatcher::Create( | 417 std::unique_ptr<PolicyWatcher> PolicyWatcher::Create( |
348 policy::PolicyService* policy_service, | 418 policy::PolicyService* policy_service, |
349 const scoped_refptr<base::SingleThreadTaskRunner>& file_task_runner) { | 419 const scoped_refptr<base::SingleThreadTaskRunner>& file_task_runner) { |
350 #if defined(OS_CHROMEOS) | 420 #if defined(OS_CHROMEOS) |
351 // On Chrome OS the PolicyService is owned by the browser. | 421 // On Chrome OS the PolicyService is owned by the browser. |
352 DCHECK(policy_service); | 422 DCHECK(policy_service); |
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
384 CreateSchemaRegistry())); | 454 CreateSchemaRegistry())); |
385 #else | 455 #else |
386 #error OS that is not yet supported by PolicyWatcher code. | 456 #error OS that is not yet supported by PolicyWatcher code. |
387 #endif | 457 #endif |
388 | 458 |
389 return PolicyWatcher::CreateFromPolicyLoader(std::move(policy_loader)); | 459 return PolicyWatcher::CreateFromPolicyLoader(std::move(policy_loader)); |
390 #endif // !(OS_CHROMEOS) | 460 #endif // !(OS_CHROMEOS) |
391 } | 461 } |
392 | 462 |
393 } // namespace remoting | 463 } // namespace remoting |
OLD | NEW |