This source file includes following definitions.
- GetVersionFromFileThread
- SetVersionInUIThread
- CheckForUpdate
- RelaunchBrowser
- OnReportResults
- UpdateStatus
- GotInstalledVersion
- CreateGoogleUpdater
- ClearGoogleUpdater
- WindowEnumeration
- GetElevationParent
- Create
#include "base/memory/ref_counted.h"
#include "base/memory/scoped_ptr.h"
#include "base/memory/weak_ptr.h"
#include "base/strings/string16.h"
#include "base/version.h"
#include "base/win/win_util.h"
#include "base/win/windows_version.h"
#include "chrome/browser/google/google_update_win.h"
#include "chrome/browser/lifetime/application_lifetime.h"
#include "chrome/browser/ui/browser.h"
#include "chrome/browser/ui/webui/help/version_updater.h"
#include "chrome/common/chrome_version_info.h"
#include "chrome/installer/util/browser_distribution.h"
#include "chrome/installer/util/install_util.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/browser/user_metrics.h"
#include "grit/chromium_strings.h"
#include "grit/generated_resources.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/views/widget/widget.h"
using base::UserMetricsAction;
using content::BrowserThread;
namespace {
class VersionUpdaterWin : public VersionUpdater,
public GoogleUpdateStatusListener {
private:
friend class VersionReader;
friend class VersionUpdater;
VersionUpdaterWin();
virtual ~VersionUpdaterWin();
virtual void CheckForUpdate(const StatusCallback& callback) OVERRIDE;
virtual void RelaunchBrowser() const OVERRIDE;
virtual void OnReportResults(GoogleUpdateUpgradeResult result,
GoogleUpdateErrorCode error_code,
const base::string16& error_message,
const base::string16& version) OVERRIDE;
void UpdateStatus(GoogleUpdateUpgradeResult result,
GoogleUpdateErrorCode error_code,
const base::string16& error_message);
void GotInstalledVersion(const Version& version);
void CreateGoogleUpdater();
void ClearGoogleUpdater();
HWND GetElevationParent();
scoped_refptr<GoogleUpdate> google_updater_;
base::WeakPtrFactory<VersionUpdaterWin> weak_factory_;
StatusCallback callback_;
DISALLOW_COPY_AND_ASSIGN(VersionUpdaterWin);
};
class VersionReader
: public base::RefCountedThreadSafe<VersionReader> {
public:
explicit VersionReader(
const base::WeakPtr<VersionUpdaterWin>& version_updater)
: version_updater_(version_updater) {
}
void GetVersionFromFileThread() {
BrowserDistribution* dist = BrowserDistribution::GetDistribution();
InstallUtil::GetChromeVersion(dist, false, &installed_version_);
if (!installed_version_.IsValid()) {
InstallUtil::GetChromeVersion(dist, true, &installed_version_);
}
BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, base::Bind(
&VersionReader::SetVersionInUIThread, this));
}
void SetVersionInUIThread() {
if (version_updater_.get() != NULL)
version_updater_->GotInstalledVersion(installed_version_);
}
private:
friend class base::RefCountedThreadSafe<VersionReader>;
base::WeakPtr<VersionUpdaterWin> version_updater_;
Version installed_version_;
};
VersionUpdaterWin::VersionUpdaterWin()
: weak_factory_(this) {
CreateGoogleUpdater();
}
VersionUpdaterWin::~VersionUpdaterWin() {
ClearGoogleUpdater();
}
void VersionUpdaterWin::CheckForUpdate(const StatusCallback& callback) {
callback_ = callback;
if (!(base::win::GetVersion() == base::win::VERSION_VISTA &&
(base::win::OSInfo::GetInstance()->service_pack().major == 0) &&
!base::win::UserAccountControlIsEnabled())) {
if (!google_updater_)
CreateGoogleUpdater();
UpdateStatus(UPGRADE_CHECK_STARTED, GOOGLE_UPDATE_NO_ERROR,
base::string16());
google_updater_->CheckForUpdate(false, GetElevationParent());
}
}
void VersionUpdaterWin::RelaunchBrowser() const {
chrome::AttemptRestart();
}
void VersionUpdaterWin::OnReportResults(
GoogleUpdateUpgradeResult result, GoogleUpdateErrorCode error_code,
const base::string16& error_message, const base::string16& version) {
ClearGoogleUpdater();
UpdateStatus(result, error_code, error_message);
}
void VersionUpdaterWin::UpdateStatus(GoogleUpdateUpgradeResult result,
GoogleUpdateErrorCode error_code,
const base::string16& error_message) {
#if defined(GOOGLE_CHROME_BUILD)
Status status = UPDATED;
base::string16 message;
switch (result) {
case UPGRADE_CHECK_STARTED: {
content::RecordAction(UserMetricsAction("UpgradeCheck_Started"));
status = CHECKING;
break;
}
case UPGRADE_STARTED: {
content::RecordAction(UserMetricsAction("Upgrade_Started"));
status = UPDATING;
break;
}
case UPGRADE_IS_AVAILABLE: {
content::RecordAction(
UserMetricsAction("UpgradeCheck_UpgradeIsAvailable"));
DCHECK(!google_updater_);
CreateGoogleUpdater();
UpdateStatus(UPGRADE_STARTED, GOOGLE_UPDATE_NO_ERROR, base::string16());
google_updater_->CheckForUpdate(true, GetElevationParent());
return;
}
case UPGRADE_ALREADY_UP_TO_DATE: {
BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE, base::Bind(
&VersionReader::GetVersionFromFileThread,
new VersionReader(weak_factory_.GetWeakPtr())));
return;
}
case UPGRADE_SUCCESSFUL: {
content::RecordAction(UserMetricsAction("UpgradeCheck_Upgraded"));
status = NEARLY_UPDATED;
break;
}
case UPGRADE_ERROR: {
content::RecordAction(UserMetricsAction("UpgradeCheck_Error"));
status = FAILED;
if (error_code == GOOGLE_UPDATE_DISABLED_BY_POLICY) {
message =
l10n_util::GetStringUTF16(IDS_UPGRADE_DISABLED_BY_POLICY);
} else if (error_code == GOOGLE_UPDATE_DISABLED_BY_POLICY_AUTO_ONLY) {
message =
l10n_util::GetStringUTF16(IDS_UPGRADE_DISABLED_BY_POLICY_MANUAL);
} else {
message =
l10n_util::GetStringFUTF16Int(IDS_UPGRADE_ERROR, error_code);
}
if (!error_message.empty()) {
message +=
l10n_util::GetStringFUTF16(IDS_ABOUT_BOX_ERROR_DURING_UPDATE_CHECK,
error_message);
}
break;
}
}
callback_.Run(status, 0, message);
#endif
}
void VersionUpdaterWin::GotInstalledVersion(const Version& version) {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
chrome::VersionInfo version_info;
Version running_version(version_info.Version());
if (!version.IsValid() || version.CompareTo(running_version) <= 0) {
content::RecordAction(
UserMetricsAction("UpgradeCheck_AlreadyUpToDate"));
callback_.Run(UPDATED, 0, base::string16());
} else {
content::RecordAction(UserMetricsAction("UpgradeCheck_AlreadyUpgraded"));
callback_.Run(NEARLY_UPDATED, 0, base::string16());
}
}
void VersionUpdaterWin::CreateGoogleUpdater() {
ClearGoogleUpdater();
google_updater_ = new GoogleUpdate();
google_updater_->set_status_listener(this);
}
void VersionUpdaterWin::ClearGoogleUpdater() {
if (google_updater_) {
google_updater_->set_status_listener(NULL);
google_updater_ = NULL;
}
}
BOOL CALLBACK WindowEnumeration(HWND window, LPARAM param) {
if (IsWindowVisible(window)) {
HWND* returned_window = reinterpret_cast<HWND*>(param);
*returned_window = window;
return FALSE;
}
return TRUE;
}
HWND VersionUpdaterWin::GetElevationParent() {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
HWND window = NULL;
EnumThreadWindows(GetCurrentThreadId(),
WindowEnumeration,
reinterpret_cast<LPARAM>(&window));
#if !defined(USE_AURA)
DCHECK(window != NULL) << "Failed to find a valid window handle on thread: "
<< GetCurrentThreadId();
#endif
return window;
}
}
VersionUpdater* VersionUpdater::Create() {
return new VersionUpdaterWin;
}