// Copyright 2015 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 "chrome/browser/site_details.h"

#include <stddef.h>
#include <stdint.h>

#include <memory>
#include <utility>
#include <vector>

#include "base/bind_helpers.h"
#include "base/files/file_path.h"
#include "base/macros.h"
#include "base/message_loop/message_loop.h"
#include "base/path_service.h"
#include "base/strings/stringprintf.h"
#include "base/test/histogram_tester.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/extensions/extension_browsertest.h"
#include "chrome/browser/extensions/test_extension_dir.h"
#include "chrome/browser/metrics/metrics_memory_details.h"
#include "chrome/browser/ui/browser.h"
#include "chrome/browser/ui/tabs/tab_strip_model.h"
#include "chrome/common/extensions/extension_process_policy.h"
#include "chrome/common/url_constants.h"
#include "chrome/test/base/in_process_browser_test.h"
#include "chrome/test/base/ui_test_utils.h"
#include "components/metrics/metrics_service.h"
#include "components/variations/metrics_util.h"
#include "content/public/browser/notification_service.h"
#include "content/public/browser/render_process_host.h"
#include "content/public/common/content_switches.h"
#include "content/public/test/browser_test_utils.h"
#include "content/public/test/test_utils.h"
#include "extensions/common/switches.h"
#include "extensions/common/value_builder.h"
#include "net/dns/mock_host_resolver.h"
#include "net/test/embedded_test_server/embedded_test_server.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"

using base::Bucket;
using content::WebContents;
using extensions::DictionaryBuilder;
using extensions::Extension;
using extensions::ListBuilder;
using extensions::TestExtensionDir;
using testing::ElementsAre;
using testing::PrintToString;

namespace {

class TestMemoryDetails : public MetricsMemoryDetails {
 public:
  TestMemoryDetails()
      : MetricsMemoryDetails(base::Bind(&base::DoNothing), nullptr) {}

  void StartFetchAndWait() {
    uma_.reset(new base::HistogramTester());
    StartFetch();
    content::RunMessageLoop();
  }

  // Returns a HistogramTester which observed the most recent call to
  // StartFetchAndWait().
  base::HistogramTester* uma() { return uma_.get(); }

  int GetOutOfProcessIframeCount() {
    std::vector<Bucket> buckets =
        uma_->GetAllSamples("SiteIsolation.OutOfProcessIframes");
    CHECK_EQ(1U, buckets.size());
    return buckets[0].min;
  }

  size_t CountPageTitles() {
    size_t count = 0;
    for (const ProcessMemoryInformation& process : ChromeBrowser()->processes) {
      if (process.process_type == content::PROCESS_TYPE_RENDERER) {
        count += process.titles.size();
      }
    }
    return count;
  }

 private:
  ~TestMemoryDetails() override {}

  void OnDetailsAvailable() override {
    MetricsMemoryDetails::OnDetailsAvailable();
    // Exit the loop initiated by StartFetchAndWait().
    base::MessageLoop::current()->QuitWhenIdle();
  }

  std::unique_ptr<base::HistogramTester> uma_;

