15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2010 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome_frame/navigation_constraints.h"
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "base/strings/string_util.h"
8868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "base/strings/utf_string_conversions.h"
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/url_constants.h"
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome_frame/utils.h"
112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "extensions/common/constants.h"
125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NavigationConstraintsImpl::NavigationConstraintsImpl() : is_privileged_(false) {
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// NavigationConstraintsImpl method definitions.
175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool NavigationConstraintsImpl::AllowUnsafeUrls() {
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // No sanity checks if unsafe URLs are allowed
195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return GetConfigBool(false, kAllowUnsafeURLs);
205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool NavigationConstraintsImpl::IsSchemeAllowed(const GURL& url) {
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (url.is_empty())
245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!url.is_valid())
275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (url.SchemeIs(chrome::kHttpScheme) ||
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      url.SchemeIs(chrome::kHttpsScheme))
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return true;
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Additional checking for view-source. Allow only http and https
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // URLs in view source.
35868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  if (url.SchemeIs(content::kViewSourceScheme)) {
36de1bd3ebc0808574e846315a068b6935d3e72d5fJonathan Dixon    GURL sub_url(url.GetContent());
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (sub_url.SchemeIs(chrome::kHttpScheme) ||
385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        sub_url.SchemeIs(chrome::kHttpsScheme))
395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return true;
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Allow only about:blank or about:version
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (url.SchemeIs(chrome::kAboutScheme)) {
4490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    if (LowerCaseEqualsASCII(url.spec(), content::kAboutBlankURL) ||
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        LowerCaseEqualsASCII(url.spec(), chrome::kAboutVersionURL)) {
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return true;
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (is_privileged_ &&
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      (url.SchemeIs(chrome::kDataScheme) ||
522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)       url.SchemeIs(extensions::kExtensionScheme))) {
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return true;
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return false;
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool NavigationConstraintsImpl::IsZoneAllowed(const GURL& url) {
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!security_manager_) {
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    HRESULT hr = security_manager_.CreateInstance(
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        CLSID_InternetSecurityManager);
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (FAILED(hr)) {
645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      NOTREACHED() << __FUNCTION__
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                   << " Failed to create SecurityManager. Error: 0x%x"
665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                   << hr;
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return true;
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DWORD zone = URLZONE_INVALID;
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    std::wstring unicode_url = UTF8ToWide(url.spec());
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    security_manager_->MapUrlToZone(unicode_url.c_str(), &zone, 0);
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (zone == URLZONE_UNTRUSTED) {
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      DLOG(WARNING) << __FUNCTION__
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                    << " Disallowing navigation to restricted url: " << url;
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return false;
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool NavigationConstraintsImpl::is_privileged() const {
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return is_privileged_;
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NavigationConstraintsImpl::set_is_privileged(bool is_privileged) {
865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  is_privileged_ = is_privileged;
875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
88