enrollment_handler_chromeos.h revision 8bcbed890bc3ce4d7a057a8f32cab53fa534672e
15d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved. 25d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// found in the LICENSE file. 45d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 55d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#ifndef CHROME_BROWSER_CHROMEOS_POLICY_ENROLLMENT_HANDLER_CHROMEOS_H_ 65d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#define CHROME_BROWSER_CHROMEOS_POLICY_ENROLLMENT_HANDLER_CHROMEOS_H_ 75d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 85d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include <string> 95d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 105d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "base/basictypes.h" 115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "base/compiler_specific.h" 125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "base/memory/ref_counted.h" 135d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "base/memory/scoped_ptr.h" 145d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "base/memory/weak_ptr.h" 155d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "chrome/browser/chromeos/policy/device_cloud_policy_manager_chromeos.h" 165d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "chrome/browser/chromeos/policy/device_cloud_policy_validator.h" 175d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "chrome/browser/chromeos/policy/enterprise_install_attributes.h" 185d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "chrome/browser/policy/cloud/cloud_policy_client.h" 195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "chrome/browser/policy/cloud/cloud_policy_store.h" 205d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "google_apis/gaia/gaia_oauth_client.h" 215d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 225d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)namespace base { 235d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)class SequencedTaskRunner; 245d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 255d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 265d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)namespace enterprise_management { 275d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)class PolicyFetchResponse; 285d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} 295d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 305d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)namespace policy { 315d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 325d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// Implements the logic that establishes enterprise enrollment for Chromium OS 335d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// devices. The process is as follows: 345d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// 1. Given an auth token, register with the policy service. 355d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// 2. Download the initial policy blob from the service. 365d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// 3. Verify the policy blob. Everything up to this point doesn't touch device 375d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// state. 385d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// 4. Download the OAuth2 authorization code for device-level API access. 395d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// 5. Download the OAuth2 refresh token for device-level API access and store 405d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// it. 415d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// 6. Establish the device lock in installation-time attributes. 425d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// 7. Store the policy blob and API refresh token. 435d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)class EnrollmentHandlerChromeOS : public CloudPolicyClient::Observer, 445d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) public CloudPolicyStore::Observer, 455d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) public gaia::GaiaOAuthClient::Delegate { 465d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) public: 475d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) typedef DeviceCloudPolicyManagerChromeOS::AllowedDeviceModes 485d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) AllowedDeviceModes; 495d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) typedef DeviceCloudPolicyManagerChromeOS::EnrollmentCallback 505d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) EnrollmentCallback; 515d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 525d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // |store| and |install_attributes| must remain valid for the life time of the 535d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // enrollment handler. |allowed_device_modes| determines what device modes 545d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // are acceptable. If the mode specified by the server is not acceptable, 555d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // enrollment will fail with an EnrollmentStatus indicating 565d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // STATUS_REGISTRATION_BAD_MODE. 575d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) EnrollmentHandlerChromeOS( 585d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DeviceCloudPolicyStoreChromeOS* store, 595d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) EnterpriseInstallAttributes* install_attributes, 605d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) scoped_ptr<CloudPolicyClient> client, 615d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) scoped_refptr<base::SequencedTaskRunner> background_task_runner, 625d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const std::string& auth_token, 635d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const std::string& client_id, 645d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) bool is_auto_enrollment, 655d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const std::string& requisition, 665d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const AllowedDeviceModes& allowed_device_modes, 675d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const EnrollmentCallback& completion_callback); 685d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual ~EnrollmentHandlerChromeOS(); 695d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 705d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Starts the enrollment process and reports the result to 715d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // |completion_callback_|. 725d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void StartEnrollment(); 735d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 745d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Releases the client. 755d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) scoped_ptr<CloudPolicyClient> ReleaseClient(); 765d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 775d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // CloudPolicyClient::Observer: 785d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void OnPolicyFetched(CloudPolicyClient* client) OVERRIDE; 795d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void OnRegistrationStateChanged(CloudPolicyClient* client) OVERRIDE; 805d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void OnRobotAuthCodesFetched(CloudPolicyClient* client) OVERRIDE; 815d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void OnClientError(CloudPolicyClient* client) OVERRIDE; 825d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 835d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // CloudPolicyStore::Observer: 845d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void OnStoreLoaded(CloudPolicyStore* store) OVERRIDE; 855d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void OnStoreError(CloudPolicyStore* store) OVERRIDE; 865d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 875d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // GaiaOAuthClient::Delegate: 885d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void OnGetTokensResponse(const std::string& refresh_token, 895d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const std::string& access_token, 905d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) int expires_in_seconds) OVERRIDE; 915d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void OnRefreshTokenResponse(const std::string& access_token, 925d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) int expires_in_seconds) OVERRIDE; 935d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void OnOAuthError() OVERRIDE; 945d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) virtual void OnNetworkError(int response_code) OVERRIDE; 955d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 965d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) private: 975d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Indicates what step of the process is currently pending. These steps need 985d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // to be listed in the order they are traversed in. 995d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) enum EnrollmentStep { 1005d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) STEP_PENDING, // Not started yet. 1015d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) STEP_LOADING_STORE, // Waiting for |store_| to initialize. 1025d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) STEP_REGISTRATION, // Currently registering the client. 1035d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) STEP_POLICY_FETCH, // Fetching policy. 1045d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) STEP_VALIDATION, // Policy validation. 1055d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) STEP_ROBOT_AUTH_FETCH, // Fetching device API auth code. 1065d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) STEP_ROBOT_AUTH_REFRESH, // Fetching device API refresh token. 1075d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) STEP_LOCK_DEVICE, // Writing installation-time attributes. 1085d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) STEP_STORE_POLICY, // Storing policy and API refresh token. 1095d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) STEP_FINISHED, // Enrollment process finished, no further action. 1105d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) }; 1115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1125d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Starts registration if the store is initialized. 1135d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void AttemptRegistration(); 1145d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1155d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Handles the policy validation result, proceeding with installation-time 1165d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // attributes locking if successful. 1175d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void PolicyValidated(DeviceCloudPolicyValidator* validator); 1185d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Method called to initiate the STEP_LOCK_DEVICE step. Usually called after 1205d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // the STEP_ROBOT_AUTH_REFRESH, but may be called directly after a failed 1215d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // STEP_ROBOT_AUTH_FETCH, since robot tokens are currently optional. 1225d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void DoLockDeviceStep(); 1235d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1245d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Calls LockDevice() and proceeds to policy installation. If unsuccessful, 1255d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // reports the result. Actual installation or error report will be done in 1265d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // HandleLockDeviceResult(). 1275d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void StartLockDevice(const std::string& user, 1285d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DeviceMode device_mode, 1295d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const std::string& device_id); 1305d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1315d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Helper for StartLockDevice(). It performs the actual action based on 1325d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // the result of LockDevice. 1335d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void HandleLockDeviceResult( 1345d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const std::string& user, 1355d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DeviceMode device_mode, 1365d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) const std::string& device_id, 1375d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) EnterpriseInstallAttributes::LockResult lock_result); 1385d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1395d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Drops any ongoing actions. 1405d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void Stop(); 1415d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1425d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Reports the result of the enrollment process to the initiator. 1435d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) void ReportResult(EnrollmentStatus status); 1445d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1455d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DeviceCloudPolicyStoreChromeOS* store_; 1465d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) EnterpriseInstallAttributes* install_attributes_; 1475d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) scoped_ptr<CloudPolicyClient> client_; 1485d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) scoped_refptr<base::SequencedTaskRunner> background_task_runner_; 1495d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) scoped_ptr<gaia::GaiaOAuthClient> gaia_oauth_client_; 1505d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1515d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) std::string auth_token_; 1525d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) std::string client_id_; 1535d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) std::string robot_refresh_token_; 1545d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) bool is_auto_enrollment_; 1555d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) std::string requisition_; 1565d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) AllowedDeviceModes allowed_device_modes_; 1575d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) EnrollmentCallback completion_callback_; 1585d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1595d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // The device mode as received in the registration request. 1605d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DeviceMode device_mode_; 1615d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1625d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // The validated policy response info to be installed in the store. 1635d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) scoped_ptr<enterprise_management::PolicyFetchResponse> policy_; 1645d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) std::string username_; 1655d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) std::string device_id_; 1665d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1675d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Current enrollment step. 1685d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) EnrollmentStep enrollment_step_; 1695d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1705d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // Total amount of time in milliseconds spent waiting for lockbox 1715d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) // initialization. 1725d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) int lockbox_init_duration_; 1735d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1745d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) base::WeakPtrFactory<EnrollmentHandlerChromeOS> weak_factory_; 1755d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1765d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(EnrollmentHandlerChromeOS); 1775d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)}; 1785d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1795d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)} // namespace policy 1805d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) 1815d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#endif // CHROME_BROWSER_CHROMEOS_POLICY_ENROLLMENT_HANDLER_CHROMEOS_H_ 1825d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)