  DISALLOW_COPY_AND_ASSIGN(TestMemoryDetails);
};

IsolationScenarioType GetCurrentPolicy() {
  if (content::AreAllSitesIsolatedForTesting())
    return ISOLATE_ALL_SITES;
#if BUILDFLAG(ENABLE_EXTENSIONS)
  return ISOLATE_EXTENSIONS;
#else
  return ISOLATE_NOTHING;
#endif
}

// This matcher takes three other matchers as arguments, and applies one of them
// depending on the current site isolation mode. The first applies if no site
// isolation mode is active; the second applies under --isolate-extensions mode;
// and the third applies under --site-per-process mode.
MATCHER_P3(DependingOnPolicy,
           isolate_nothing,
           isolate_extensions,
           isolate_all_sites,
           GetCurrentPolicy() == ISOLATE_NOTHING
               ? std::string("(with oopifs disabled) ") +
                     PrintToString(isolate_nothing)
               : GetCurrentPolicy() == ISOLATE_EXTENSIONS
                     ? std::string("(under --isolate-extensions) ") +
                           PrintToString(isolate_extensions)
                     : std::string("(under --site-per-process) ") +
                           PrintToString(isolate_all_sites)) {
  switch (GetCurrentPolicy()) {
    case ISOLATE_NOTHING:
      return ExplainMatchResult(isolate_nothing, arg, result_listener);
    case ISOLATE_EXTENSIONS:
      return ExplainMatchResult(isolate_extensions, arg, result_listener);
    case ISOLATE_ALL_SITES:
      return ExplainMatchResult(isolate_all_sites, arg, result_listener);
    default:
      return false;
  }
}

// Matcher for base::Bucket objects that allows bucket_min to be a matcher.
MATCHER_P2(Sample,
           bucket_min,
           count,
           std::string("is a Bucket whose count is ") + PrintToString(count) +
               std::string(" and whose value is ") +
               PrintToString(bucket_min)) {
  return ExplainMatchResult(count, arg.count, result_listener) &&
         ExplainMatchResult(bucket_min, arg.min, result_listener);
}

// Allow matchers to be pretty-printed when passed to PrintToString() for the
// cases we care about.
template <typename P1, typename P2, typename P3>
void PrintTo(const DependingOnPolicyMatcherP3<P1, P2, P3>& matcher,
             std::ostream* os) {
  testing::Matcher<int> matcherCast = matcher;
  matcherCast.DescribeTo(os);
}

template <typename P1, typename P2>
void PrintTo(const SampleMatcherP2<P1, P2>& matcher, std::ostream* os) {
  testing::Matcher<Bucket> matcherCast = matcher;
  matcherCast.DescribeTo(os);
}

// Matches a container of histogram samples, for the common case where the
// histogram received just one sample.
#define HasOneSample(x) ElementsAre(Sample(x, 1))

}  // namespace

class SiteDetailsBrowserTest : public ExtensionBrowserTest {
 public:
  SiteDetailsBrowserTest() {}
  ~SiteDetailsBrowserTest() override {}

  void SetUpOnMainThread() override {
    ExtensionBrowserTest::SetUpOnMainThread();
    host_resolver()->AddRule("*", "127.0.0.1");

    // Add content/test/data so we can use cross_site_iframe_factory.html
    base::FilePath test_data_dir;
    ASSERT_TRUE(PathService::Get(base::DIR_SOURCE_ROOT, &test_data_dir));
    embedded_test_server()->ServeFilesFromDirectory(
        test_data_dir.AppendASCII("content/test/data/"));
    ASSERT_TRUE(embedded_test_server()->Start());
  }

  // Create and install an extension that has a couple of web-accessible
  // resources and, optionally, a background process.
  const Extension* CreateExtension(const std::string& name,
                                   bool has_background_process) {
    std::unique_ptr<TestExtensionDir> dir(new TestExtensionDir);

    DictionaryBuilder manifest;
    manifest.Set("name", name)
        .Set("version", "1.0")
        .Set("manifest_version", 2)
        .Set("web_accessible_resources", ListBuilder()
                                             .Append("blank_iframe.html")
                                             .Append("http_iframe.html")
                                             .Append("two_http_iframes.html")
                                             .Build());

    if (has_background_process) {
      manifest.Set(
          "background",
          DictionaryBuilder()
              .Set("scripts", ListBuilder().Append("script.js").Build())
              .Build());
      dir->WriteFile(FILE_PATH_LITERAL("script.js"),
                     "console.log('" + name + " running');");
    }

    dir->WriteFile(FILE_PATH_LITERAL("blank_iframe.html"),
                   base::StringPrintf("<html><body>%s, blank iframe:"
                                      "  <iframe width=80 height=80></iframe>"
                                      "</body></html>",
                                      name.c_str()));
    std::string iframe_url =
        embedded_test_server()
            ->GetURL("w.com", "/cross_site_iframe_factory.html?w")
            .spec();
    std::string iframe_url2 =
        embedded_test_server()
            ->GetURL("x.com", "/cross_site_iframe_factory.html?x")
            .spec();
    dir->WriteFile(
        FILE_PATH_LITERAL("http_iframe.html"),
        base::StringPrintf("<html><body>%s, http:// iframe:"
                           "  <iframe width=80 height=80 src='%s'></iframe>"
                           "</body></html>",
                           name.c_str(), iframe_url.c_str()));
    dir->WriteFile(FILE_PATH_LITERAL("two_http_iframes.html"),
                   base::StringPrintf(
                       "<html><body>%s, two http:// iframes:"
                       "  <iframe width=80 height=80 src='%s'></iframe>"
                       "  <iframe width=80 height=80 src='%s'></iframe>"
                       "</body></html>",
                       name.c_str(), iframe_url.c_str(), iframe_url2.c_str()));
    dir->WriteManifest(manifest.ToJSON());

    const Extension* extension = LoadExtension(dir->UnpackedPath());
    EXPECT_TRUE(extension);
    temp_dirs_.push_back(std::move(dir));
    return extension;
  }

