| Index: chrome/browser/services/gcm/gcm_profile_service.cc
|
| diff --git a/chrome/browser/services/gcm/gcm_profile_service.cc b/chrome/browser/services/gcm/gcm_profile_service.cc
|
| index 4f0c270014514b92ce09a8bd9936e4857813ea09..3afea2173d8d888f726db7c801a655b191af6703 100644
|
| --- a/chrome/browser/services/gcm/gcm_profile_service.cc
|
| +++ b/chrome/browser/services/gcm/gcm_profile_service.cc
|
| @@ -38,9 +38,13 @@ class GCMProfileService::DelayedTaskController {
|
| DelayedTaskController();
|
| ~DelayedTaskController();
|
|
|
| - // Adds an app to non-ready list that queue all tasks to invoke until ready.
|
| + // Adds an app to the tracking list. It will be first marked as not ready.
|
| + // Tasks will be queued for delay execution until the app is marked as ready.
|
| void AddApp(const std::string& app_id);
|
|
|
| + // Removes the app from the tracking list.
|
| + void RemoveApp(const std::string& app_id);
|
| +
|
| // Adds a task that will be invoked once we're ready.
|
| void AddTask(const std::string& app_id, base::Closure task);
|
|
|
| @@ -53,6 +57,9 @@ class GCMProfileService::DelayedTaskController {
|
| // Returns true if it is ready to perform operations for an app.
|
| bool CanRunTaskWithoutDelay(const std::string& app_id) const;
|
|
|
| + // Returns true if the app has been tracked for readiness.
|
| + bool IsAppTracked(const std::string& app_id) const;
|
| +
|
| private:
|
| struct AppTaskQueue {
|
| AppTaskQueue();
|
| @@ -100,6 +107,11 @@ void GCMProfileService::DelayedTaskController::AddApp(
|
| delayed_task_map_[app_id] = new AppTaskQueue;
|
| }
|
|
|
| +void GCMProfileService::DelayedTaskController::RemoveApp(
|
| + const std::string& app_id) {
|
| + delayed_task_map_.erase(app_id);
|
| +}
|
| +
|
| void GCMProfileService::DelayedTaskController::AddTask(
|
| const std::string& app_id, base::Closure task) {
|
| DelayedTaskMap::const_iterator iter = delayed_task_map_.find(app_id);
|
| @@ -149,6 +161,11 @@ bool GCMProfileService::DelayedTaskController::CanRunTaskWithoutDelay(
|
| return iter->second->ready;
|
| }
|
|
|
| +bool GCMProfileService::DelayedTaskController::IsAppTracked(
|
| + const std::string& app_id) const {
|
| + return delayed_task_map_.find(app_id) != delayed_task_map_.end();
|
| +}
|
| +
|
| void GCMProfileService::DelayedTaskController::RunTasks(
|
| AppTaskQueue* task_queue) {
|
| DCHECK(gcm_client_ready_ && task_queue->ready);
|
| @@ -415,7 +432,11 @@ bool GCMProfileService::RegistrationInfo::IsValid() const {
|
| bool GCMProfileService::enable_gcm_for_testing_ = false;
|
|
|
| // static
|
| -bool GCMProfileService::IsGCMEnabled() {
|
| +bool GCMProfileService::IsGCMEnabled(Profile* profile) {
|
| + // GCM is not enabled in incognito mode.
|
| + if (profile->IsOffTheRecord())
|
| + return false;
|
| +
|
| if (enable_gcm_for_testing_)
|
| return true;
|
|
|
| @@ -443,6 +464,7 @@ GCMProfileService::GCMProfileService(Profile* profile)
|
| : profile_(profile),
|
| testing_delegate_(NULL),
|
| weak_ptr_factory_(this) {
|
| + DCHECK(!profile->IsOffTheRecord());
|
| Init();
|
| }
|
|
|
| @@ -725,6 +747,9 @@ void GCMProfileService::Unregister(const std::string& app_id) {
|
| // Remove the persisted registration info.
|
| DeleteRegistrationInfo(app_id);
|
|
|
| + // No need to track the app any more.
|
| + delayed_task_controller_->RemoveApp(app_id);
|
| +
|
| // Ask the server to unregister it. There could be a small chance that the
|
| // unregister request fails. If this occurs, it does not bring any harm since
|
| // we simply reject the messages/events received from the server.
|
| @@ -887,12 +912,16 @@ void GCMProfileService::WriteRegistrationInfo(const std::string& app_id) {
|
| }
|
|
|
| void GCMProfileService::ReadRegistrationInfo(const std::string& app_id) {
|
| - extensions::StateStore* storage =
|
| - extensions::ExtensionSystem::Get(profile_)->state_store();
|
| - DCHECK(storage);
|
| + // This function can be called more than once when the app is allowed in
|
| + // incognito and the extension service reloads the app.
|
| + if (delayed_task_controller_->IsAppTracked(app_id))
|
| + return;
|
|
|
| delayed_task_controller_->AddApp(app_id);
|
|
|
| + extensions::StateStore* storage =
|
| + extensions::ExtensionSystem::Get(profile_)->state_store();
|
| + DCHECK(storage);
|
| storage->GetExtensionValue(
|
| app_id,
|
| kRegistrationKey,
|
|
|