// Copyright 2017 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <sstream>
#include "base/strings/string_split.h"
#include "base/strings/string_util.h"
#include "content/common/content_security_policy/csp_context.h"

namespace content {

namespace {

static CSPDirective::Name CSPFallback(CSPDirective::Name directive) {
  switch (directive) {
    case CSPDirective::DefaultSrc:
    case CSPDirective::FormAction:
    case CSPDirective::UpgradeInsecureRequests:
      return CSPDirective::Unknown;

    case CSPDirective::FrameSrc:
      return CSPDirective::ChildSrc;

    case CSPDirective::ChildSrc:
      return CSPDirective::DefaultSrc;

    case CSPDirective::Unknown:
      NOTREACHED();
      return CSPDirective::Unknown;
  }
  NOTREACHED();
  return CSPDirective::Unknown;
}

std::string ElideURLForReportViolation(const GURL& url) {
  // TODO(arthursonzogni): the url length should be limited to 1024 char. Find
  // a function that will not break the utf8 encoding while eliding the string.
  return url.spec();
}

void ReportViolation(CSPContext* context,
                     const ContentSecurityPolicy& policy,
                     const CSPDirective& directive,
                     const CSPDirective::Name directive_name,
                     const GURL& url,
                     bool is_redirect,
                     const SourceLocation& source_location) {
  // We should never have a violation against `child-src` or `default-src`
  // directly; the effective directive should always be one of the explicit
  // fetch directives.
  DCHECK_NE(directive_name, CSPDirective::DefaultSrc);
  DCHECK_NE(directive_name, CSPDirective::ChildSrc);

  // For security reasons, some urls must not be disclosed. This includes the
  // blocked url and the source location of the error. Care must be taken to
  // ensure that these are not transmitted between different cross-origin
  // renderers.
  GURL safe_url = url;
  SourceLocation safe_source_location = source_location;
  context->SanitizeDataForUseInCspViolation(is_redirect, directive_name,
                                            &safe_url, &safe_source_location);

  std::stringstream message;

  if (policy.header.type == blink::kWebContentSecurityPolicyTypeReport)
    message << "[Report Only] ";

  if (directive_name == CSPDirective::FormAction)
    message << "Refused to send form data to '";
  else if (directive_name == CSPDirective::FrameSrc)
    message << "Refused to frame '";

  message << ElideURLForReportViolation(safe_url)
          << "' because it violates the following Content Security Policy "
             "directive: \""
          << directive.ToString() << "\".";

  if (directive.name != directive_name)
    message << " Note that '" << CSPDirective::NameToString(directive_name)
            << "' was not explicitly set, so '"
            << CSPDirective::NameToString(directive.name)
            << "' is used as a fallback.";

  message << "\n";

  context->ReportContentSecurityPolicyViolation(CSPViolationParams(
      CSPDirective::NameToString(directive.name),
      CSPDirective::NameToString(directive_name), message.str(), safe_url,
      policy.report_endpoints, policy.use_reporting_api,
      policy.header.header_value, policy.header.type, is_redirect,
      safe_source_location));
}

bool AllowDirective(CSPContext* context,
                    const ContentSecurityPolicy& policy,
                    const CSPDirective& directive,
                    CSPDirective::Name directive_name,
                    const GURL& url,
                    bool is_redirect,
                    const SourceLocation& source_location) {
  if (CSPSourceList::Allow(directive.source_list, url, context, is_redirect))
    return true;

  ReportViolation(context, policy, directive, directive_name, url, is_redirect,
                  source_location);
  return false;
}

const GURL ExtractInnerURL(const GURL& url) {
  if (const GURL* inner_url = url.inner_url())
    return *inner_url;
  else
    // TODO(arthursonzogni): revisit this once GURL::inner_url support blob-URL.
    return GURL(url.path());
}

bool ShouldBypassContentSecurityPolicy(CSPContext* context, const GURL& url) {
  if (url.SchemeIsFileSystem() || url.SchemeIsBlob()) {
    return context->SchemeShouldBypassCSP(ExtractInnerURL(url).scheme());
  } else {
    return context->SchemeShouldBypassCSP(url.scheme());
  }
}

}  // namespace

ContentSecurityPolicy::ContentSecurityPolicy() = default;

ContentSecurityPolicy::ContentSecurityPolicy(
    const ContentSecurityPolicyHeader& header,
    const std::vector<CSPDirective>& directives,
    const std::vector<std::string>& report_endpoints,
    bool use_reporting_api)
    : header(header),
      directives(directives),
      report_endpoints(report_endpoints),
      use_reporting_api(use_reporting_api) {}

ContentSecurityPolicy::ContentSecurityPolicy(
    const ContentSecurityPolicy& other) = default;

ContentSecurityPolicy::~ContentSecurityPolicy() = default;

// static
bool ContentSecurityPolicy::Allow(const ContentSecurityPolicy& policy,
                                  CSPDirective::Name directive_name,
                                  const GURL& url,
                                  bool is_redirect,
                                  CSPContext* context,
                                  const SourceLocation& source_location) {
  if (ShouldBypassContentSecurityPolicy(context, url)) return true;

  CSPDirective::Name current_directive_name = directive_name;
  do {
    for (const CSPDirective& directive : policy.directives) {
      if (directive.name == current_directive_name) {
        bool allowed =
            AllowDirective(context, policy, directive, directive_name, url,
                           is_redirect, source_location);
        return allowed ||
               policy.header.type == blink::kWebContentSecurityPolicyTypeReport;
      }
    }
    current_directive_name = CSPFallback(current_directive_name);
  } while (current_directive_name != CSPDirective::Unknown);
  return true;
}

std::string ContentSecurityPolicy::ToString() const {
  std::stringstream text;
  bool is_first_policy = true;
  for (const CSPDirective& directive : directives) {
    if (!is_first_policy)
      text << "; ";
    is_first_policy = false;
    text << directive.ToString();
  }

  if (!report_endpoints.empty()) {
    if (!is_first_policy)
      text << "; ";
    is_first_policy = false;
    text << "report-uri";
    for (const std::string& endpoint : report_endpoints)
      text << " " << endpoint;
  }

  return text.str();
}

// static
bool ContentSecurityPolicy::ShouldUpgradeInsecureRequest(
    const ContentSecurityPolicy& policy) {
  for (const CSPDirective& directive : policy.directives) {
    if (directive.name == CSPDirective::UpgradeInsecureRequests)
      return true;
  }
  return false;
}

}  // namespace content