  // Creates a V2 platform app that loads a web iframe in the app's sandbox
  // page.
  // TODO(lazyboy): Deprecate this behavior in https://crbug.com/615585.
  void CreateAppWithSandboxPage(const std::string& name) {
    std::unique_ptr<TestExtensionDir> dir(new TestExtensionDir);

    DictionaryBuilder manifest;
    manifest.Set("name", name)
        .Set("version", "1.0")
        .Set("manifest_version", 2)
        .Set("sandbox",
             DictionaryBuilder()
                 .Set("pages", ListBuilder().Append("sandbox.html").Build())
                 .Build())
        .Set("app",
             DictionaryBuilder()
                 .Set("background",
                      DictionaryBuilder()
                          .Set("scripts",
                               ListBuilder().Append("background.js").Build())
                          .Build())
                 .Build());

    dir->WriteFile(FILE_PATH_LITERAL("background.js"),
                   "var sandboxFrame = document.createElement('iframe');"
                   "sandboxFrame.src = 'sandbox.html';"
                   "document.body.appendChild(sandboxFrame);");

    std::string iframe_url =
        embedded_test_server()->GetURL("/title1.html").spec();
    dir->WriteFile(
        FILE_PATH_LITERAL("sandbox.html"),
        base::StringPrintf("<html><body>%s, web iframe:"
                           "  <iframe width=80 height=80 src=%s></iframe>"
                           "</body></html>",
                           name.c_str(), iframe_url.c_str()));
    dir->WriteManifest(manifest.ToJSON());

    const Extension* extension = LoadExtension(dir->UnpackedPath());
    EXPECT_TRUE(extension);
    temp_dirs_.push_back(std::move(dir));
  }

  const Extension* CreateHostedApp(const std::string& name,
                                   const GURL& app_url) {
    std::unique_ptr<TestExtensionDir> dir(new TestExtensionDir);

    DictionaryBuilder manifest;
    manifest.Set("name", name)
        .Set("version", "1.0")
        .Set("manifest_version", 2)
        .Set(
            "app",
            DictionaryBuilder()
                .Set("urls", ListBuilder().Append(app_url.spec()).Build())
                .Set("launch",
                     DictionaryBuilder().Set("web_url", app_url.spec()).Build())
                .Build());
    dir->WriteManifest(manifest.ToJSON());

    const Extension* extension = LoadExtension(dir->UnpackedPath());
    EXPECT_TRUE(extension);
    temp_dirs_.push_back(std::move(dir));
    return extension;
  }

  int GetRenderProcessCount() {
    int count = 0;
    for (content::RenderProcessHost::iterator it(
             content::RenderProcessHost::AllHostsIterator());
         !it.IsAtEnd(); it.Advance()) {
      count++;
    }
    return count;
  }

 private:
  std::vector<std::unique_ptr<TestExtensionDir>> temp_dirs_;
  DISALLOW_COPY_AND_ASSIGN(SiteDetailsBrowserTest);
};


