OLD | NEW |
| (Empty) |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | |
2 // Use of this source code is governed by a BSD-style license that can be | |
3 // found in the LICENSE file. | |
4 | |
5 #include "components/policy/core/common/policy_loader_mac.h" | |
6 | |
7 #include "base/bind.h" | |
8 #include "base/bind_helpers.h" | |
9 #include "base/callback.h" | |
10 #include "base/files/file_util.h" | |
11 #include "base/mac/foundation_util.h" | |
12 #include "base/mac/scoped_cftyperef.h" | |
13 #include "base/sequenced_task_runner.h" | |
14 #include "base/strings/sys_string_conversions.h" | |
15 #include "base/values.h" | |
16 #include "components/policy/core/common/external_data_fetcher.h" | |
17 #include "components/policy/core/common/mac_util.h" | |
18 #include "components/policy/core/common/policy_bundle.h" | |
19 #include "components/policy/core/common/policy_load_status.h" | |
20 #include "components/policy/core/common/policy_map.h" | |
21 #include "components/policy/core/common/preferences_mac.h" | |
22 #include "components/policy/core/common/schema.h" | |
23 #include "components/policy/core/common/schema_map.h" | |
24 | |
25 using base::ScopedCFTypeRef; | |
26 | |
27 namespace policy { | |
28 | |
29 PolicyLoaderMac::PolicyLoaderMac( | |
30 scoped_refptr<base::SequencedTaskRunner> task_runner, | |
31 const base::FilePath& managed_policy_path, | |
32 MacPreferences* preferences) | |
33 : AsyncPolicyLoader(task_runner), | |
34 preferences_(preferences), | |
35 managed_policy_path_(managed_policy_path) {} | |
36 | |
37 PolicyLoaderMac::~PolicyLoaderMac() {} | |
38 | |
39 void PolicyLoaderMac::InitOnBackgroundThread() { | |
40 if (!managed_policy_path_.empty()) { | |
41 watcher_.Watch( | |
42 managed_policy_path_, false, | |
43 base::Bind(&PolicyLoaderMac::OnFileUpdated, base::Unretained(this))); | |
44 } | |
45 } | |
46 | |
47 scoped_ptr<PolicyBundle> PolicyLoaderMac::Load() { | |
48 preferences_->AppSynchronize(kCFPreferencesCurrentApplication); | |
49 scoped_ptr<PolicyBundle> bundle(new PolicyBundle()); | |
50 | |
51 // Load Chrome's policy. | |
52 PolicyMap& chrome_policy = | |
53 bundle->Get(PolicyNamespace(POLICY_DOMAIN_CHROME, std::string())); | |
54 | |
55 PolicyLoadStatusSample status; | |
56 bool policy_present = false; | |
57 const Schema* schema = | |
58 schema_map()->GetSchema(PolicyNamespace(POLICY_DOMAIN_CHROME, "")); | |
59 for (Schema::Iterator it = schema->GetPropertiesIterator(); | |
60 !it.IsAtEnd(); it.Advance()) { | |
61 base::ScopedCFTypeRef<CFStringRef> name( | |
62 base::SysUTF8ToCFStringRef(it.key())); | |
63 base::ScopedCFTypeRef<CFPropertyListRef> value( | |
64 preferences_->CopyAppValue(name, kCFPreferencesCurrentApplication)); | |
65 if (!value.get()) | |
66 continue; | |
67 policy_present = true; | |
68 bool forced = | |
69 preferences_->AppValueIsForced(name, kCFPreferencesCurrentApplication); | |
70 PolicyLevel level = forced ? POLICY_LEVEL_MANDATORY : | |
71 POLICY_LEVEL_RECOMMENDED; | |
72 // TODO(joaodasilva): figure the policy scope. | |
73 scoped_ptr<base::Value> policy = PropertyToValue(value); | |
74 if (policy) { | |
75 chrome_policy.Set( | |
76 it.key(), level, POLICY_SCOPE_USER, policy.release(), NULL); | |
77 } else { | |
78 status.Add(POLICY_LOAD_STATUS_PARSE_ERROR); | |
79 } | |
80 } | |
81 | |
82 if (!policy_present) | |
83 status.Add(POLICY_LOAD_STATUS_NO_POLICY); | |
84 | |
85 // Load policy for the registered components. | |
86 LoadPolicyForDomain(POLICY_DOMAIN_EXTENSIONS, "extensions", bundle.get()); | |
87 | |
88 return bundle.Pass(); | |
89 } | |
90 | |
91 base::Time PolicyLoaderMac::LastModificationTime() { | |
92 base::File::Info file_info; | |
93 if (!base::GetFileInfo(managed_policy_path_, &file_info) || | |
94 file_info.is_directory) { | |
95 return base::Time(); | |
96 } | |
97 | |
98 return file_info.last_modified; | |
99 } | |
100 | |
101 void PolicyLoaderMac::LoadPolicyForDomain( | |
102 PolicyDomain domain, | |
103 const std::string& domain_name, | |
104 PolicyBundle* bundle) { | |
105 std::string id_prefix(base::mac::BaseBundleID()); | |
106 id_prefix.append(".").append(domain_name).append("."); | |
107 | |
108 const ComponentMap* components = schema_map()->GetComponents(domain); | |
109 if (!components) | |
110 return; | |
111 | |
112 for (ComponentMap::const_iterator it = components->begin(); | |
113 it != components->end(); ++it) { | |
114 PolicyMap policy; | |
115 LoadPolicyForComponent(id_prefix + it->first, it->second, &policy); | |
116 if (!policy.empty()) | |
117 bundle->Get(PolicyNamespace(domain, it->first)).Swap(&policy); | |
118 } | |
119 } | |
120 | |
121 void PolicyLoaderMac::LoadPolicyForComponent( | |
122 const std::string& bundle_id_string, | |
123 const Schema& schema, | |
124 PolicyMap* policy) { | |
125 // TODO(joaodasilva): Extensions may be registered in a ComponentMap | |
126 // without a schema, to allow a graceful update of the Legacy Browser Support | |
127 // extension on Windows. Remove this check once that support is removed. | |
128 if (!schema.valid()) | |
129 return; | |
130 | |
131 base::ScopedCFTypeRef<CFStringRef> bundle_id( | |
132 base::SysUTF8ToCFStringRef(bundle_id_string)); | |
133 preferences_->AppSynchronize(bundle_id); | |
134 | |
135 for (Schema::Iterator it = schema.GetPropertiesIterator(); | |
136 !it.IsAtEnd(); it.Advance()) { | |
137 base::ScopedCFTypeRef<CFStringRef> pref_name( | |
138 base::SysUTF8ToCFStringRef(it.key())); | |
139 base::ScopedCFTypeRef<CFPropertyListRef> value( | |
140 preferences_->CopyAppValue(pref_name, bundle_id)); | |
141 if (!value.get()) | |
142 continue; | |
143 bool forced = | |
144 preferences_->AppValueIsForced(pref_name, bundle_id); | |
145 PolicyLevel level = forced ? POLICY_LEVEL_MANDATORY : | |
146 POLICY_LEVEL_RECOMMENDED; | |
147 scoped_ptr<base::Value> policy_value = PropertyToValue(value); | |
148 if (policy_value) { | |
149 policy->Set(it.key(), level, POLICY_SCOPE_USER, | |
150 policy_value.release(), NULL); | |
151 } | |
152 } | |
153 } | |
154 | |
155 void PolicyLoaderMac::OnFileUpdated(const base::FilePath& path, bool error) { | |
156 if (!error) | |
157 Reload(false); | |
158 } | |
159 | |
160 } // namespace policy | |
OLD | NEW |