1 // Copyright (c) 2013 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/ui/webui/chromeos/login/signin_screen_handler.h" 6 7 #include "base/callback.h" 8 #include "base/chromeos/chromeos_version.h" 9 #include "base/command_line.h" 10 #include "base/debug/trace_event.h" 11 #include "base/logging.h" 12 #include "base/memory/scoped_ptr.h" 13 #include "base/metrics/histogram.h" 14 #include "base/prefs/pref_registry_simple.h" 15 #include "base/prefs/pref_service.h" 16 #include "base/strings/string16.h" 17 #include "base/strings/string_util.h" 18 #include "base/strings/stringprintf.h" 19 #include "base/strings/utf_string_conversions.h" 20 #include "chrome/browser/browser_process.h" 21 #include "chrome/browser/browser_process_platform_part_chromeos.h" 22 #include "chrome/browser/browser_shutdown.h" 23 #include "chrome/browser/chrome_notification_types.h" 24 #include "chrome/browser/chromeos/app_mode/kiosk_app_manager.h" 25 #include "chrome/browser/chromeos/input_method/input_method_util.h" 26 #include "chrome/browser/chromeos/kiosk_mode/kiosk_mode_settings.h" 27 #include "chrome/browser/chromeos/login/hwid_checker.h" 28 #include "chrome/browser/chromeos/login/login_display_host_impl.h" 29 #include "chrome/browser/chromeos/login/screen_locker.h" 30 #include "chrome/browser/chromeos/login/screens/core_oobe_actor.h" 31 #include "chrome/browser/chromeos/login/user.h" 32 #include "chrome/browser/chromeos/login/webui_login_display.h" 33 #include "chrome/browser/chromeos/login/wizard_controller.h" 34 #include "chrome/browser/chromeos/net/network_portal_detector.h" 35 #include "chrome/browser/chromeos/profiles/profile_helper.h" 36 #include "chrome/browser/chromeos/settings/cros_settings.h" 37 #include "chrome/browser/io_thread.h" 38 #include "chrome/browser/policy/browser_policy_connector.h" 39 #include "chrome/browser/prefs/scoped_user_pref_update.h" 40 #include "chrome/browser/profiles/profile.h" 41 #include "chrome/browser/ui/webui/chromeos/login/error_screen_handler.h" 42 #include "chrome/browser/ui/webui/chromeos/login/native_window_delegate.h" 43 #include "chrome/browser/ui/webui/chromeos/login/network_state_informer.h" 44 #include "chrome/browser/ui/webui/chromeos/login/oobe_ui.h" 45 #include "chrome/common/chrome_switches.h" 46 #include "chrome/common/pref_names.h" 47 #include "chrome/common/url_constants.h" 48 #include "chromeos/chromeos_switches.h" 49 #include "chromeos/dbus/dbus_thread_manager.h" 50 #include "chromeos/dbus/power_manager_client.h" 51 #include "chromeos/ime/input_method_manager.h" 52 #include "chromeos/ime/xkeyboard.h" 53 #include "chromeos/network/network_state.h" 54 #include "chromeos/network/network_state_handler.h" 55 #include "content/public/browser/render_view_host.h" 56 #include "content/public/browser/web_contents.h" 57 #include "google_apis/gaia/gaia_auth_util.h" 58 #include "google_apis/gaia/gaia_switches.h" 59 #include "google_apis/gaia/gaia_urls.h" 60 #include "grit/chromium_strings.h" 61 #include "grit/generated_resources.h" 62 #include "third_party/cros_system_api/dbus/service_constants.h" 63 #include "ui/base/l10n/l10n_util.h" 64 65 #if defined(USE_AURA) 66 #include "ash/shell.h" 67 #include "ash/wm/lock_state_controller.h" 68 #endif 69 70 using content::BrowserThread; 71 using content::RenderViewHost; 72 73 namespace { 74 75 // User dictionary keys. 76 const char kKeyUsername[] = "username"; 77 const char kKeyDisplayName[] = "displayName"; 78 const char kKeyEmailAddress[] = "emailAddress"; 79 const char kKeyEnterpriseDomain[] = "enterpriseDomain"; 80 const char kKeyPublicAccount[] = "publicAccount"; 81 const char kKeyLocallyManagedUser[] = "locallyManagedUser"; 82 const char kKeySignedIn[] = "signedIn"; 83 const char kKeyCanRemove[] = "canRemove"; 84 const char kKeyIsOwner[] = "isOwner"; 85 const char kKeyOauthTokenStatus[] = "oauthTokenStatus"; 86 87 // Max number of users to show. 88 const size_t kMaxUsers = 18; 89 90 // Timeout to delay first notification about offline state for a 91 // current network. 92 const int kOfflineTimeoutSec = 5; 93 94 // Timeout used to prevent infinite connecting to a flaky network. 95 const int kConnectingTimeoutSec = 60; 96 97 // Type of the login screen UI that is currently presented to user. 98 const char kSourceGaiaSignin[] = "gaia-signin"; 99 const char kSourceAccountPicker[] = "account-picker"; 100 101 // The Task posted to PostTaskAndReply in StartClearingDnsCache on the IO 102 // thread. 103 void ClearDnsCache(IOThread* io_thread) { 104 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); 105 if (browser_shutdown::IsTryingToQuit()) 106 return; 107 108 io_thread->ClearHostCache(); 109 } 110 111 static bool Contains(const std::vector<std::string>& container, 112 const std::string& value) { 113 return std::find(container.begin(), container.end(), value) != 114 container.end(); 115 } 116 117 } // namespace 118 119 namespace chromeos { 120 121 namespace { 122 123 const char kNetworkStateOffline[] = "offline"; 124 const char kNetworkStateOnline[] = "online"; 125 const char kNetworkStateCaptivePortal[] = "behind captive portal"; 126 const char kNetworkStateConnecting[] = "connecting"; 127 const char kNetworkStateProxyAuthRequired[] = "proxy auth required"; 128 129 const char kErrorReasonProxyAuthCancelled[] = "proxy auth cancelled"; 130 const char kErrorReasonProxyAuthSupplied[] = "proxy auth supplied"; 131 const char kErrorReasonProxyConnectionFailed[] = "proxy connection failed"; 132 const char kErrorReasonProxyConfigChanged[] = "proxy config changed"; 133 const char kErrorReasonLoadingTimeout[] = "loading timeout"; 134 const char kErrorReasonPortalDetected[] = "portal detected"; 135 const char kErrorReasonNetworkStateChanged[] = "network state changed"; 136 const char kErrorReasonUpdate[] = "update"; 137 const char kErrorReasonFrameError[] = "frame error"; 138 139 const char* NetworkStateStatusString(NetworkStateInformer::State state) { 140 switch (state) { 141 case NetworkStateInformer::OFFLINE: 142 return kNetworkStateOffline; 143 case NetworkStateInformer::ONLINE: 144 return kNetworkStateOnline; 145 case NetworkStateInformer::CAPTIVE_PORTAL: 146 return kNetworkStateCaptivePortal; 147 case NetworkStateInformer::CONNECTING: 148 return kNetworkStateConnecting; 149 case NetworkStateInformer::PROXY_AUTH_REQUIRED: 150 return kNetworkStateProxyAuthRequired; 151 default: 152 NOTREACHED(); 153 return NULL; 154 } 155 } 156 157 const char* ErrorReasonString(ErrorScreenActor::ErrorReason reason) { 158 switch (reason) { 159 case ErrorScreenActor::ERROR_REASON_PROXY_AUTH_CANCELLED: 160 return kErrorReasonProxyAuthCancelled; 161 case ErrorScreenActor::ERROR_REASON_PROXY_AUTH_SUPPLIED: 162 return kErrorReasonProxyAuthSupplied; 163 case ErrorScreenActor::ERROR_REASON_PROXY_CONNECTION_FAILED: 164 return kErrorReasonProxyConnectionFailed; 165 case ErrorScreenActor::ERROR_REASON_PROXY_CONFIG_CHANGED: 166 return kErrorReasonProxyConfigChanged; 167 case ErrorScreenActor::ERROR_REASON_LOADING_TIMEOUT: 168 return kErrorReasonLoadingTimeout; 169 case ErrorScreenActor::ERROR_REASON_PORTAL_DETECTED: 170 return kErrorReasonPortalDetected; 171 case ErrorScreenActor::ERROR_REASON_NETWORK_STATE_CHANGED: 172 return kErrorReasonNetworkStateChanged; 173 case ErrorScreenActor::ERROR_REASON_UPDATE: 174 return kErrorReasonUpdate; 175 case ErrorScreenActor::ERROR_REASON_FRAME_ERROR: 176 return kErrorReasonFrameError; 177 default: 178 NOTREACHED(); 179 return NULL; 180 } 181 } 182 183 // Updates params dictionary passed to the auth extension with related 184 // preferences from CrosSettings. 185 void UpdateAuthParamsFromSettings(DictionaryValue* params, 186 const CrosSettings* cros_settings) { 187 bool allow_new_user = true; 188 cros_settings->GetBoolean(kAccountsPrefAllowNewUser, &allow_new_user); 189 bool allow_guest = true; 190 cros_settings->GetBoolean(kAccountsPrefAllowGuest, &allow_guest); 191 // Account creation depends on Guest sign-in (http://crosbug.com/24570). 192 params->SetBoolean("createAccount", allow_new_user && allow_guest); 193 params->SetBoolean("guestSignin", allow_guest); 194 } 195 196 bool IsOnline(NetworkStateInformer::State state, 197 ErrorScreenActor::ErrorReason reason) { 198 return state == NetworkStateInformer::ONLINE && 199 reason != ErrorScreenActor::ERROR_REASON_PORTAL_DETECTED && 200 reason != ErrorScreenActor::ERROR_REASON_LOADING_TIMEOUT; 201 } 202 203 bool IsUnderCaptivePortal(NetworkStateInformer::State state, 204 ErrorScreenActor::ErrorReason reason) { 205 return state == NetworkStateInformer::CAPTIVE_PORTAL || 206 reason == ErrorScreenActor::ERROR_REASON_PORTAL_DETECTED; 207 } 208 209 bool IsProxyError(NetworkStateInformer::State state, 210 ErrorScreenActor::ErrorReason reason, 211 net::Error frame_error) { 212 return state == NetworkStateInformer::PROXY_AUTH_REQUIRED || 213 reason == ErrorScreenActor::ERROR_REASON_PROXY_AUTH_CANCELLED || 214 reason == ErrorScreenActor::ERROR_REASON_PROXY_CONNECTION_FAILED || 215 (reason == ErrorScreenActor::ERROR_REASON_FRAME_ERROR && 216 (frame_error == net::ERR_PROXY_CONNECTION_FAILED || 217 frame_error == net::ERR_TUNNEL_CONNECTION_FAILED)); 218 } 219 220 bool IsSigninScreen(const OobeUI::Screen screen) { 221 return screen == OobeUI::SCREEN_GAIA_SIGNIN || 222 screen == OobeUI::SCREEN_ACCOUNT_PICKER; 223 } 224 225 bool IsSigninScreenError(ErrorScreen::ErrorState error_state) { 226 return error_state == ErrorScreen::ERROR_STATE_PORTAL || 227 error_state == ErrorScreen::ERROR_STATE_OFFLINE || 228 error_state == ErrorScreen::ERROR_STATE_PROXY || 229 error_state == ErrorScreen::ERROR_STATE_AUTH_EXT_TIMEOUT; 230 } 231 232 // Returns network name by service path. 233 std::string GetNetworkName(const std::string& service_path) { 234 const NetworkState* network = NetworkHandler::Get()->network_state_handler()-> 235 GetNetworkState(service_path); 236 if (!network) 237 return std::string(); 238 return network->name(); 239 } 240 241 // Returns captive portal state for a network by its service path. 242 NetworkPortalDetector::CaptivePortalState GetCaptivePortalState( 243 const std::string& service_path) { 244 NetworkPortalDetector* detector = NetworkPortalDetector::GetInstance(); 245 const NetworkState* network = NetworkHandler::Get()->network_state_handler()-> 246 GetNetworkState(service_path); 247 if (!detector || !network) 248 return NetworkPortalDetector::CaptivePortalState(); 249 return detector->GetCaptivePortalState(network); 250 } 251 252 void RecordDiscrepancyWithShill( 253 const NetworkState* network, 254 const NetworkPortalDetector::CaptivePortalStatus status) { 255 if (network->connection_state() == flimflam::kStateOnline) { 256 UMA_HISTOGRAM_ENUMERATION( 257 "CaptivePortal.OOBE.DiscrepancyWithShill_Online", 258 status, 259 NetworkPortalDetector::CAPTIVE_PORTAL_STATUS_COUNT); 260 } else if (network->connection_state() == flimflam::kStatePortal) { 261 UMA_HISTOGRAM_ENUMERATION( 262 "CaptivePortal.OOBE.DiscrepancyWithShill_RestrictedPool", 263 status, 264 NetworkPortalDetector::CAPTIVE_PORTAL_STATUS_COUNT); 265 } else { 266 UMA_HISTOGRAM_ENUMERATION( 267 "CaptivePortal.OOBE.DiscrepancyWithShill_Offline", 268 status, 269 NetworkPortalDetector::CAPTIVE_PORTAL_STATUS_COUNT); 270 } 271 } 272 273 // Record state and descripancies with shill (e.g. shill thinks that 274 // network is online but NetworkPortalDetector claims that it's behind 275 // portal) for the network identified by |service_path|. 276 void RecordNetworkPortalDetectorStats(const std::string& service_path) { 277 const NetworkState* network = NetworkHandler::Get()->network_state_handler()-> 278 GetNetworkState(service_path); 279 if (!network) 280 return; 281 NetworkPortalDetector::CaptivePortalState state = 282 GetCaptivePortalState(service_path); 283 if (state.status == NetworkPortalDetector::CAPTIVE_PORTAL_STATUS_UNKNOWN) 284 return; 285 286 UMA_HISTOGRAM_ENUMERATION("CaptivePortal.OOBE.DetectionResult", 287 state.status, 288 NetworkPortalDetector::CAPTIVE_PORTAL_STATUS_COUNT); 289 290 switch (state.status) { 291 case NetworkPortalDetector::CAPTIVE_PORTAL_STATUS_UNKNOWN: 292 NOTREACHED(); 293 break; 294 case NetworkPortalDetector::CAPTIVE_PORTAL_STATUS_OFFLINE: 295 if (network->connection_state() == flimflam::kStateOnline || 296 network->connection_state() == flimflam::kStatePortal) 297 RecordDiscrepancyWithShill(network, state.status); 298 break; 299 case NetworkPortalDetector::CAPTIVE_PORTAL_STATUS_ONLINE: 300 if (network->connection_state() != flimflam::kStateOnline) 301 RecordDiscrepancyWithShill(network, state.status); 302 break; 303 case NetworkPortalDetector::CAPTIVE_PORTAL_STATUS_PORTAL: 304 if (network->connection_state() != flimflam::kStatePortal) 305 RecordDiscrepancyWithShill(network, state.status); 306 break; 307 case NetworkPortalDetector::CAPTIVE_PORTAL_STATUS_PROXY_AUTH_REQUIRED: 308 if (network->connection_state() != flimflam::kStateOnline) 309 RecordDiscrepancyWithShill(network, state.status); 310 break; 311 case NetworkPortalDetector::CAPTIVE_PORTAL_STATUS_COUNT: 312 NOTREACHED(); 313 break; 314 } 315 } 316 317 static bool SetUserInputMethodImpl( 318 const std::string& username, 319 chromeos::input_method::InputMethodManager* manager) { 320 PrefService* const local_state = g_browser_process->local_state(); 321 322 const base::DictionaryValue* users_lru_input_methods = 323 local_state->GetDictionary(prefs::kUsersLRUInputMethod); 324 325 if (users_lru_input_methods == NULL) { 326 DLOG(WARNING) << "SetUserInputMethod('" << username 327 << "'): no kUsersLRUInputMethod"; 328 return false; 329 } 330 331 std::string input_method; 332 333 if (!users_lru_input_methods->GetStringWithoutPathExpansion(username, 334 &input_method)) { 335 DLOG(INFO) << "SetUserInputMethod('" << username 336 << "'): no input method for this user"; 337 return false; 338 } 339 340 if (input_method.empty()) 341 return false; 342 343 if (!manager->IsFullLatinKeyboard(input_method)) { 344 LOG(WARNING) << "SetUserInputMethod('" << username 345 << "'): stored user LRU input method '" << input_method 346 << "' is no longer Full Latin Keyboard Language" 347 << " (entry dropped). Use hardware default instead."; 348 349 DictionaryPrefUpdate updater(local_state, prefs::kUsersLRUInputMethod); 350 351 base::DictionaryValue* const users_lru_input_methods = updater.Get(); 352 if (users_lru_input_methods != NULL) { 353 users_lru_input_methods->SetStringWithoutPathExpansion(username, ""); 354 } 355 return false; 356 } 357 358 if (!Contains(manager->GetActiveInputMethodIds(), input_method)) { 359 if (!manager->EnableInputMethod(input_method)) { 360 DLOG(ERROR) << "SigninScreenHandler::SetUserInputMethod('" << username 361 << "'): user input method '" << input_method 362 << "' is not enabled and enabling failed (ignored!)."; 363 } 364 } 365 manager->ChangeInputMethod(input_method); 366 367 return true; 368 } 369 370 } // namespace 371 372 // SigninScreenHandler implementation ------------------------------------------ 373 374 SigninScreenHandler::SigninScreenHandler( 375 const scoped_refptr<NetworkStateInformer>& network_state_informer, 376 ErrorScreenActor* error_screen_actor, 377 CoreOobeActor* core_oobe_actor) 378 : ui_state_(UI_STATE_UNKNOWN), 379 frame_state_(FRAME_STATE_UNKNOWN), 380 frame_error_(net::OK), 381 delegate_(NULL), 382 native_window_delegate_(NULL), 383 show_on_init_(false), 384 oobe_ui_(false), 385 focus_stolen_(false), 386 gaia_silent_load_(false), 387 is_account_picker_showing_first_time_(false), 388 dns_cleared_(false), 389 dns_clear_task_running_(false), 390 cookies_cleared_(false), 391 network_state_informer_(network_state_informer), 392 test_expects_complete_login_(false), 393 weak_factory_(this), 394 webui_visible_(false), 395 preferences_changed_delayed_(false), 396 error_screen_actor_(error_screen_actor), 397 core_oobe_actor_(core_oobe_actor), 398 is_first_update_state_call_(true), 399 offline_login_active_(false), 400 last_network_state_(NetworkStateInformer::UNKNOWN), 401 has_pending_auth_ui_(false) { 402 DCHECK(network_state_informer_.get()); 403 DCHECK(error_screen_actor_); 404 DCHECK(core_oobe_actor_); 405 network_state_informer_->AddObserver(this); 406 CrosSettings::Get()->AddSettingsObserver(kAccountsPrefAllowNewUser, this); 407 CrosSettings::Get()->AddSettingsObserver(kAccountsPrefAllowGuest, this); 408 409 registrar_.Add(this, 410 chrome::NOTIFICATION_AUTH_NEEDED, 411 content::NotificationService::AllSources()); 412 registrar_.Add(this, 413 chrome::NOTIFICATION_AUTH_SUPPLIED, 414 content::NotificationService::AllSources()); 415 registrar_.Add(this, 416 chrome::NOTIFICATION_AUTH_CANCELLED, 417 content::NotificationService::AllSources()); 418 } 419 420 SigninScreenHandler::~SigninScreenHandler() { 421 weak_factory_.InvalidateWeakPtrs(); 422 SystemKeyEventListener* key_event_listener = 423 SystemKeyEventListener::GetInstance(); 424 if (key_event_listener) 425 key_event_listener->RemoveCapsLockObserver(this); 426 if (delegate_) 427 delegate_->SetWebUIHandler(NULL); 428 network_state_informer_->RemoveObserver(this); 429 CrosSettings::Get()->RemoveSettingsObserver(kAccountsPrefAllowNewUser, this); 430 CrosSettings::Get()->RemoveSettingsObserver(kAccountsPrefAllowGuest, this); 431 } 432 433 void SigninScreenHandler::DeclareLocalizedValues( 434 LocalizedValuesBuilder* builder) { 435 builder->Add("signinScreenTitle", IDS_SIGNIN_SCREEN_TITLE); 436 builder->Add("signinScreenPasswordChanged", 437 IDS_SIGNIN_SCREEN_PASSWORD_CHANGED); 438 builder->Add("passwordHint", IDS_LOGIN_POD_EMPTY_PASSWORD_TEXT); 439 builder->Add("podMenuButtonAccessibleName", 440 IDS_LOGIN_POD_MENU_BUTTON_ACCESSIBLE_NAME); 441 builder->Add("podMenuRemoveItemAccessibleName", 442 IDS_LOGIN_POD_MENU_REMOVE_ITEM_ACCESSIBLE_NAME); 443 builder->Add("passwordFieldAccessibleName", 444 IDS_LOGIN_POD_PASSWORD_FIELD_ACCESSIBLE_NAME); 445 builder->Add("signedIn", IDS_SCREEN_LOCK_ACTIVE_USER); 446 builder->Add("signinButton", IDS_LOGIN_BUTTON); 447 builder->Add("shutDown", IDS_SHUTDOWN_BUTTON); 448 builder->Add("addUser", IDS_ADD_USER_BUTTON); 449 builder->Add("cancelUserAdding", IDS_CANCEL_USER_ADDING); 450 builder->Add("browseAsGuest", IDS_GO_INCOGNITO_BUTTON); 451 builder->Add("cancel", IDS_CANCEL); 452 builder->Add("signOutUser", IDS_SCREEN_LOCK_SIGN_OUT); 453 builder->Add("createAccount", IDS_CREATE_ACCOUNT_HTML); 454 builder->Add("guestSignin", IDS_BROWSE_WITHOUT_SIGNING_IN_HTML); 455 builder->Add("createLocallyManagedUser", 456 IDS_CREATE_LOCALLY_MANAGED_USER_HTML); 457 builder->Add("createManagedUserFeatureName", 458 IDS_CREATE_LOCALLY_MANAGED_USER_FEATURE_NAME); 459 builder->Add("offlineLogin", IDS_OFFLINE_LOGIN_HTML); 460 builder->Add("ownerUserPattern", IDS_LOGIN_POD_OWNER_USER); 461 builder->Add("removeUser", IDS_LOGIN_POD_REMOVE_USER); 462 builder->Add("errorTpmFailureTitle", IDS_LOGIN_ERROR_TPM_FAILURE_TITLE); 463 builder->Add("errorTpmFailureReboot", IDS_LOGIN_ERROR_TPM_FAILURE_REBOOT); 464 builder->Add("errorTpmFailureRebootButton", 465 IDS_LOGIN_ERROR_TPM_FAILURE_REBOOT_BUTTON); 466 builder->Add( 467 "disabledAddUserTooltip", 468 g_browser_process->browser_policy_connector()->IsEnterpriseManaged() ? 469 IDS_DISABLED_ADD_USER_TOOLTIP_ENTERPRISE : 470 IDS_DISABLED_ADD_USER_TOOLTIP); 471 472 // Strings used by password changed dialog. 473 builder->Add("passwordChangedTitle", IDS_LOGIN_PASSWORD_CHANGED_TITLE); 474 builder->Add("passwordChangedDesc", IDS_LOGIN_PASSWORD_CHANGED_DESC); 475 builder->AddF("passwordChangedMoreInfo", 476 IDS_LOGIN_PASSWORD_CHANGED_MORE_INFO, 477 IDS_SHORT_PRODUCT_OS_NAME); 478 479 builder->Add("oldPasswordHint", IDS_LOGIN_PASSWORD_CHANGED_OLD_PASSWORD_HINT); 480 builder->Add("oldPasswordIncorrect", 481 IDS_LOGIN_PASSWORD_CHANGED_INCORRECT_OLD_PASSWORD); 482 builder->Add("passwordChangedCantRemember", 483 IDS_LOGIN_PASSWORD_CHANGED_CANT_REMEMBER); 484 builder->Add("passwordChangedBackButton", 485 IDS_LOGIN_PASSWORD_CHANGED_BACK_BUTTON); 486 builder->Add("passwordChangedsOkButton", IDS_OK); 487 builder->Add("passwordChangedProceedAnyway", 488 IDS_LOGIN_PASSWORD_CHANGED_PROCEED_ANYWAY); 489 builder->Add("proceedAnywayButton", 490 IDS_LOGIN_PASSWORD_CHANGED_PROCEED_ANYWAY_BUTTON); 491 builder->Add("publicAccountInfoFormat", IDS_LOGIN_PUBLIC_ACCOUNT_INFO_FORMAT); 492 builder->Add("publicAccountReminder", 493 IDS_LOGIN_PUBLIC_ACCOUNT_SIGNOUT_REMINDER); 494 builder->Add("publicAccountEnter", IDS_LOGIN_PUBLIC_ACCOUNT_ENTER); 495 builder->Add("publicAccountEnterAccessibleName", 496 IDS_LOGIN_PUBLIC_ACCOUNT_ENTER_ACCESSIBLE_NAME); 497 builder->AddF("removeUserWarningText", 498 IDS_LOGIN_POD_USER_REMOVE_WARNING, 499 UTF8ToUTF16(chrome::kSupervisedUserManagementDisplayURL)); 500 builder->Add("removeUserWarningButtonTitle", 501 IDS_LOGIN_POD_USER_REMOVE_WARNING_BUTTON); 502 503 if (chromeos::KioskModeSettings::Get()->IsKioskModeEnabled()) 504 builder->Add("demoLoginMessage", IDS_KIOSK_MODE_LOGIN_MESSAGE); 505 } 506 507 void SigninScreenHandler::Show(bool oobe_ui) { 508 CHECK(delegate_); 509 oobe_ui_ = oobe_ui; 510 if (!page_is_ready()) { 511 show_on_init_ = true; 512 return; 513 } 514 515 if (oobe_ui) { 516 // Shows new user sign-in for OOBE. 517 HandleShowAddUser(NULL); 518 } else { 519 // Populates account picker. Animation is turned off for now until we 520 // figure out how to make it fast enough. 521 SendUserList(false); 522 523 // Reset Caps Lock state when login screen is shown. 524 input_method::InputMethodManager::Get()->GetXKeyboard()-> 525 SetCapsLockEnabled(false); 526 527 DictionaryValue params; 528 params.SetBoolean("disableAddUser", AllWhitelistedUsersPresent()); 529 UpdateUIState(UI_STATE_ACCOUNT_PICKER, ¶ms); 530 } 531 } 532 533 void SigninScreenHandler::ShowRetailModeLoginSpinner() { 534 CallJS("showLoginSpinner"); 535 } 536 537 void SigninScreenHandler::SetDelegate(SigninScreenHandlerDelegate* delegate) { 538 delegate_ = delegate; 539 if (delegate_) 540 delegate_->SetWebUIHandler(this); 541 } 542 543 void SigninScreenHandler::SetNativeWindowDelegate( 544 NativeWindowDelegate* native_window_delegate) { 545 native_window_delegate_ = native_window_delegate; 546 } 547 548 void SigninScreenHandler::OnNetworkReady() { 549 MaybePreloadAuthExtension(); 550 } 551 552 void SigninScreenHandler::UpdateState(ErrorScreenActor::ErrorReason reason) { 553 UpdateStateInternal(reason, false); 554 } 555 556 // SigninScreenHandler, private: ----------------------------------------------- 557 558 void SigninScreenHandler::UpdateUIState(UIState ui_state, 559 DictionaryValue* params) { 560 switch (ui_state) { 561 case UI_STATE_GAIA_SIGNIN: 562 ui_state_ = UI_STATE_GAIA_SIGNIN; 563 ShowScreen(OobeUI::kScreenGaiaSignin, params); 564 break; 565 case UI_STATE_ACCOUNT_PICKER: 566 ui_state_ = UI_STATE_ACCOUNT_PICKER; 567 ShowScreen(OobeUI::kScreenAccountPicker, params); 568 break; 569 default: 570 NOTREACHED(); 571 break; 572 } 573 } 574 575 // TODO (ygorshenin@): split this method into small parts. 576 void SigninScreenHandler::UpdateStateInternal( 577 ErrorScreenActor::ErrorReason reason, 578 bool force_update) { 579 // Do nothing once user has signed in or sign in is in progress. 580 // TODO(ygorshenin): We will end up here when processing network state 581 // notification but no ShowSigninScreen() was called so delegate_ will be 582 // NULL. Network state processing logic does not belong here. 583 if (delegate_ && 584 (delegate_->IsUserSigninCompleted() || delegate_->IsSigninInProgress())) { 585 return; 586 } 587 588 NetworkStateInformer::State state = network_state_informer_->state(); 589 const std::string network_path = network_state_informer_->network_path(); 590 const std::string network_name = GetNetworkName(network_path); 591 592 // Skip "update" notification about OFFLINE state from 593 // NetworkStateInformer if previous notification already was 594 // delayed. 595 if ((state == NetworkStateInformer::OFFLINE || has_pending_auth_ui_) && 596 !force_update && 597 !update_state_closure_.IsCancelled()) { 598 return; 599 } 600 601 // TODO (ygorshenin@): switch log level to INFO once signin screen 602 // will be tested well. 603 LOG(WARNING) << "SigninScreenHandler::UpdateStateInternal(): " 604 << "state=" << NetworkStateStatusString(state) << ", " 605 << "network_name=" << network_name << ", " 606 << "reason=" << ErrorReasonString(reason) << ", " 607 << "force_update=" << force_update; 608 update_state_closure_.Cancel(); 609 610 if ((state == NetworkStateInformer::OFFLINE && !force_update) || 611 has_pending_auth_ui_) { 612 update_state_closure_.Reset( 613 base::Bind( 614 &SigninScreenHandler::UpdateStateInternal, 615 weak_factory_.GetWeakPtr(), reason, true)); 616 base::MessageLoop::current()->PostDelayedTask( 617 FROM_HERE, 618 update_state_closure_.callback(), 619 base::TimeDelta::FromSeconds(kOfflineTimeoutSec)); 620 return; 621 } 622 623 // Don't show or hide error screen if we're in connecting state. 624 if (state == NetworkStateInformer::CONNECTING && !force_update) { 625 if (connecting_closure_.IsCancelled()) { 626 // First notification about CONNECTING state. 627 connecting_closure_.Reset( 628 base::Bind(&SigninScreenHandler::UpdateStateInternal, 629 weak_factory_.GetWeakPtr(), reason, true)); 630 base::MessageLoop::current()->PostDelayedTask( 631 FROM_HERE, 632 connecting_closure_.callback(), 633 base::TimeDelta::FromSeconds(kConnectingTimeoutSec)); 634 } 635 return; 636 } 637 connecting_closure_.Cancel(); 638 639 const bool is_online = IsOnline(state, reason); 640 const bool is_under_captive_portal = IsUnderCaptivePortal(state, reason); 641 const bool is_gaia_loading_timeout = 642 (reason == ErrorScreenActor::ERROR_REASON_LOADING_TIMEOUT); 643 const bool is_gaia_error = frame_error_ != net::OK && 644 frame_error_ != net::ERR_NETWORK_CHANGED; 645 const bool is_gaia_signin = IsGaiaVisible() || IsGaiaHiddenByError(); 646 const bool error_screen_should_overlay = 647 !offline_login_active_ && IsGaiaVisible(); 648 const bool from_not_online_to_online_transition = 649 is_online && last_network_state_ != NetworkStateInformer::ONLINE; 650 last_network_state_ = state; 651 652 if (is_online || !is_under_captive_portal) 653 error_screen_actor_->HideCaptivePortal(); 654 655 // Hide offline message (if needed) and return if current screen is 656 // not a Gaia frame. 657 if (!is_gaia_signin) { 658 if (!IsSigninScreenHiddenByError()) 659 HideOfflineMessage(state, reason); 660 return; 661 } 662 663 // Reload frame if network state is changed from {!ONLINE} -> ONLINE state. 664 if (reason == ErrorScreenActor::ERROR_REASON_NETWORK_STATE_CHANGED && 665 from_not_online_to_online_transition) { 666 // Schedules a immediate retry. 667 LOG(WARNING) << "Retry page load since network has been changed."; 668 ReloadGaiaScreen(); 669 } 670 671 if (reason == ErrorScreenActor::ERROR_REASON_PROXY_CONFIG_CHANGED && 672 error_screen_should_overlay) { 673 // Schedules a immediate retry. 674 LOG(WARNING) << "Retry page load since proxy settings has been changed."; 675 ReloadGaiaScreen(); 676 } 677 678 if (reason == ErrorScreenActor::ERROR_REASON_FRAME_ERROR && 679 !IsProxyError(state, reason, frame_error_)) { 680 LOG(WARNING) << "Retry page load due to reason: " 681 << ErrorReasonString(reason); 682 ReloadGaiaScreen(); 683 } 684 685 if ((!is_online || is_gaia_loading_timeout || is_gaia_error) && 686 !offline_login_active_) { 687 SetupAndShowOfflineMessage(state, reason); 688 } else { 689 HideOfflineMessage(state, reason); 690 } 691 } 692 693 void SigninScreenHandler::SetupAndShowOfflineMessage( 694 NetworkStateInformer:: State state, 695 ErrorScreenActor::ErrorReason reason) { 696 const std::string network_path = network_state_informer_->network_path(); 697 const bool is_under_captive_portal = IsUnderCaptivePortal(state, reason); 698 const bool is_proxy_error = IsProxyError(state, reason, frame_error_); 699 const bool is_gaia_loading_timeout = 700 (reason == ErrorScreenActor::ERROR_REASON_LOADING_TIMEOUT); 701 702 // Record portal detection stats only if we're going to show or 703 // change state of the error screen. 704 RecordNetworkPortalDetectorStats(network_path); 705 706 if (is_proxy_error) { 707 error_screen_actor_->SetErrorState(ErrorScreen::ERROR_STATE_PROXY, 708 std::string()); 709 } else if (is_under_captive_portal) { 710 // Do not bother a user with obsessive captive portal showing. This 711 // check makes captive portal being shown only once: either when error 712 // screen is shown for the first time or when switching from another 713 // error screen (offline, proxy). 714 if (IsGaiaVisible() || 715 (error_screen_actor_->error_state() != 716 ErrorScreen::ERROR_STATE_PORTAL)) { 717 error_screen_actor_->FixCaptivePortal(); 718 } 719 const std::string network_name = GetNetworkName(network_path); 720 error_screen_actor_->SetErrorState(ErrorScreen::ERROR_STATE_PORTAL, 721 network_name); 722 } else if (is_gaia_loading_timeout) { 723 error_screen_actor_->SetErrorState( 724 ErrorScreen::ERROR_STATE_AUTH_EXT_TIMEOUT, std::string()); 725 } else { 726 error_screen_actor_->SetErrorState(ErrorScreen::ERROR_STATE_OFFLINE, 727 std::string()); 728 } 729 730 const bool guest_signin_allowed = IsGuestSigninAllowed() && 731 IsSigninScreenError(error_screen_actor_->error_state()); 732 error_screen_actor_->AllowGuestSignin(guest_signin_allowed); 733 734 const bool offline_login_allowed = IsOfflineLoginAllowed() && 735 IsSigninScreenError(error_screen_actor_->error_state()) && 736 error_screen_actor_->error_state() != 737 ErrorScreen::ERROR_STATE_AUTH_EXT_TIMEOUT; 738 error_screen_actor_->AllowOfflineLogin(offline_login_allowed); 739 740 if (GetCurrentScreen() != OobeUI::SCREEN_ERROR_MESSAGE) { 741 DictionaryValue params; 742 const std::string network_type = network_state_informer_->network_type(); 743 params.SetString("lastNetworkType", network_type); 744 error_screen_actor_->SetUIState(ErrorScreen::UI_STATE_SIGNIN); 745 error_screen_actor_->Show(OobeUI::SCREEN_GAIA_SIGNIN, ¶ms); 746 } 747 } 748 749 void SigninScreenHandler::HideOfflineMessage( 750 NetworkStateInformer::State state, 751 ErrorScreenActor::ErrorReason reason) { 752 if (!IsSigninScreenHiddenByError()) 753 return; 754 755 error_screen_actor_->Hide(); 756 757 // Forces a reload for Gaia screen on hiding error message. 758 if (IsGaiaVisible() || IsGaiaHiddenByError()) 759 ReloadGaiaScreen(); 760 } 761 762 void SigninScreenHandler::ReloadGaiaScreen() { 763 if (frame_state_ == FRAME_STATE_LOADING) 764 return; 765 NetworkStateInformer::State state = network_state_informer_->state(); 766 if (state != NetworkStateInformer::ONLINE) { 767 LOG(WARNING) << "Skipping reload of auth extension frame since " 768 << "network state=" << NetworkStateStatusString(state); 769 return; 770 } 771 LOG(WARNING) << "Reload auth extension frame."; 772 frame_state_ = FRAME_STATE_LOADING; 773 CallJS("login.GaiaSigninScreen.doReload"); 774 } 775 776 void SigninScreenHandler::Initialize() { 777 // If delegate_ is NULL here (e.g. WebUIScreenLocker has been destroyed), 778 // don't do anything, just return. 779 if (!delegate_) 780 return; 781 782 // Register for Caps Lock state change notifications; 783 SystemKeyEventListener* key_event_listener = 784 SystemKeyEventListener::GetInstance(); 785 if (key_event_listener) 786 key_event_listener->AddCapsLockObserver(this); 787 788 if (show_on_init_) { 789 show_on_init_ = false; 790 Show(oobe_ui_); 791 } 792 } 793 794 gfx::NativeWindow SigninScreenHandler::GetNativeWindow() { 795 if (native_window_delegate_) 796 return native_window_delegate_->GetNativeWindow(); 797 return NULL; 798 } 799 800 void SigninScreenHandler::RegisterMessages() { 801 AddCallback("authenticateUser", &SigninScreenHandler::HandleAuthenticateUser); 802 AddCallback("completeLogin", &SigninScreenHandler::HandleCompleteLogin); 803 AddCallback("completeAuthentication", 804 &SigninScreenHandler::HandleCompleteAuthentication); 805 AddCallback("getUsers", &SigninScreenHandler::HandleGetUsers); 806 AddCallback("launchDemoUser", &SigninScreenHandler::HandleLaunchDemoUser); 807 AddCallback("launchIncognito", &SigninScreenHandler::HandleLaunchIncognito); 808 AddCallback("showLocallyManagedUserCreationScreen", 809 &SigninScreenHandler::HandleShowLocallyManagedUserCreationScreen); 810 AddCallback("launchPublicAccount", 811 &SigninScreenHandler::HandleLaunchPublicAccount); 812 AddRawCallback("offlineLogin", &SigninScreenHandler::HandleOfflineLogin); 813 AddCallback("rebootSystem", &SigninScreenHandler::HandleRebootSystem); 814 AddRawCallback("showAddUser", &SigninScreenHandler::HandleShowAddUser); 815 AddCallback("shutdownSystem", &SigninScreenHandler::HandleShutdownSystem); 816 AddCallback("loadWallpaper", &SigninScreenHandler::HandleLoadWallpaper); 817 AddCallback("removeUser", &SigninScreenHandler::HandleRemoveUser); 818 AddCallback("toggleEnrollmentScreen", 819 &SigninScreenHandler::HandleToggleEnrollmentScreen); 820 AddCallback("toggleKioskEnableScreen", 821 &SigninScreenHandler::HandleToggleKioskEnableScreen); 822 AddCallback("toggleResetScreen", 823 &SigninScreenHandler::HandleToggleResetScreen); 824 AddCallback("launchHelpApp", &SigninScreenHandler::HandleLaunchHelpApp); 825 AddCallback("createAccount", &SigninScreenHandler::HandleCreateAccount); 826 AddCallback("accountPickerReady", 827 &SigninScreenHandler::HandleAccountPickerReady); 828 AddCallback("wallpaperReady", &SigninScreenHandler::HandleWallpaperReady); 829 AddCallback("loginWebuiReady", &SigninScreenHandler::HandleLoginWebuiReady); 830 AddCallback("signOutUser", &SigninScreenHandler::HandleSignOutUser); 831 AddCallback("networkErrorShown", 832 &SigninScreenHandler::HandleNetworkErrorShown); 833 AddCallback("openProxySettings", 834 &SigninScreenHandler::HandleOpenProxySettings); 835 AddCallback("loginVisible", &SigninScreenHandler::HandleLoginVisible); 836 AddCallback("cancelPasswordChangedFlow", 837 &SigninScreenHandler::HandleCancelPasswordChangedFlow); 838 AddCallback("cancelUserAdding", 839 &SigninScreenHandler::HandleCancelUserAdding); 840 AddCallback("migrateUserData", &SigninScreenHandler::HandleMigrateUserData); 841 AddCallback("resyncUserData", &SigninScreenHandler::HandleResyncUserData); 842 AddCallback("loginUIStateChanged", 843 &SigninScreenHandler::HandleLoginUIStateChanged); 844 AddCallback("unlockOnLoginSuccess", 845 &SigninScreenHandler::HandleUnlockOnLoginSuccess); 846 AddCallback("frameLoadingCompleted", 847 &SigninScreenHandler::HandleFrameLoadingCompleted); 848 AddCallback("showLoadingTimeoutError", 849 &SigninScreenHandler::HandleShowLoadingTimeoutError); 850 AddCallback("updateOfflineLogin", 851 &SigninScreenHandler::HandleUpdateOfflineLogin); 852 } 853 854 void SigninScreenHandler::RegisterPrefs(PrefRegistrySimple* registry) { 855 registry->RegisterDictionaryPref(prefs::kUsersLRUInputMethod); 856 } 857 858 void SigninScreenHandler::HandleGetUsers() { 859 SendUserList(false); 860 } 861 862 void SigninScreenHandler::ClearAndEnablePassword() { 863 core_oobe_actor_->ResetSignInUI(false); 864 } 865 866 void SigninScreenHandler::ClearUserPodPassword() { 867 core_oobe_actor_->ClearUserPodPassword(); 868 } 869 870 void SigninScreenHandler::RefocusCurrentPod() { 871 core_oobe_actor_->RefocusCurrentPod(); 872 } 873 874 void SigninScreenHandler::OnLoginSuccess(const std::string& username) { 875 core_oobe_actor_->OnLoginSuccess(username); 876 } 877 878 void SigninScreenHandler::OnUserRemoved(const std::string& username) { 879 SendUserList(false); 880 } 881 882 void SigninScreenHandler::OnUserImageChanged(const User& user) { 883 if (page_is_ready()) 884 CallJS("login.AccountPickerScreen.updateUserImage", user.email()); 885 } 886 887 void SigninScreenHandler::OnPreferencesChanged() { 888 // Make sure that one of the login UI is fully functional now, otherwise 889 // preferences update would be picked up next time it will be shown. 890 if (!webui_visible_) { 891 LOG(WARNING) << "Login UI is not active - postponed prefs change."; 892 preferences_changed_delayed_ = true; 893 return; 894 } 895 896 if (delegate_ && !delegate_->IsShowUsers()) { 897 HandleShowAddUser(NULL); 898 } else { 899 SendUserList(false); 900 UpdateUIState(UI_STATE_ACCOUNT_PICKER, NULL); 901 } 902 preferences_changed_delayed_ = false; 903 } 904 905 void SigninScreenHandler::ResetSigninScreenHandlerDelegate() { 906 SetDelegate(NULL); 907 } 908 909 void SigninScreenHandler::ShowError(int login_attempts, 910 const std::string& error_text, 911 const std::string& help_link_text, 912 HelpAppLauncher::HelpTopic help_topic_id) { 913 core_oobe_actor_->ShowSignInError(login_attempts, error_text, help_link_text, 914 help_topic_id); 915 } 916 917 void SigninScreenHandler::ShowErrorScreen(LoginDisplay::SigninError error_id) { 918 switch (error_id) { 919 case LoginDisplay::TPM_ERROR: 920 core_oobe_actor_->ShowTpmError(); 921 break; 922 default: 923 NOTREACHED() << "Unknown sign in error"; 924 break; 925 } 926 } 927 928 void SigninScreenHandler::ShowSigninUI(const std::string& email) { 929 930 } 931 932 void SigninScreenHandler::ShowGaiaPasswordChanged(const std::string& username) { 933 email_ = username; 934 password_changed_for_.insert(email_); 935 core_oobe_actor_->ShowSignInUI(email_); 936 CallJS("login.AccountPickerScreen.updateUserGaiaNeeded", email_); 937 } 938 939 void SigninScreenHandler::ShowPasswordChangedDialog(bool show_password_error) { 940 core_oobe_actor_->ShowPasswordChangedScreen(show_password_error); 941 } 942 943 void SigninScreenHandler::ShowSigninScreenForCreds( 944 const std::string& username, 945 const std::string& password) { 946 VLOG(2) << "ShowSigninScreenForCreds for user " << username 947 << ", frame_state=" << frame_state_; 948 949 test_user_ = username; 950 test_pass_ = password; 951 test_expects_complete_login_ = true; 952 953 // Submit login form for test if gaia is ready. If gaia is loading, login 954 // will be attempted in HandleLoginWebuiReady after gaia is ready. Otherwise, 955 // reload gaia then follow the loading case. 956 if (frame_state_ == FRAME_STATE_LOADED) 957 SubmitLoginFormForTest(); 958 else if (frame_state_ != FRAME_STATE_LOADING) 959 HandleShowAddUser(NULL); 960 } 961 962 void SigninScreenHandler::OnCookiesCleared(base::Closure on_clear_callback) { 963 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 964 cookies_cleared_ = true; 965 on_clear_callback.Run(); 966 } 967 968 void SigninScreenHandler::OnCapsLockChange(bool enabled) { 969 if (page_is_ready()) 970 CallJS("login.AccountPickerScreen.setCapsLockState", enabled); 971 } 972 973 void SigninScreenHandler::Observe(int type, 974 const content::NotificationSource& source, 975 const content::NotificationDetails& details) { 976 switch (type) { 977 case chrome::NOTIFICATION_SYSTEM_SETTING_CHANGED: { 978 UpdateAuthExtension(); 979 UpdateAddButtonStatus(); 980 break; 981 } 982 case chrome::NOTIFICATION_AUTH_NEEDED: { 983 has_pending_auth_ui_ = true; 984 break; 985 } 986 case chrome::NOTIFICATION_AUTH_SUPPLIED: 987 has_pending_auth_ui_ = false; 988 if (IsSigninScreenHiddenByError()) { 989 // Hide error screen and reload auth extension. 990 HideOfflineMessage(network_state_informer_->state(), 991 ErrorScreenActor::ERROR_REASON_PROXY_AUTH_SUPPLIED); 992 } else if (ui_state_ == UI_STATE_GAIA_SIGNIN) { 993 // Reload auth extension as proxy credentials are supplied. 994 ReloadGaiaScreen(); 995 } 996 break; 997 case chrome::NOTIFICATION_AUTH_CANCELLED: { 998 // Don't reload auth extension if proxy auth dialog was cancelled. 999 has_pending_auth_ui_ = false; 1000 break; 1001 } 1002 default: 1003 NOTREACHED() << "Unexpected notification " << type; 1004 } 1005 } 1006 1007 void SigninScreenHandler::OnDnsCleared() { 1008 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 1009 dns_clear_task_running_ = false; 1010 dns_cleared_ = true; 1011 ShowSigninScreenIfReady(); 1012 } 1013 1014 // Update keyboard layout to least recently used by the user. 1015 void SigninScreenHandler::SetUserInputMethod(const std::string& username) { 1016 chromeos::input_method::InputMethodManager* const manager = 1017 chromeos::input_method::InputMethodManager::Get(); 1018 1019 const bool succeed = SetUserInputMethodImpl(username, manager); 1020 1021 // This is also a case when LRU layout is set only for a few local users, 1022 // thus others need to be switched to default locale. 1023 // Otherwise they will end up using another user's locale to log in. 1024 if (!succeed) { 1025 DLOG(INFO) << "SetUserInputMethod('" << username 1026 << "'): failed to set user layout. Switching to default."; 1027 1028 manager->SetInputMethodDefault(); 1029 } 1030 } 1031 1032 void SigninScreenHandler::ShowSigninScreenIfReady() { 1033 if (!dns_cleared_ || !cookies_cleared_ || !delegate_) 1034 return; 1035 1036 std::string active_network_path = network_state_informer_->network_path(); 1037 if (gaia_silent_load_ && 1038 (network_state_informer_->state() != NetworkStateInformer::ONLINE || 1039 gaia_silent_load_network_ != active_network_path)) { 1040 // Network has changed. Force Gaia reload. 1041 gaia_silent_load_ = false; 1042 // Gaia page will be realoded, so focus isn't stolen anymore. 1043 focus_stolen_ = false; 1044 } 1045 1046 // Note that LoadAuthExtension clears |email_|. 1047 if (email_.empty()) 1048 delegate_->LoadSigninWallpaper(); 1049 else 1050 delegate_->LoadWallpaper(email_); 1051 1052 // Set Least Recently Used input method for the user. 1053 if (!email_.empty()) 1054 SetUserInputMethod(email_); 1055 1056 LoadAuthExtension(!gaia_silent_load_, false, false); 1057 UpdateUIState(UI_STATE_GAIA_SIGNIN, NULL); 1058 1059 if (gaia_silent_load_) { 1060 // The variable is assigned to false because silently loaded Gaia page was 1061 // used. 1062 gaia_silent_load_ = false; 1063 if (focus_stolen_) 1064 HandleLoginWebuiReady(); 1065 } 1066 1067 UpdateState(ErrorScreenActor::ERROR_REASON_UPDATE); 1068 } 1069 1070 1071 void SigninScreenHandler::UpdateAuthParams(DictionaryValue* params) { 1072 if (!delegate_) 1073 return; 1074 1075 UpdateAuthParamsFromSettings(params, CrosSettings::Get()); 1076 1077 // Allow locally managed user creation only if: 1078 // 1. Enterprise managed device > is allowed by policy. 1079 // 2. Consumer device > owner exists. 1080 // 3. New users are allowed by owner. 1081 1082 CrosSettings* cros_settings = CrosSettings::Get(); 1083 bool allow_new_user = false; 1084 cros_settings->GetBoolean(kAccountsPrefAllowNewUser, &allow_new_user); 1085 1086 bool managed_users_allowed = 1087 UserManager::Get()->AreLocallyManagedUsersAllowed(); 1088 bool managed_users_can_create = true; 1089 int message_id = -1; 1090 if (delegate_->GetUsers().size() == 0) { 1091 managed_users_can_create = false; 1092 message_id = IDS_CREATE_LOCALLY_MANAGED_USER_NO_MANAGER_TEXT; 1093 } 1094 if (!allow_new_user) { 1095 managed_users_can_create = false; 1096 message_id = IDS_CREATE_LOCALLY_MANAGED_USER_CREATION_RESTRICTED_TEXT; 1097 } 1098 1099 params->SetBoolean("managedUsersEnabled", managed_users_allowed); 1100 params->SetBoolean("managedUsersCanCreate", managed_users_can_create); 1101 if (!managed_users_can_create) { 1102 params->SetString("managedUsersRestrictionReason", 1103 l10n_util::GetStringUTF16(message_id)); 1104 } 1105 } 1106 1107 void SigninScreenHandler::LoadAuthExtension( 1108 bool force, bool silent_load, bool offline) { 1109 DictionaryValue params; 1110 1111 params.SetBoolean("forceReload", force); 1112 params.SetBoolean("silentLoad", silent_load); 1113 params.SetBoolean("isLocal", offline); 1114 params.SetBoolean("passwordChanged", 1115 !email_.empty() && password_changed_for_.count(email_)); 1116 if (delegate_) 1117 params.SetBoolean("isShowUsers", delegate_->IsShowUsers()); 1118 params.SetBoolean("useOffline", offline); 1119 params.SetString("email", email_); 1120 email_.clear(); 1121 1122 UpdateAuthParams(¶ms); 1123 1124 if (!offline) { 1125 const std::string app_locale = g_browser_process->GetApplicationLocale(); 1126 if (!app_locale.empty()) 1127 params.SetString("hl", app_locale); 1128 } else { 1129 base::DictionaryValue *localized_strings = new base::DictionaryValue(); 1130 localized_strings->SetString("stringEmail", 1131 l10n_util::GetStringUTF16(IDS_LOGIN_OFFLINE_EMAIL)); 1132 localized_strings->SetString("stringPassword", 1133 l10n_util::GetStringUTF16(IDS_LOGIN_OFFLINE_PASSWORD)); 1134 localized_strings->SetString("stringSignIn", 1135 l10n_util::GetStringUTF16(IDS_LOGIN_OFFLINE_SIGNIN)); 1136 localized_strings->SetString("stringEmptyEmail", 1137 l10n_util::GetStringUTF16(IDS_LOGIN_OFFLINE_EMPTY_EMAIL)); 1138 localized_strings->SetString("stringEmptyPassword", 1139 l10n_util::GetStringUTF16(IDS_LOGIN_OFFLINE_EMPTY_PASSWORD)); 1140 localized_strings->SetString("stringError", 1141 l10n_util::GetStringUTF16(IDS_LOGIN_OFFLINE_ERROR)); 1142 params.Set("localizedStrings", localized_strings); 1143 } 1144 1145 const GURL gaia_url = 1146 CommandLine::ForCurrentProcess()->HasSwitch(::switches::kGaiaUrl) ? 1147 GURL(CommandLine::ForCurrentProcess()->GetSwitchValueASCII( 1148 ::switches::kGaiaUrl)) : 1149 GaiaUrls::GetInstance()->gaia_url(); 1150 params.SetString("gaiaUrl", gaia_url.spec()); 1151 1152 frame_state_ = FRAME_STATE_LOADING; 1153 CallJS("login.GaiaSigninScreen.loadAuthExtension", params); 1154 } 1155 1156 void SigninScreenHandler::UpdateAuthExtension() { 1157 DictionaryValue params; 1158 UpdateAuthParams(¶ms); 1159 CallJS("login.GaiaSigninScreen.updateAuthExtension", params); 1160 } 1161 1162 void SigninScreenHandler::UpdateAddButtonStatus() { 1163 CallJS("cr.ui.login.DisplayManager.updateAddUserButtonStatus", 1164 AllWhitelistedUsersPresent()); 1165 } 1166 1167 void SigninScreenHandler::HandleCompleteLogin(const std::string& typed_email, 1168 const std::string& password) { 1169 if (!delegate_) 1170 return; 1171 const std::string sanitized_email = gaia::SanitizeEmail(typed_email); 1172 delegate_->SetDisplayEmail(sanitized_email); 1173 delegate_->CompleteLogin(UserContext(sanitized_email, 1174 password, 1175 std::string())); // auth_code 1176 1177 if (test_expects_complete_login_) { 1178 VLOG(2) << "Complete test login for " << typed_email 1179 << ", requested=" << test_user_; 1180 1181 test_expects_complete_login_ = false; 1182 test_user_.clear(); 1183 test_pass_.clear(); 1184 } 1185 } 1186 1187 void SigninScreenHandler::HandleCompleteAuthentication( 1188 const std::string& email, 1189 const std::string& password, 1190 const std::string& auth_code) { 1191 if (!delegate_) 1192 return; 1193 const std::string sanitized_email = gaia::SanitizeEmail(email); 1194 delegate_->SetDisplayEmail(sanitized_email); 1195 delegate_->CompleteLogin(UserContext(sanitized_email, password, auth_code)); 1196 } 1197 1198 void SigninScreenHandler::HandleAuthenticateUser(const std::string& username, 1199 const std::string& password) { 1200 if (!delegate_) 1201 return; 1202 delegate_->Login(UserContext(gaia::SanitizeEmail(username), 1203 password, 1204 std::string())); // auth_code 1205 } 1206 1207 void SigninScreenHandler::HandleLaunchDemoUser() { 1208 if (delegate_) 1209 delegate_->LoginAsRetailModeUser(); 1210 } 1211 1212 void SigninScreenHandler::HandleLaunchIncognito() { 1213 if (delegate_) 1214 delegate_->LoginAsGuest(); 1215 } 1216 1217 void SigninScreenHandler::HandleShowLocallyManagedUserCreationScreen() { 1218 if (!UserManager::Get()->AreLocallyManagedUsersAllowed()) { 1219 LOG(ERROR) << "Managed users not allowed."; 1220 return; 1221 } 1222 scoped_ptr<DictionaryValue> params(new DictionaryValue()); 1223 LoginDisplayHostImpl::default_host()-> 1224 StartWizard(WizardController::kLocallyManagedUserCreationScreenName, 1225 params.Pass()); 1226 } 1227 1228 void SigninScreenHandler::HandleLaunchPublicAccount( 1229 const std::string& username) { 1230 if (delegate_) 1231 delegate_->LoginAsPublicAccount(username); 1232 } 1233 1234 void SigninScreenHandler::HandleOfflineLogin(const base::ListValue* args) { 1235 if (!delegate_ || delegate_->IsShowUsers()) { 1236 NOTREACHED(); 1237 return; 1238 } 1239 if (!args->GetString(0, &email_)) 1240 email_.clear(); 1241 // Load auth extension. Parameters are: force reload, do not load extension in 1242 // background, use offline version. 1243 LoadAuthExtension(true, false, true); 1244 UpdateUIState(UI_STATE_GAIA_SIGNIN, NULL); 1245 } 1246 1247 void SigninScreenHandler::HandleShutdownSystem() { 1248 ash::Shell::GetInstance()->lock_state_controller()->RequestShutdown(); 1249 } 1250 1251 void SigninScreenHandler::HandleLoadWallpaper(const std::string& email) { 1252 if (delegate_) 1253 delegate_->LoadWallpaper(email); 1254 } 1255 1256 void SigninScreenHandler::HandleRebootSystem() { 1257 chromeos::DBusThreadManager::Get()->GetPowerManagerClient()->RequestRestart(); 1258 } 1259 1260 void SigninScreenHandler::HandleRemoveUser(const std::string& email) { 1261 if (!delegate_) 1262 return; 1263 delegate_->RemoveUser(email); 1264 UpdateAddButtonStatus(); 1265 } 1266 1267 void SigninScreenHandler::HandleShowAddUser(const base::ListValue* args) { 1268 email_.clear(); 1269 // |args| can be null if it's OOBE. 1270 if (args) 1271 args->GetString(0, &email_); 1272 is_account_picker_showing_first_time_ = false; 1273 1274 if (gaia_silent_load_ && email_.empty()) { 1275 dns_cleared_ = true; 1276 cookies_cleared_ = true; 1277 ShowSigninScreenIfReady(); 1278 } else { 1279 StartClearingDnsCache(); 1280 StartClearingCookies(base::Bind( 1281 &SigninScreenHandler::ShowSigninScreenIfReady, 1282 weak_factory_.GetWeakPtr())); 1283 } 1284 } 1285 1286 void SigninScreenHandler::HandleToggleEnrollmentScreen() { 1287 if (delegate_) 1288 delegate_->ShowEnterpriseEnrollmentScreen(); 1289 } 1290 1291 void SigninScreenHandler::HandleToggleKioskEnableScreen() { 1292 if (delegate_ && 1293 !g_browser_process->browser_policy_connector()->IsEnterpriseManaged()) { 1294 delegate_->ShowKioskEnableScreen(); 1295 } 1296 } 1297 1298 void SigninScreenHandler::HandleToggleResetScreen() { 1299 if (delegate_ && 1300 !g_browser_process->browser_policy_connector()->IsEnterpriseManaged()) { 1301 delegate_->ShowResetScreen(); 1302 } 1303 } 1304 1305 void SigninScreenHandler::HandleToggleKioskAutolaunchScreen() { 1306 if (delegate_ && 1307 !g_browser_process->browser_policy_connector()->IsEnterpriseManaged()) { 1308 delegate_->ShowKioskAutolaunchScreen(); 1309 } 1310 } 1311 1312 void SigninScreenHandler::HandleLaunchHelpApp(double help_topic_id) { 1313 if (!delegate_) 1314 return; 1315 if (!help_app_.get()) 1316 help_app_ = new HelpAppLauncher(GetNativeWindow()); 1317 help_app_->ShowHelpTopic( 1318 static_cast<HelpAppLauncher::HelpTopic>(help_topic_id)); 1319 } 1320 1321 void SigninScreenHandler::FillUserDictionary(User* user, 1322 bool is_owner, 1323 DictionaryValue* user_dict) { 1324 const std::string& email = user->email(); 1325 bool is_public_account = 1326 user->GetType() == User::USER_TYPE_PUBLIC_ACCOUNT; 1327 bool is_locally_managed_user = 1328 user->GetType() == User::USER_TYPE_LOCALLY_MANAGED; 1329 1330 user_dict->SetString(kKeyUsername, email); 1331 user_dict->SetString(kKeyEmailAddress, user->display_email()); 1332 user_dict->SetString(kKeyDisplayName, user->GetDisplayName()); 1333 user_dict->SetBoolean(kKeyPublicAccount, is_public_account); 1334 user_dict->SetBoolean(kKeyLocallyManagedUser, is_locally_managed_user); 1335 user_dict->SetInteger(kKeyOauthTokenStatus, user->oauth_token_status()); 1336 user_dict->SetBoolean(kKeySignedIn, user->is_logged_in()); 1337 user_dict->SetBoolean(kKeyIsOwner, is_owner); 1338 1339 if (is_public_account) { 1340 policy::BrowserPolicyConnector* policy_connector = 1341 g_browser_process->browser_policy_connector(); 1342 1343 if (policy_connector->IsEnterpriseManaged()) { 1344 user_dict->SetString(kKeyEnterpriseDomain, 1345 policy_connector->GetEnterpriseDomain()); 1346 } 1347 } 1348 } 1349 1350 void SigninScreenHandler::SendUserList(bool animated) { 1351 if (!delegate_) 1352 return; 1353 1354 size_t max_non_owner_users = kMaxUsers - 1; 1355 size_t non_owner_count = 0; 1356 1357 ListValue users_list; 1358 const UserList& users = delegate_->GetUsers(); 1359 1360 // TODO(nkostylev): Show optional intro dialog about multi-profiles feature 1361 // based on user preferences. http://crbug.com/230862 1362 1363 // TODO(nkostylev): Move to a separate method in UserManager. 1364 // http://crbug.com/230852 1365 bool is_signin_to_add = LoginDisplayHostImpl::default_host() && 1366 UserManager::Get()->IsUserLoggedIn(); 1367 1368 bool single_user = users.size() == 1; 1369 for (UserList::const_iterator it = users.begin(); it != users.end(); ++it) { 1370 const std::string& email = (*it)->email(); 1371 1372 std::string owner; 1373 chromeos::CrosSettings::Get()->GetString(chromeos::kDeviceOwner, &owner); 1374 bool is_owner = (email == owner); 1375 1376 if (non_owner_count < max_non_owner_users || is_owner) { 1377 DictionaryValue* user_dict = new DictionaryValue(); 1378 FillUserDictionary(*it, is_owner, user_dict); 1379 bool is_public_account = 1380 ((*it)->GetType() == User::USER_TYPE_PUBLIC_ACCOUNT); 1381 bool signed_in = (*it)->is_logged_in(); 1382 // Single user check here is necessary because owner info might not be 1383 // available when running into login screen on first boot. 1384 // See http://crosbug.com/12723 1385 user_dict->SetBoolean(kKeyCanRemove, 1386 !single_user && 1387 !email.empty() && 1388 !is_owner && 1389 !is_public_account && 1390 !signed_in && 1391 !is_signin_to_add); 1392 1393 users_list.Append(user_dict); 1394 if (!is_owner) 1395 ++non_owner_count; 1396 } 1397 } 1398 1399 CallJS("login.AccountPickerScreen.loadUsers", users_list, animated, 1400 delegate_->IsShowGuest()); 1401 } 1402 1403 void SigninScreenHandler::HandleAccountPickerReady() { 1404 LOG(INFO) << "Login WebUI >> AccountPickerReady"; 1405 1406 if (delegate_ && !ScreenLocker::default_screen_locker() && 1407 !chromeos::IsMachineHWIDCorrect() && 1408 !oobe_ui_) { 1409 delegate_->ShowWrongHWIDScreen(); 1410 return; 1411 } 1412 1413 PrefService* prefs = g_browser_process->local_state(); 1414 if (prefs->GetBoolean(prefs::kFactoryResetRequested)) { 1415 prefs->SetBoolean(prefs::kFactoryResetRequested, false); 1416 prefs->CommitPendingWrite(); 1417 HandleToggleResetScreen(); 1418 return; 1419 } 1420 1421 is_account_picker_showing_first_time_ = true; 1422 MaybePreloadAuthExtension(); 1423 1424 if (ScreenLocker::default_screen_locker()) { 1425 content::NotificationService::current()->Notify( 1426 chrome::NOTIFICATION_LOCK_WEBUI_READY, 1427 content::NotificationService::AllSources(), 1428 content::NotificationService::NoDetails()); 1429 } 1430 1431 if (delegate_) 1432 delegate_->OnSigninScreenReady(); 1433 } 1434 1435 void SigninScreenHandler::HandleWallpaperReady() { 1436 if (ScreenLocker::default_screen_locker()) { 1437 content::NotificationService::current()->Notify( 1438 chrome::NOTIFICATION_LOCK_BACKGROUND_DISPLAYED, 1439 content::NotificationService::AllSources(), 1440 content::NotificationService::NoDetails()); 1441 } 1442 } 1443 1444 void SigninScreenHandler::HandleLoginWebuiReady() { 1445 if (focus_stolen_) { 1446 // Set focus to the Gaia page. 1447 // TODO(altimofeev): temporary solution, until focus parameters are 1448 // implemented on the Gaia side. 1449 // Do this only once. Any subsequent call would relod GAIA frame. 1450 focus_stolen_ = false; 1451 const char code[] = "gWindowOnLoad();"; 1452 RenderViewHost* rvh = web_ui()->GetWebContents()->GetRenderViewHost(); 1453 rvh->ExecuteJavascriptInWebFrame( 1454 ASCIIToUTF16("//iframe[@id='signin-frame']\n//iframe"), 1455 ASCIIToUTF16(code)); 1456 } 1457 if (!gaia_silent_load_) { 1458 content::NotificationService::current()->Notify( 1459 chrome::NOTIFICATION_LOGIN_WEBUI_LOADED, 1460 content::NotificationService::AllSources(), 1461 content::NotificationService::NoDetails()); 1462 } else { 1463 focus_stolen_ = true; 1464 // Prevent focus stealing by the Gaia page. 1465 // TODO(altimofeev): temporary solution, until focus parameters are 1466 // implemented on the Gaia side. 1467 const char code[] = "var gWindowOnLoad = window.onload; " 1468 "window.onload=function() {};"; 1469 RenderViewHost* rvh = web_ui()->GetWebContents()->GetRenderViewHost(); 1470 rvh->ExecuteJavascriptInWebFrame( 1471 ASCIIToUTF16("//iframe[@id='signin-frame']\n//iframe"), 1472 ASCIIToUTF16(code)); 1473 // As we could miss and window.onload could already be called, restore 1474 // focus to current pod (see crbug/175243). 1475 RefocusCurrentPod(); 1476 } 1477 HandleFrameLoadingCompleted(0); 1478 1479 if (test_expects_complete_login_) 1480 SubmitLoginFormForTest(); 1481 } 1482 1483 void SigninScreenHandler::HandleSignOutUser() { 1484 if (delegate_) 1485 delegate_->Signout(); 1486 } 1487 1488 void SigninScreenHandler::HandleNetworkErrorShown() { 1489 content::NotificationService::current()->Notify( 1490 chrome::NOTIFICATION_LOGIN_NETWORK_ERROR_SHOWN, 1491 content::NotificationService::AllSources(), 1492 content::NotificationService::NoDetails()); 1493 } 1494 1495 void SigninScreenHandler::HandleCreateAccount() { 1496 if (delegate_) 1497 delegate_->CreateAccount(); 1498 } 1499 1500 void SigninScreenHandler::HandleOpenProxySettings() { 1501 LoginDisplayHostImpl::default_host()->OpenProxySettings(); 1502 } 1503 1504 void SigninScreenHandler::HandleLoginVisible(const std::string& source) { 1505 LOG(WARNING) << "Login WebUI >> loginVisible, src: " << source << ", " 1506 << "webui_visible_: " << webui_visible_; 1507 if (!webui_visible_) { 1508 // There might be multiple messages from OOBE UI so send notifications after 1509 // the first one only. 1510 content::NotificationService::current()->Notify( 1511 chrome::NOTIFICATION_LOGIN_OR_LOCK_WEBUI_VISIBLE, 1512 content::NotificationService::AllSources(), 1513 content::NotificationService::NoDetails()); 1514 TRACE_EVENT_ASYNC_END0( 1515 "ui", "ShowLoginWebUI", LoginDisplayHostImpl::kShowLoginWebUIid); 1516 } 1517 webui_visible_ = true; 1518 if (preferences_changed_delayed_) 1519 OnPreferencesChanged(); 1520 } 1521 1522 void SigninScreenHandler::HandleCancelPasswordChangedFlow() { 1523 StartClearingCookies(base::Bind( 1524 &SigninScreenHandler::CancelPasswordChangedFlowInternal, 1525 weak_factory_.GetWeakPtr())); 1526 } 1527 1528 void SigninScreenHandler::HandleCancelUserAdding() { 1529 if (delegate_) 1530 delegate_->CancelUserAdding(); 1531 } 1532 1533 void SigninScreenHandler::HandleMigrateUserData( 1534 const std::string& old_password) { 1535 if (delegate_) 1536 delegate_->MigrateUserData(old_password); 1537 } 1538 1539 void SigninScreenHandler::HandleResyncUserData() { 1540 if (delegate_) 1541 delegate_->ResyncUserData(); 1542 } 1543 1544 void SigninScreenHandler::HandleLoginUIStateChanged(const std::string& source, 1545 bool new_value) { 1546 LOG(INFO) << "Login WebUI >> active: " << new_value << ", " 1547 << "source: " << source; 1548 1549 if (!KioskAppManager::Get()->GetAutoLaunchApp().empty() && 1550 KioskAppManager::Get()->IsAutoLaunchRequested()) { 1551 LOG(INFO) << "Showing auto-launch warning"; 1552 HandleToggleKioskAutolaunchScreen(); 1553 return; 1554 } 1555 1556 if (source == kSourceGaiaSignin) { 1557 ui_state_ = UI_STATE_GAIA_SIGNIN; 1558 } else if (source == kSourceAccountPicker) { 1559 ui_state_ = UI_STATE_ACCOUNT_PICKER; 1560 } else { 1561 NOTREACHED(); 1562 return; 1563 } 1564 } 1565 1566 void SigninScreenHandler::HandleUnlockOnLoginSuccess() { 1567 DCHECK(UserManager::Get()->IsUserLoggedIn()); 1568 if (ScreenLocker::default_screen_locker()) 1569 ScreenLocker::default_screen_locker()->UnlockOnLoginSuccess(); 1570 } 1571 1572 void SigninScreenHandler::HandleFrameLoadingCompleted(int status) { 1573 const net::Error frame_error = static_cast<net::Error>(-status); 1574 if (frame_error == net::ERR_ABORTED) { 1575 LOG(WARNING) << "Ignore gaia frame error: " << frame_error; 1576 return; 1577 } 1578 frame_error_ = frame_error; 1579 if (frame_error == net::OK) { 1580 LOG(INFO) << "Gaia frame is loaded"; 1581 frame_state_ = FRAME_STATE_LOADED; 1582 } else { 1583 LOG(WARNING) << "Gaia frame error: " << frame_error_; 1584 frame_state_ = FRAME_STATE_ERROR; 1585 } 1586 1587 if (network_state_informer_->state() != NetworkStateInformer::ONLINE) 1588 return; 1589 if (frame_state_ == FRAME_STATE_LOADED) 1590 UpdateState(ErrorScreenActor::ERROR_REASON_UPDATE); 1591 else if (frame_state_ == FRAME_STATE_ERROR) 1592 UpdateState(ErrorScreenActor::ERROR_REASON_FRAME_ERROR); 1593 } 1594 1595 void SigninScreenHandler::HandleShowLoadingTimeoutError() { 1596 UpdateState(ErrorScreenActor::ERROR_REASON_LOADING_TIMEOUT); 1597 } 1598 1599 void SigninScreenHandler::HandleUpdateOfflineLogin(bool offline_login_active) { 1600 offline_login_active_ = offline_login_active; 1601 } 1602 1603 void SigninScreenHandler::StartClearingDnsCache() { 1604 if (dns_clear_task_running_ || !g_browser_process->io_thread()) 1605 return; 1606 1607 dns_cleared_ = false; 1608 BrowserThread::PostTaskAndReply( 1609 BrowserThread::IO, FROM_HERE, 1610 base::Bind(&ClearDnsCache, g_browser_process->io_thread()), 1611 base::Bind(&SigninScreenHandler::OnDnsCleared, 1612 weak_factory_.GetWeakPtr())); 1613 dns_clear_task_running_ = true; 1614 } 1615 1616 void SigninScreenHandler::StartClearingCookies( 1617 const base::Closure& on_clear_callback) { 1618 cookies_cleared_ = false; 1619 ProfileHelper* profile_helper = 1620 g_browser_process->platform_part()->profile_helper(); 1621 LOG_ASSERT( 1622 Profile::FromWebUI(web_ui()) == profile_helper->GetSigninProfile()); 1623 profile_helper->ClearSigninProfile(base::Bind( 1624 &SigninScreenHandler::OnCookiesCleared, 1625 weak_factory_.GetWeakPtr(), on_clear_callback)); 1626 } 1627 1628 void SigninScreenHandler::MaybePreloadAuthExtension() { 1629 // Fetching of the extension is not started before account picker page is 1630 // loaded because it can affect the loading speed. Also if cookies clearing 1631 // was initiated or |dns_clear_task_running_| then auth extension showing has 1632 // already been initiated and preloading is senseless. 1633 // Do not load the extension for the screen locker, see crosbug.com/25018. 1634 if (is_account_picker_showing_first_time_ && 1635 !gaia_silent_load_ && 1636 !ScreenLocker::default_screen_locker() && 1637 !cookies_cleared_ && 1638 !dns_clear_task_running_ && 1639 network_state_informer_->state() == NetworkStateInformer::ONLINE) { 1640 gaia_silent_load_ = true; 1641 gaia_silent_load_network_ = network_state_informer_->network_path(); 1642 LoadAuthExtension(true, true, false); 1643 } 1644 } 1645 1646 bool SigninScreenHandler::AllWhitelistedUsersPresent() { 1647 CrosSettings* cros_settings = CrosSettings::Get(); 1648 bool allow_new_user = false; 1649 cros_settings->GetBoolean(kAccountsPrefAllowNewUser, &allow_new_user); 1650 if (allow_new_user) 1651 return false; 1652 UserManager* user_manager = UserManager::Get(); 1653 const UserList& users = user_manager->GetUsers(); 1654 if (!delegate_ || users.size() > kMaxUsers) { 1655 return false; 1656 } 1657 const base::ListValue* whitelist = NULL; 1658 if (!cros_settings->GetList(kAccountsPrefUsers, &whitelist) || !whitelist) 1659 return false; 1660 for (size_t i = 0; i < whitelist->GetSize(); ++i) { 1661 std::string whitelisted_user; 1662 // NB: Wildcards in the whitelist are also detected as not present here. 1663 if (!whitelist->GetString(i, &whitelisted_user) || 1664 !user_manager->IsKnownUser(whitelisted_user)) { 1665 return false; 1666 } 1667 } 1668 return true; 1669 } 1670 1671 void SigninScreenHandler::CancelPasswordChangedFlowInternal() { 1672 if (delegate_) { 1673 Show(oobe_ui_); 1674 delegate_->CancelPasswordChangedFlow(); 1675 } 1676 } 1677 1678 OobeUI::Screen SigninScreenHandler::GetCurrentScreen() const { 1679 OobeUI::Screen screen = OobeUI::SCREEN_UNKNOWN; 1680 OobeUI* oobe_ui = static_cast<OobeUI*>(web_ui()->GetController()); 1681 if (oobe_ui) 1682 screen = oobe_ui->current_screen(); 1683 return screen; 1684 } 1685 1686 bool SigninScreenHandler::IsGaiaVisible() const { 1687 return IsSigninScreen(GetCurrentScreen()) && 1688 ui_state_ == UI_STATE_GAIA_SIGNIN; 1689 } 1690 1691 bool SigninScreenHandler::IsGaiaHiddenByError() const { 1692 return IsSigninScreenHiddenByError() && 1693 ui_state_ == UI_STATE_GAIA_SIGNIN; 1694 } 1695 1696 bool SigninScreenHandler::IsSigninScreenHiddenByError() const { 1697 return (GetCurrentScreen() == OobeUI::SCREEN_ERROR_MESSAGE) && 1698 (IsSigninScreen(error_screen_actor_->parent_screen())); 1699 } 1700 1701 bool SigninScreenHandler::IsGuestSigninAllowed() const { 1702 CrosSettings* cros_settings = CrosSettings::Get(); 1703 if (!cros_settings) 1704 return false; 1705 bool allow_guest; 1706 cros_settings->GetBoolean(kAccountsPrefAllowGuest, &allow_guest); 1707 return allow_guest; 1708 } 1709 1710 bool SigninScreenHandler::IsOfflineLoginAllowed() const { 1711 CrosSettings* cros_settings = CrosSettings::Get(); 1712 if (!cros_settings) 1713 return false; 1714 1715 // Offline login is allowed only when user pods are hidden. 1716 bool show_pods; 1717 cros_settings->GetBoolean(kAccountsPrefShowUserNamesOnSignIn, &show_pods); 1718 return !show_pods; 1719 } 1720 1721 void SigninScreenHandler::SubmitLoginFormForTest() { 1722 VLOG(2) << "Submit login form for test, user=" << test_user_; 1723 1724 std::string code; 1725 code += "document.getElementById('Email').value = '" + test_user_ + "';"; 1726 code += "document.getElementById('Passwd').value = '" + test_pass_ + "';"; 1727 code += "document.getElementById('signIn').click();"; 1728 1729 RenderViewHost* rvh = web_ui()->GetWebContents()->GetRenderViewHost(); 1730 rvh->ExecuteJavascriptInWebFrame( 1731 ASCIIToUTF16("//iframe[@id='signin-frame']\n//iframe"), 1732 ASCIIToUTF16(code)); 1733 1734 // Test properties are cleared in HandleCompleteLogin because the form 1735 // submission might fail and login will not be attempted after reloading 1736 // if they are cleared here. 1737 } 1738 1739 } // namespace chromeos 1740