// Test the accuracy of SiteDetails process estimation, in the presence of
// multiple iframes, navigation, multiple BrowsingInstances, and multiple tabs
// in the same BrowsingInstance.
IN_PROC_BROWSER_TEST_F(SiteDetailsBrowserTest, ManyIframes) {
  // Page with 14 nested oopifs across 9 sites (a.com through i.com).
  // None of these are https.
  GURL abcdefghi_url = embedded_test_server()->GetURL(
      "a.com",
      "/cross_site_iframe_factory.html?a(b(a(b,c,d,e,f,g,h)),c,d,e,i(f))");
  ui_test_utils::NavigateToURL(browser(), abcdefghi_url);

  // Get the metrics.
  scoped_refptr<TestMemoryDetails> details = new TestMemoryDetails();
  details->StartFetchAndWait();

  EXPECT_EQ(1U, details->CountPageTitles());
  EXPECT_THAT(
      details->uma()->GetAllSamples("SiteIsolation.BrowsingInstanceCount"),
      HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountEstimate"),
              HasOneSample(9));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountLowerBound"),
              HasOneSample(9));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountNoLimit"),
              HasOneSample(9));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountNoLimit"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(1));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(1, 1, 9));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 0, 14));
  EXPECT_THAT(details->uma()->GetAllSamples("SiteIsolation.ProxyCount"),
              HasOneSample(DependingOnPolicy(0, 0, 114)));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.ProxyCountPerBrowsingInstance"),
              HasOneSample(DependingOnPolicy(0, 0, 114)));

  // Navigate to a different, disjoint set of 7 sites.
  GURL pqrstuv_url = embedded_test_server()->GetURL(
      "p.com",
      "/cross_site_iframe_factory.html?p(q(r),r(s),s(t),t(q),u(u),v(p))");
  ui_test_utils::NavigateToURL(browser(), pqrstuv_url);

  details = new TestMemoryDetails();
  details->StartFetchAndWait();

  EXPECT_EQ(1U, details->CountPageTitles());
  EXPECT_THAT(
      details->uma()->GetAllSamples("SiteIsolation.BrowsingInstanceCount"),
      HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountEstimate"),
              HasOneSample(7));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountLowerBound"),
              HasOneSample(7));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountNoLimit"),
              HasOneSample(7));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountNoLimit"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(1));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(1, 1, 7));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 0, 11));
  EXPECT_THAT(details->uma()->GetAllSamples("SiteIsolation.ProxyCount"),
              HasOneSample(DependingOnPolicy(0, 0, 68)));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.ProxyCountPerBrowsingInstance"),
              HasOneSample(DependingOnPolicy(0, 0, 68)));

  // Open a second tab (different BrowsingInstance) with 4 sites (a through d).
  GURL abcd_url = embedded_test_server()->GetURL(
      "a.com", "/cross_site_iframe_factory.html?a(b(c(d())))");
  AddTabAtIndex(1, abcd_url, ui::PAGE_TRANSITION_TYPED);

  details = new TestMemoryDetails();
  details->StartFetchAndWait();

  EXPECT_EQ(2U, details->CountPageTitles());
  EXPECT_THAT(
      details->uma()->GetAllSamples("SiteIsolation.BrowsingInstanceCount"),
      HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountEstimate"),
              HasOneSample(11));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountLowerBound"),
              HasOneSample(11));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountNoLimit"),
              HasOneSample(11));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountEstimate"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountLowerBound"),
              HasOneSample(1));  // TODO(nick): This should be 2.
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountNoLimit"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(2));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(2, 2, 11));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 0, 14));
  EXPECT_THAT(details->uma()->GetAllSamples("SiteIsolation.ProxyCount"),
              HasOneSample(DependingOnPolicy(0, 0, 81)));
  EXPECT_THAT(
      details->uma()->GetAllSamples(
          "SiteIsolation.ProxyCountPerBrowsingInstance"),
      DependingOnPolicy(ElementsAre(Bucket(0, 2)), ElementsAre(Bucket(0, 2)),
                        ElementsAre(Bucket(12, 1), Bucket(68, 1))));

  // Open a third tab (different BrowsingInstance) with the same 4 sites.
  AddTabAtIndex(2, abcd_url, ui::PAGE_TRANSITION_TYPED);

  details = new TestMemoryDetails();
  details->StartFetchAndWait();

  EXPECT_THAT(
      details->uma()->GetAllSamples("SiteIsolation.BrowsingInstanceCount"),
      HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(3));
  // Could be 11 if subframe processes were reused across BrowsingInstances.
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountEstimate"),
              HasOneSample(15));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountLowerBound"),
              HasOneSample(11));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountNoLimit"),
              HasOneSample(15));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountLowerBound"),
              HasOneSample(1));  // TODO(nick): This should be 3.
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountNoLimit"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(3));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(3, 3, 15));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 0, 17));
  EXPECT_THAT(details->uma()->GetAllSamples("SiteIsolation.ProxyCount"),
              HasOneSample(DependingOnPolicy(0, 0, 96)));
  EXPECT_THAT(
      details->uma()->GetAllSamples(
          "SiteIsolation.ProxyCountPerBrowsingInstance"),
      DependingOnPolicy(ElementsAre(Bucket(0, 3)), ElementsAre(Bucket(0, 3)),
                        ElementsAre(Bucket(12, 2), Bucket(68, 1))));

  // From the third tab, window.open() a fourth tab in the same
  // BrowsingInstance, to a page using the same four sites "a-d" as third tab,
  // plus an additional site "e". The estimated process counts should increase
  // by one (not five) from the previous scenario, as the new tab can reuse the
  // four processes already in the BrowsingInstance.
  GURL dcbae_url = embedded_test_server()->GetURL(
      "a.com", "/cross_site_iframe_factory.html?d(c(b(a(e))))");
  ui_test_utils::UrlLoadObserver load_complete(
      dcbae_url, content::NotificationService::AllSources());
  ASSERT_EQ(3, browser()->tab_strip_model()->count());
  ASSERT_TRUE(content::ExecuteScript(
      browser()->tab_strip_model()->GetActiveWebContents(),
      "window.open('" + dcbae_url.spec() + "');"));
  ASSERT_EQ(4, browser()->tab_strip_model()->count());
  load_complete.Wait();

  details = new TestMemoryDetails();
  details->StartFetchAndWait();

  EXPECT_THAT(
      details->uma()->GetAllSamples("SiteIsolation.BrowsingInstanceCount"),
      HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(3));
  // Could be 11 if subframe processes were reused across BrowsingInstances.
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountEstimate"),
              HasOneSample(16));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountLowerBound"),
              HasOneSample(12));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountNoLimit"),
              HasOneSample(16));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountLowerBound"),
              HasOneSample(1));  // TODO(nick): This should be 3.
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateHttpsSitesProcessCountNoLimit"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(3));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(3, 3, 16));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 0, 21));
  EXPECT_THAT(details->uma()->GetAllSamples("SiteIsolation.ProxyCount"),
              HasOneSample(DependingOnPolicy(0, 0, 114)));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.ProxyCountPerBrowsingInstance"),
              DependingOnPolicy(
                  ElementsAre(Bucket(0, 3)), ElementsAre(Bucket(0, 3)),
                  ElementsAre(Bucket(12, 1), Bucket(29, 1), Bucket(68, 1))));
}

