Update To 11.40.268.0
[platform/framework/web/crosswalk.git] / src / chrome / browser / chromeos / policy / consumer_management_service.cc
1 // Copyright 2014 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 "chrome/browser/chromeos/policy/consumer_management_service.h"
6
7 #include "base/bind.h"
8 #include "base/callback.h"
9 #include "base/logging.h"
10 #include "base/prefs/pref_registry_simple.h"
11 #include "base/prefs/pref_service.h"
12 #include "chrome/browser/browser_process.h"
13 #include "chrome/common/pref_names.h"
14 #include "chromeos/dbus/cryptohome/rpc.pb.h"
15 #include "chromeos/dbus/cryptohome_client.h"
16 #include "policy/proto/device_management_backend.pb.h"
17
18 namespace em = enterprise_management;
19
20 namespace {
21
22 // Boot atttributes ID.
23 const char kAttributeOwnerId[] = "consumer_management.owner_id";
24
25 // The string of Status enum.
26 const char* const kStatusString[] = {
27   "StatusUnknown",
28   "StatusEnrolled",
29   "StatusEnrolling",
30   "StatusUnenrolled",
31   "StatusUnenrolling",
32 };
33
34 COMPILE_ASSERT(
35     arraysize(kStatusString) == policy::ConsumerManagementService::STATUS_LAST,
36     "invalid kStatusString array size.");
37
38 }  // namespace
39
40 namespace policy {
41
42 ConsumerManagementService::ConsumerManagementService(
43     chromeos::CryptohomeClient* client,
44     chromeos::DeviceSettingsService* device_settings_service)
45     : client_(client),
46       device_settings_service_(device_settings_service),
47       weak_ptr_factory_(this) {
48   // A NULL value may be passed in tests.
49   if (device_settings_service_)
50     device_settings_service_->AddObserver(this);
51 }
52
53 ConsumerManagementService::~ConsumerManagementService() {
54   if (device_settings_service_)
55     device_settings_service_->RemoveObserver(this);
56 }
57
58 // static
59 void ConsumerManagementService::RegisterPrefs(PrefRegistrySimple* registry) {
60   registry->RegisterIntegerPref(
61       prefs::kConsumerManagementEnrollmentStage, ENROLLMENT_STAGE_NONE);
62 }
63
64 void ConsumerManagementService::AddObserver(Observer* observer) {
65   observers_.AddObserver(observer);
66 }
67
68 void ConsumerManagementService::RemoveObserver(Observer* observer) {
69   observers_.RemoveObserver(observer);
70 }
71
72 ConsumerManagementService::Status
73 ConsumerManagementService::GetStatus() const {
74   if (!device_settings_service_)
75     return STATUS_UNKNOWN;
76
77   const em::PolicyData* policy_data = device_settings_service_->policy_data();
78   if (!policy_data)
79     return STATUS_UNKNOWN;
80
81   if (policy_data->management_mode() == em::PolicyData::CONSUMER_MANAGED) {
82     // TODO(davidyu): Check if unenrollment is in progress.
83     // http://crbug.com/353050.
84     return STATUS_ENROLLED;
85   }
86
87   EnrollmentStage stage = GetEnrollmentStage();
88   if (stage > ENROLLMENT_STAGE_NONE && stage < ENROLLMENT_STAGE_SUCCESS)
89     return STATUS_ENROLLING;
90
91   return STATUS_UNENROLLED;
92 }
93
94 std::string ConsumerManagementService::GetStatusString() const {
95   return kStatusString[GetStatus()];
96 }
97
98 bool ConsumerManagementService::HasPendingEnrollmentNotification() const {
99   EnrollmentStage stage = GetEnrollmentStage();
100   return stage >= ENROLLMENT_STAGE_SUCCESS && stage < ENROLLMENT_STAGE_LAST;
101 }
102
103 ConsumerManagementService::EnrollmentStage
104 ConsumerManagementService::GetEnrollmentStage() const {
105   const PrefService* prefs = g_browser_process->local_state();
106   int stage = prefs->GetInteger(prefs::kConsumerManagementEnrollmentStage);
107   if (stage < 0 || stage >= ENROLLMENT_STAGE_LAST) {
108     LOG(ERROR) << "Unknown enrollment stage: " << stage;
109     stage = 0;
110   }
111   return static_cast<EnrollmentStage>(stage);
112 }
113
114 void ConsumerManagementService::SetEnrollmentStage(EnrollmentStage stage) {
115   PrefService* prefs = g_browser_process->local_state();
116   prefs->SetInteger(prefs::kConsumerManagementEnrollmentStage, stage);
117
118   NotifyStatusChanged();
119 }
120
121 void ConsumerManagementService::GetOwner(const GetOwnerCallback& callback) {
122   cryptohome::GetBootAttributeRequest request;
123   request.set_name(kAttributeOwnerId);
124   client_->GetBootAttribute(
125       request,
126       base::Bind(&ConsumerManagementService::OnGetBootAttributeDone,
127                  weak_ptr_factory_.GetWeakPtr(),
128                  callback));
129 }
130
131 void ConsumerManagementService::SetOwner(const std::string& user_id,
132                                          const SetOwnerCallback& callback) {
133   cryptohome::SetBootAttributeRequest request;
134   request.set_name(kAttributeOwnerId);
135   request.set_value(user_id.data(), user_id.size());
136   client_->SetBootAttribute(
137       request,
138       base::Bind(&ConsumerManagementService::OnSetBootAttributeDone,
139                  weak_ptr_factory_.GetWeakPtr(),
140                  callback));
141 }
142
143 void ConsumerManagementService::OwnershipStatusChanged() {
144 }
145
146 void ConsumerManagementService::DeviceSettingsUpdated() {
147   NotifyStatusChanged();
148 }
149
150 void ConsumerManagementService::OnDeviceSettingsServiceShutdown() {
151   device_settings_service_ = nullptr;
152 }
153
154 void ConsumerManagementService::OnGetBootAttributeDone(
155     const GetOwnerCallback& callback,
156     chromeos::DBusMethodCallStatus call_status,
157     bool dbus_success,
158     const cryptohome::BaseReply& reply) {
159   if (!dbus_success || reply.error() != 0) {
160     LOG(ERROR) << "Failed to get the owner info from boot lockbox.";
161     callback.Run("");
162     return;
163   }
164
165   callback.Run(
166       reply.GetExtension(cryptohome::GetBootAttributeReply::reply).value());
167 }
168
169 void ConsumerManagementService::OnSetBootAttributeDone(
170     const SetOwnerCallback& callback,
171     chromeos::DBusMethodCallStatus call_status,
172     bool dbus_success,
173     const cryptohome::BaseReply& reply) {
174   if (!dbus_success || reply.error() != 0) {
175     LOG(ERROR) << "Failed to set owner info in boot lockbox.";
176     callback.Run(false);
177     return;
178   }
179
180   cryptohome::FlushAndSignBootAttributesRequest request;
181   client_->FlushAndSignBootAttributes(
182       request,
183       base::Bind(&ConsumerManagementService::OnFlushAndSignBootAttributesDone,
184                  weak_ptr_factory_.GetWeakPtr(),
185                  callback));
186 }
187
188 void ConsumerManagementService::OnFlushAndSignBootAttributesDone(
189     const SetOwnerCallback& callback,
190     chromeos::DBusMethodCallStatus call_status,
191     bool dbus_success,
192     const cryptohome::BaseReply& reply) {
193   if (!dbus_success || reply.error() != 0) {
194     LOG(ERROR) << "Failed to flush and sign boot lockbox.";
195     callback.Run(false);
196     return;
197   }
198
199   callback.Run(true);
200 }
201
202 void ConsumerManagementService::NotifyStatusChanged() {
203   FOR_EACH_OBSERVER(Observer, observers_, OnConsumerManagementStatusChanged());
204 }
205
206 }  // namespace policy