diff options
author | mad@chromium.org <mad@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-09-12 04:12:52 +0000 |
---|---|---|
committer | mad@chromium.org <mad@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-09-12 04:12:52 +0000 |
commit | a683b57737059aac1ba465e11ce92017e6716d75 (patch) | |
tree | 4eebe25cab3c078689478df89440748f690f703b /content/app | |
parent | b606eded570739fe01fb3cff27b91a037bf0161c (diff) | |
download | chromium_src-a683b57737059aac1ba465e11ce92017e6716d75.zip chromium_src-a683b57737059aac1ba465e11ce92017e6716d75.tar.gz chromium_src-a683b57737059aac1ba465e11ce92017e6716d75.tar.bz2 |
Prime the Windows theme DLL earlier.
On Windows 8, we need to check if we are touch-enabled before we load our resources, and this happens before the code to prime the theme DLL gets executed. Since checking for touch-enable requires a call into the theme dll, it didn't get properly initialized in the render process... So moving this code to be done earlier was required...
At the same time, I changed the code a bit to rely on the current window station to no be WinSta0 to decide whether we need to do this or not, as opposed to looking at the sandbox state.
BUG=139241
TEST=Make sure we always get the proper theme for UI controls like scrollbars.
Review URL: https://chromiumcodereview.appspot.com/10914119
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@156232 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'content/app')
-rw-r--r-- | content/app/content_main_runner.cc | 56 |
1 files changed, 56 insertions, 0 deletions
diff --git a/content/app/content_main_runner.cc b/content/app/content_main_runner.cc index 44421e8..14dbc9e 100644 --- a/content/app/content_main_runner.cc +++ b/content/app/content_main_runner.cc @@ -20,6 +20,7 @@ #include "base/path_service.h" #include "base/process_util.h" #include "base/profiler/alternate_timer.h" +#include "base/string_util.h" #include "base/stringprintf.h" #include "base/string_number_conversions.h" #include "content/browser/browser_main.h" @@ -95,6 +96,58 @@ extern int ZygoteMain(const MainFunctionParams&, } // namespace content #endif +namespace { +#if defined(OS_WIN) +// In order to have Theme support, we need to connect to the theme service. +// This needs to be done before we lock down the process. Officially this +// can be done with OpenThemeData() but it fails unless you pass a valid +// window at least the first time. Interestingly, the very act of creating a +// window also sets the connection to the theme service. +void EnableThemeSupportOnAllWindowStations() { + HDESK desktop_handle = ::OpenInputDesktop(0, FALSE, READ_CONTROL); + if (desktop_handle) { + // This means we are running in an input desktop, which implies WinSta0. + ::CloseDesktop(desktop_handle); + return; + } + + HWINSTA current_station = ::GetProcessWindowStation(); + DCHECK(current_station); + + HWINSTA winsta0 = ::OpenWindowStationA("WinSta0", FALSE, GENERIC_READ); + if (!winsta0 || !::SetProcessWindowStation(winsta0)) { + // Could not set the alternate window station. There is a possibility + // that the theme wont be correctly initialized. + NOTREACHED() << "Unable to switch to WinSta0, we: "<< ::GetLastError(); + } + + HWND window = ::CreateWindowExW(0, L"Static", L"", WS_POPUP | WS_DISABLED, + CW_USEDEFAULT, 0, 0, 0, HWND_MESSAGE, NULL, + ::GetModuleHandleA(NULL), NULL); + if (!window) { + DLOG(WARNING) << "failed to enable theme support"; + } else { + ::DestroyWindow(window); + window = NULL; + } + + // Revert the window station. + if (!::SetProcessWindowStation(current_station)) { + // We failed to switch back to the secure window station. This might + // confuse the process enough that we should kill it now. + LOG(FATAL) << "Failed to restore alternate window station"; + } + + if (!::CloseWindowStation(winsta0)) { + // We might be leaking a winsta0 handle. This is a security risk, but + // since we allow fail over to no desktop protection in low memory + // condition, this is not a big risk. + NOTREACHED(); + } +} +#endif // defined(OS_WIN) +} // namespace + namespace content { base::LazyInstance<ContentBrowserClient> @@ -563,6 +616,9 @@ static void ReleaseFreeMemoryThunk() { SendTaskPortToParentProcess(); } #elif defined(OS_WIN) + // This must be done early enough since some helper functions like + // IsTouchEnanbled, needed to load resources, may call into the theme dll. + EnableThemeSupportOnAllWindowStations(); #if defined(ENABLE_HIDPI) ui::EnableHighDPISupport(); #endif |