// Flaky on Windows and Mac. crbug.com/671891
#if defined(OS_WIN) || defined(OS_MACOSX)
#define MAYBE_IsolateExtensions DISABLED_IsolateExtensions
#else
#define MAYBE_IsolateExtensions IsolateExtensions
#endif
IN_PROC_BROWSER_TEST_F(SiteDetailsBrowserTest, MAYBE_IsolateExtensions) {
  // We start on "about:blank", which should be credited with a process in this
  // case.
  scoped_refptr<TestMemoryDetails> details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(1));
  EXPECT_THAT(GetRenderProcessCount(), 1);
  EXPECT_EQ(0, details->GetOutOfProcessIframeCount());

  // Install one script-injecting extension with background page, and an
  // extension with web accessible resources.
  const Extension* extension1 = CreateExtension("Extension One", true);
  const Extension* extension2 = CreateExtension("Extension Two", false);

  // Open two a.com tabs (with cross site http iframes). IsolateExtensions mode
  // should have no effect so far, since there are no frames straddling the
  // extension/web boundary.
  GURL tab1_url = embedded_test_server()->GetURL(
      "a.com", "/cross_site_iframe_factory.html?a(b,c)");
  ui_test_utils::NavigateToURL(browser(), tab1_url);
  WebContents* tab1 = browser()->tab_strip_model()->GetWebContentsAt(0);
  GURL tab2_url = embedded_test_server()->GetURL(
      "a.com", "/cross_site_iframe_factory.html?a(d,e)");
  AddTabAtIndex(1, tab2_url, ui::PAGE_TRANSITION_TYPED);
  WebContents* tab2 = browser()->tab_strip_model()->GetWebContentsAt(1);

  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(3));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(3, 3, 7));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 0, 4));

  // Test that "one process per extension" applies even when web content has an
  // extension iframe.

  // Tab1 navigates its first iframe to a resource of extension1. This shouldn't
  // result in a new extension process (it should share with extension1's
  // background page).
  content::NavigateIframeToURL(
      tab1, "child-0", extension1->GetResourceURL("/blank_iframe.html"));
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(3));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(3, 3, 6));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 1, 4));

  // Tab2 navigates its first iframe to a resource of extension1. This also
  // shouldn't result in a new extension process (it should share with the
  // background page and the other iframe).
  content::NavigateIframeToURL(
      tab2, "child-0", extension1->GetResourceURL("/blank_iframe.html"));
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(3));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(3, 3, 5));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 2, 4));

  // Tab1 navigates its second iframe to a resource of extension2. This SHOULD
  // result in a new process since extension2 had no existing process.
  content::NavigateIframeToURL(
      tab1, "child-1", extension2->GetResourceURL("/blank_iframe.html"));
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(4));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(4));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(3, 4, 5));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 3, 4));

  // Tab2 navigates its second iframe to a resource of extension2. This should
  // share the existing extension2 process.
  content::NavigateIframeToURL(
      tab2, "child-1", extension2->GetResourceURL("/blank_iframe.html"));
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(4));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(4));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(3, 4, 4));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 4, 4));

  // Install extension3 (identical config to extension2)
  const Extension* extension3 = CreateExtension("Extension Three", false);

  // Navigate Tab2 to a top-level page from extension3. There are four processes
  // now: one for tab1's main frame, and one for each of the extensions:
  // extension1 has a process because it has a background page; extension2 is
  // used as an iframe in tab1, and extension3 is the top-level frame in tab2.
  ui_test_utils::NavigateToURL(browser(),
                               extension3->GetResourceURL("blank_iframe.html"));
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(4));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(4));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(4));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(3, 4, 4));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 2, 2));

  // Navigate tab2 to a different extension3 page containing a web iframe. The
  // iframe should get its own process. The lower bound number indicates that,
  // in theory, the iframe could share a process with tab1's main frame.
  ui_test_utils::NavigateToURL(browser(),
                               extension3->GetResourceURL("http_iframe.html"));
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(5));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(4));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(5));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(3, 5, 5));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 3, 3));

  // Navigate tab1 to an extension3 page with an extension3 iframe. There should
  // be three processes estimated by IsolateExtensions: one for extension3, one
  // for extension1's background page, and one for the web iframe in tab2.
  browser()->tab_strip_model()->ActivateTabAt(0, true);
  ui_test_utils::NavigateToURL(browser(),
                               extension3->GetResourceURL("blank_iframe.html"));
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(3));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(2, 3, 3));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 1, 1));

  // Now navigate tab1 to an extension3 page with a web iframe. This could share
  // a process with tab2's iframe (the LowerBound number), or it could get its
  // own process (the Estimate number).
  ui_test_utils::NavigateToURL(browser(),
                               extension3->GetResourceURL("http_iframe.html"));
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(4));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(3));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(4));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(2, 4, 4));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 2, 2));
}

