Home | History | Annotate | Download | only in chrome_frame
      1 // Copyright (c) 2012 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_frame/policy_settings.h"
      6 
      7 #include <algorithm>
      8 
      9 #include "base/logging.h"
     10 #include "base/strings/string_util.h"
     11 #include "base/strings/utf_string_conversions.h"
     12 #include "base/win/registry.h"
     13 #include "chrome_frame/utils.h"
     14 #include "policy/policy_constants.h"
     15 
     16 namespace {
     17 
     18 // This array specifies the order in which registry keys are tested.  Do not
     19 // change this unless the decision is made product-wide (i.e., in Chrome's
     20 // configuration policy provider).
     21 const HKEY kRootKeys[] = {
     22   HKEY_LOCAL_MACHINE,
     23   HKEY_CURRENT_USER
     24 };
     25 
     26 }  // namespace
     27 
     28 PolicySettings::RendererForUrl PolicySettings::GetRendererForUrl(
     29     const wchar_t* url) {
     30   RendererForUrl renderer = default_renderer_;
     31   std::vector<std::wstring>::const_iterator it;
     32   for (it = renderer_exclusion_list_.begin();
     33        it != renderer_exclusion_list_.end(); ++it) {
     34     if (MatchPattern(url, (*it))) {
     35       renderer = (renderer == RENDER_IN_HOST) ?
     36           RENDER_IN_CHROME_FRAME : RENDER_IN_HOST;
     37       break;
     38     }
     39   }
     40   return renderer;
     41 }
     42 
     43 PolicySettings::RendererForUrl PolicySettings::GetRendererForContentType(
     44     const wchar_t* content_type) {
     45   DCHECK(content_type);
     46   RendererForUrl renderer = RENDERER_NOT_SPECIFIED;
     47   std::vector<std::wstring>::const_iterator it;
     48   for (it = content_type_list_.begin();
     49        it != content_type_list_.end(); ++it) {
     50     if (lstrcmpiW(content_type, (*it).c_str()) == 0) {
     51       renderer = RENDER_IN_CHROME_FRAME;
     52       break;
     53     }
     54   }
     55   return renderer;
     56 }
     57 
     58 const CommandLine& PolicySettings::AdditionalLaunchParameters() const {
     59   return additional_launch_parameters_;
     60 }
     61 
     62 // static
     63 void PolicySettings::ReadUrlSettings(
     64     RendererForUrl* default_renderer,
     65     std::vector<std::wstring>* renderer_exclusion_list) {
     66   DCHECK(default_renderer);
     67   DCHECK(renderer_exclusion_list);
     68 
     69   *default_renderer = RENDERER_NOT_SPECIFIED;
     70   renderer_exclusion_list->clear();
     71 
     72   base::win::RegKey config_key;
     73   DWORD value = RENDERER_NOT_SPECIFIED;
     74   std::wstring settings_value(
     75       ASCIIToWide(policy::key::kChromeFrameRendererSettings));
     76   for (int i = 0; i < arraysize(kRootKeys); ++i) {
     77     if ((config_key.Open(kRootKeys[i], policy::kRegistryChromePolicyKey,
     78                          KEY_READ) == ERROR_SUCCESS) &&
     79         (config_key.ReadValueDW(settings_value.c_str(),
     80                                 &value) == ERROR_SUCCESS)) {
     81         break;
     82     }
     83   }
     84 
     85   DCHECK(value == RENDERER_NOT_SPECIFIED ||
     86          value == RENDER_IN_HOST ||
     87          value == RENDER_IN_CHROME_FRAME)
     88       << "invalid default renderer setting: " << value;
     89 
     90   if (value != RENDER_IN_HOST && value != RENDER_IN_CHROME_FRAME) {
     91     DVLOG(1) << "default renderer not specified via policy";
     92   } else {
     93     *default_renderer = static_cast<RendererForUrl>(value);
     94     const char* exclusion_list_name = (*default_renderer == RENDER_IN_HOST) ?
     95         policy::key::kRenderInChromeFrameList :
     96         policy::key::kRenderInHostList;
     97 
     98     EnumerateKeyValues(config_key.Handle(),
     99         ASCIIToWide(exclusion_list_name).c_str(), renderer_exclusion_list);
    100 
    101     DVLOG(1) << "Default renderer as specified via policy: "
    102              << *default_renderer
    103              << " exclusion list size: " << renderer_exclusion_list->size();
    104   }
    105 }
    106 
    107 // static
    108 void PolicySettings::ReadMetadataCheckSettings(
    109     SkipMetadataCheck* skip_metadata_check) {
    110   DCHECK(skip_metadata_check);
    111 
    112   *skip_metadata_check = SKIP_METADATA_CHECK_NOT_SPECIFIED;
    113 
    114   base::win::RegKey config_key;
    115   DWORD value = SKIP_METADATA_CHECK_NOT_SPECIFIED;
    116   string16 settings_value(
    117       ASCIIToWide(policy::key::kSkipMetadataCheck));
    118   for (int i = 0; i < arraysize(kRootKeys); ++i) {
    119     if ((config_key.Open(kRootKeys[i], policy::kRegistryChromePolicyKey,
    120                          KEY_READ) == ERROR_SUCCESS) &&
    121         (config_key.ReadValueDW(settings_value.c_str(),
    122                                 &value) == ERROR_SUCCESS)) {
    123       break;
    124     }
    125   }
    126 
    127   DCHECK(value == SKIP_METADATA_CHECK_NOT_SPECIFIED ||
    128          value == SKIP_METADATA_CHECK_NO ||
    129          value == SKIP_METADATA_CHECK_YES)
    130       << "invalid skip metadata check setting: " << value;
    131 
    132   if (value != SKIP_METADATA_CHECK_NO && value != SKIP_METADATA_CHECK_YES) {
    133     DVLOG(1) << "metadata check not specified via policy";
    134   } else {
    135     *skip_metadata_check = static_cast<SkipMetadataCheck>(value);
    136     DVLOG(1) << "SkipMetadata check as specified via policy: "
    137              << *skip_metadata_check;
    138   }
    139 }
    140 
    141 // static
    142 void PolicySettings::ReadContentTypeSetting(
    143     std::vector<std::wstring>* content_type_list) {
    144   DCHECK(content_type_list);
    145 
    146   std::wstring sub_key(policy::kRegistryChromePolicyKey);
    147   sub_key += L"\\";
    148   sub_key += ASCIIToWide(policy::key::kChromeFrameContentTypes);
    149 
    150   content_type_list->clear();
    151   for (int i = 0; i < arraysize(kRootKeys) && content_type_list->empty();
    152        ++i) {
    153     EnumerateKeyValues(kRootKeys[i], sub_key.c_str(), content_type_list);
    154   }
    155 }
    156 
    157 // static
    158 void PolicySettings::ReadStringSetting(const char* value_name,
    159                                        std::wstring* value) {
    160   DCHECK(value);
    161   value->clear();
    162   base::win::RegKey config_key;
    163   std::wstring value_name_str(ASCIIToWide(value_name));
    164   for (int i = 0; i < arraysize(kRootKeys); ++i) {
    165     if ((config_key.Open(kRootKeys[i], policy::kRegistryChromePolicyKey,
    166                          KEY_READ) == ERROR_SUCCESS) &&
    167         (config_key.ReadValue(value_name_str.c_str(),
    168                               value) == ERROR_SUCCESS)) {
    169       break;
    170     }
    171   }
    172 }
    173 
    174 // static
    175 void PolicySettings::ReadBoolSetting(const char* value_name, bool* value) {
    176   DCHECK(value);
    177   base::win::RegKey config_key;
    178   string16 value_name_str(ASCIIToWide(value_name));
    179   DWORD dword_value = 0;
    180   for (int i = 0; i < arraysize(kRootKeys); ++i) {
    181     if ((config_key.Open(kRootKeys[i], policy::kRegistryChromePolicyKey,
    182                          KEY_QUERY_VALUE) == ERROR_SUCCESS) &&
    183         (config_key.ReadValueDW(value_name_str.c_str(),
    184                                 &dword_value) == ERROR_SUCCESS)) {
    185       *value = (dword_value != 0);
    186       break;
    187     }
    188   }
    189 }
    190 
    191 void PolicySettings::RefreshFromRegistry() {
    192   RendererForUrl default_renderer;
    193   SkipMetadataCheck skip_metadata_check;
    194   std::vector<std::wstring> renderer_exclusion_list;
    195   std::vector<std::wstring> content_type_list;
    196   std::wstring application_locale;
    197   CommandLine additional_launch_parameters(CommandLine::NO_PROGRAM);
    198   std::wstring additional_parameters_str;
    199   bool suppress_turndown_prompt = false;
    200 
    201   // Read the latest settings from the registry
    202   ReadUrlSettings(&default_renderer, &renderer_exclusion_list);
    203   ReadMetadataCheckSettings(&skip_metadata_check);
    204   ReadContentTypeSetting(&content_type_list);
    205   ReadStringSetting(policy::key::kApplicationLocaleValue, &application_locale);
    206   ReadStringSetting(policy::key::kAdditionalLaunchParameters,
    207                     &additional_parameters_str);
    208   if (!additional_parameters_str.empty()) {
    209     additional_parameters_str.insert(0, L"fake.exe ");
    210     additional_launch_parameters.ParseFromString(additional_parameters_str);
    211   }
    212   ReadBoolSetting(policy::key::kSuppressChromeFrameTurndownPrompt,
    213                   &suppress_turndown_prompt);
    214 
    215   // Nofail swap in the new values.  (Note: this is all that need be protected
    216   // under a mutex if/when this becomes thread safe.)
    217   using std::swap;
    218 
    219   swap(default_renderer_, default_renderer);
    220   swap(skip_metadata_check_, skip_metadata_check);
    221   swap(renderer_exclusion_list_, renderer_exclusion_list);
    222   swap(content_type_list_, content_type_list);
    223   swap(application_locale_, application_locale);
    224   swap(additional_launch_parameters_, additional_launch_parameters);
    225   swap(suppress_turndown_prompt_, suppress_turndown_prompt);
    226 }
    227 
    228 // static
    229 PolicySettings* PolicySettings::GetInstance() {
    230   return Singleton<PolicySettings>::get();
    231 }
    232