// Due to http://crbug.com/612711, we are not isolating iframes from platform
// apps with --isolate-extenions.
IN_PROC_BROWSER_TEST_F(SiteDetailsBrowserTest, PlatformAppsNotIsolated) {
  // --site-per-process will still isolate iframes from platform apps, so skip
  // the test in that case.
  if (content::AreAllSitesIsolatedForTesting())
    return;
  CreateAppWithSandboxPage("Extension One");
  scoped_refptr<TestMemoryDetails> details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_EQ(0, details->GetOutOfProcessIframeCount());
}

// Exercises accounting in the case where an extension has two different-site
// web iframes.
IN_PROC_BROWSER_TEST_F(SiteDetailsBrowserTest, ExtensionWithTwoWebIframes) {
  scoped_refptr<TestMemoryDetails> details = new TestMemoryDetails();
  details->StartFetchAndWait();

  // Install one script-injecting extension with background page, and an
  // extension with web accessible resources.
  const Extension* extension = CreateExtension("Test Extension", false);

  ui_test_utils::NavigateToURL(
      browser(), extension->GetResourceURL("/two_http_iframes.html"));

  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(2));
  // TODO(nick): https://crbug.com/512560 Make the number below agree with the
  // estimates above, which assume consolidation of subframe processes.
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(1, 3, 3));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 2, 2));
}

// Verifies that --isolate-extensions doesn't isolate hosted apps.
IN_PROC_BROWSER_TEST_F(SiteDetailsBrowserTest, IsolateExtensionsHostedApps) {
  GURL app_with_web_iframe_url = embedded_test_server()->GetURL(
      "app.org", "/cross_site_iframe_factory.html?app.org(b.com)");
  GURL app_in_web_iframe_url = embedded_test_server()->GetURL(
      "b.com", "/cross_site_iframe_factory.html?b.com(app.org)");

  // No hosted app is installed: app.org just behaves like a normal domain.
  ui_test_utils::NavigateToURL(browser(), app_with_web_iframe_url);
  scoped_refptr<TestMemoryDetails> details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(1));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(1, 1, 2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountEstimate"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountLowerBound"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountNoLimit"),
              HasOneSample(2));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(1, 1, 2));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 0, 1));

  ui_test_utils::NavigateToURL(browser(), app_in_web_iframe_url);
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(1));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(1, 1, 2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountEstimate"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountLowerBound"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountNoLimit"),
              HasOneSample(2));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(1, 1, 2));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 0, 1));

  // Now install app.org as a hosted app.
  CreateHostedApp("App", GURL("http://app.org"));

  // Reload the same two pages, and verify that the hosted app still is not
  // isolated by --isolate-extensions, but is isolated by --site-per-process.
  ui_test_utils::NavigateToURL(browser(), app_with_web_iframe_url);
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(1));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(1, 1, 2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountEstimate"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountLowerBound"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountNoLimit"),
              HasOneSample(2));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(1, 1, 2));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 0, 1));

  ui_test_utils::NavigateToURL(browser(), app_in_web_iframe_url);
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.CurrentRendererProcessCount"),
              HasOneSample(GetRenderProcessCount()));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateNothingProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountEstimate"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountLowerBound"),
              HasOneSample(1));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateExtensionsProcessCountNoLimit"),
              HasOneSample(1));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(1, 1, 2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountEstimate"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountLowerBound"),
              HasOneSample(2));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.IsolateAllSitesProcessCountNoLimit"),
              HasOneSample(2));
  EXPECT_THAT(GetRenderProcessCount(), DependingOnPolicy(1, 1, 2));
  EXPECT_THAT(details->GetOutOfProcessIframeCount(),
              DependingOnPolicy(0, 0, 1));
}

// Verifies that the UMA counter for SiteInstances in a BrowsingInstance is
// correct when using tabs with web pages.
IN_PROC_BROWSER_TEST_F(SiteDetailsBrowserTest,
                       VerifySiteInstanceCountInBrowsingInstance) {
  // Page with 14 nested oopifs across 9 sites (a.com through i.com).
  GURL abcdefghi_url = embedded_test_server()->GetURL(
      "a.com",
      "/cross_site_iframe_factory.html?a(b(a(b,c,d,e,f,g,h)),c,d,e,i(f))");
  ui_test_utils::NavigateToURL(browser(), abcdefghi_url);

  // Get the metrics.
  scoped_refptr<TestMemoryDetails> details = new TestMemoryDetails();
  details->StartFetchAndWait();

  // Since there are no extensions involved, the results in the default case
  // and extensions::IsIsolateExtensionsEnabled() are the same.
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.SiteInstancesPerBrowsingInstance"),
              HasOneSample(DependingOnPolicy(1, 1, 9)));
  EXPECT_THAT(details->uma()->GetAllSamples("SiteIsolation.ProxyCount"),
              HasOneSample(DependingOnPolicy(0, 0, 114)));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.ProxyCountPerBrowsingInstance"),
              HasOneSample(DependingOnPolicy(0, 0, 114)));

  // Open another tab through window.open(), which will be in the same
  // BrowsingInstance.
  GURL dcbae_url = embedded_test_server()->GetURL(
      "a.com", "/cross_site_iframe_factory.html?d(c(b(j(k))))");
  ui_test_utils::UrlLoadObserver load_complete(
      dcbae_url, content::NotificationService::AllSources());
  ASSERT_EQ(1, browser()->tab_strip_model()->count());
  ASSERT_TRUE(content::ExecuteScript(
      browser()->tab_strip_model()->GetActiveWebContents(),
      "window.open('" + dcbae_url.spec() + "');"));
  ASSERT_EQ(2, browser()->tab_strip_model()->count());
  load_complete.Wait();

  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.SiteInstancesPerBrowsingInstance"),
              HasOneSample(DependingOnPolicy(1, 1, 11)));
  EXPECT_THAT(details->uma()->GetAllSamples("SiteIsolation.ProxyCount"),
              HasOneSample(DependingOnPolicy(0, 0, 160)));
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.ProxyCountPerBrowsingInstance"),
              HasOneSample(DependingOnPolicy(0, 0, 160)));

  // Open a tab, which will be in a different BrowsingInstance.
  GURL abcd_url = embedded_test_server()->GetURL(
      "a.com", "/cross_site_iframe_factory.html?a(b(c(d())))");
  AddTabAtIndex(1, abcd_url, ui::PAGE_TRANSITION_TYPED);

  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(
      details->uma()->GetAllSamples(
          "SiteIsolation.SiteInstancesPerBrowsingInstance"),
      DependingOnPolicy(ElementsAre(Sample(1, 2)), ElementsAre(Sample(1, 2)),
                        ElementsAre(Sample(4, 1), Sample(11, 1))));
  EXPECT_THAT(details->uma()->GetAllSamples("SiteIsolation.ProxyCount"),
              HasOneSample(DependingOnPolicy(0, 0, 160)));
  EXPECT_THAT(
      details->uma()->GetAllSamples(
          "SiteIsolation.ProxyCountPerBrowsingInstance"),
      DependingOnPolicy(ElementsAre(Sample(0, 2)), ElementsAre(Sample(0, 2)),
                        ElementsAre(Sample(12, 1), Sample(160, 1))));
}

// Verifies that the UMA counter for SiteInstances in a BrowsingInstance is
// correct when extensions and web pages are mixed together.
IN_PROC_BROWSER_TEST_F(
    SiteDetailsBrowserTest,
    VerifySiteInstanceCountInBrowsingInstanceWithExtensions) {
  // Open two a.com tabs (with cross site http iframes). IsolateExtensions mode
  // should have no effect so far, since there are no frames straddling the
  // extension/web boundary.
  GURL tab_url = embedded_test_server()->GetURL(
      "a.com", "/cross_site_iframe_factory.html?a(b,c,d(e))");
  ui_test_utils::NavigateToURL(browser(), tab_url);
  WebContents* tab = browser()->tab_strip_model()->GetWebContentsAt(0);
  scoped_refptr<TestMemoryDetails> details = new TestMemoryDetails();
  details->StartFetchAndWait();

  // Since there are no extensions loaded yet, the results in the default case
  // and extensions::IsIsolateExtensionsEnabled() are the same.
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.SiteInstancesPerBrowsingInstance"),
              HasOneSample(DependingOnPolicy(1, 1, 5)));

  // Load an extension without a background page, which will avoid creating a
  // BrowsingInstance for it.
  const Extension* extension1 = CreateExtension("Extension One", false);

  // Navigate the tab's first iframe to a resource of the extension. The
  // extension iframe will be put in the same BrowsingInstance as it is part
  // of the frame tree.
  content::NavigateIframeToURL(
      tab, "child-0", extension1->GetResourceURL("/blank_iframe.html"));
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.SiteInstancesPerBrowsingInstance"),
              HasOneSample(DependingOnPolicy(1, 2, 5)));

  // Now load an extension with a background page. This will result in a
  // BrowsingInstance for the background page.
  const Extension* extension2 = CreateExtension("Extension Two", true);
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.SiteInstancesPerBrowsingInstance"),
              DependingOnPolicy(ElementsAre(Bucket(1, 2)),
                                ElementsAre(Bucket(1, 1), Bucket(2, 1)),
                                ElementsAre(Bucket(1, 1), Bucket(5, 1))));

  // Navigate the second iframe of the tab to the second extension. It should
  // stay in the same BrowsingInstance as the page.
  content::NavigateIframeToURL(
      tab, "child-1", extension2->GetResourceURL("/blank_iframe.html"));
  details = new TestMemoryDetails();
  details->StartFetchAndWait();
  EXPECT_THAT(details->uma()->GetAllSamples(
                  "SiteIsolation.SiteInstancesPerBrowsingInstance"),
              DependingOnPolicy(ElementsAre(Bucket(1, 2)),
                                ElementsAre(Bucket(1, 1), Bucket(3, 1)),
                                ElementsAre(Bucket(1, 1), Bucket(5, 1))));
}
