site_instance.h revision 5f1c94371a64b3196d4be9466099bb892df9b88e
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#ifndef CONTENT_PUBLIC_BROWSER_SITE_INSTANCE_H_ 6#define CONTENT_PUBLIC_BROWSER_SITE_INSTANCE_H_ 7 8#include "base/basictypes.h" 9#include "base/memory/ref_counted.h" 10#include "content/common/content_export.h" 11#include "url/gurl.h" 12 13namespace content { 14class BrowserContext; 15class RenderProcessHost; 16 17/////////////////////////////////////////////////////////////////////////////// 18// SiteInstance interface. 19// 20// A SiteInstance represents a group of web pages that may be able to 21// synchronously script each other, and thus must live in the same renderer 22// process. 23// 24// We identify this group using a combination of where the page comes from 25// (the site) and which tabs have references to each other (the instance). 26// Here, a "site" is similar to the page's origin, but it only includes the 27// registered domain name and scheme, not the port or subdomains. This accounts 28// for the fact that changes to document.domain allow similar origin pages with 29// different ports or subdomains to script each other. An "instance" includes 30// all tabs that might be able to script each other because of how they were 31// created (e.g., window.open or targeted links). We represent instances using 32// the BrowsingInstance class. 33// 34// Process models: 35// 36// In process-per-site-instance (the current default process model), 37// SiteInstances are created (1) when the user manually creates a new tab 38// (which also creates a new BrowsingInstance), and (2) when the user navigates 39// across site boundaries (which uses the same BrowsingInstance). If the user 40// navigates within a site, the same SiteInstance is used. 41// (Caveat: we currently allow renderer-initiated cross-site navigations to 42// stay in the same SiteInstance, to preserve compatibility in cases like 43// cross-site iframes that open popups.) 44// 45// In --process-per-tab, SiteInstances are created when the user manually 46// creates a new tab, but not when navigating across site boundaries (unless 47// a process swap is required for security reasons, such as navigating from 48// a privileged WebUI page to a normal web page). This corresponds to one 49// process per BrowsingInstance. 50// 51// In --process-per-site, we consolidate all SiteInstances for a given site into 52// the same process, throughout the entire browser context. This ensures that 53// only one process will be used for each site. 54// 55// Each NavigationEntry for a WebContents points to the SiteInstance that 56// rendered it. Each RenderViewHost also points to the SiteInstance that it is 57// associated with. A SiteInstance keeps track of the number of these 58// references and deletes itself when the count goes to zero. This means that 59// a SiteInstance is only live as long as it is accessible, either from new 60// tabs with no NavigationEntries or in NavigationEntries in the history. 61// 62/////////////////////////////////////////////////////////////////////////////// 63class CONTENT_EXPORT SiteInstance : public base::RefCounted<SiteInstance> { 64 public: 65 // Returns a unique ID for this SiteInstance. 66 virtual int32 GetId() = 0; 67 68 // Whether this SiteInstance has a running process associated with it. 69 // This may return true before the first call to GetProcess(), in cases where 70 // we use process-per-site and there is an existing process available. 71 virtual bool HasProcess() const = 0; 72 73 // Returns the current RenderProcessHost being used to render pages for this 74 // SiteInstance. If there is no RenderProcessHost (because either none has 75 // yet been created or there was one but it was cleanly destroyed (e.g. when 76 // it is not actively being used)), then this method will create a new 77 // RenderProcessHost (and a new ID). Note that renderer process crashes leave 78 // the current RenderProcessHost (and ID) in place. 79 // 80 // For sites that require process-per-site mode (e.g., WebUI), this will 81 // ensure only one RenderProcessHost for the site exists/ within the 82 // BrowserContext. 83 virtual content::RenderProcessHost* GetProcess() = 0; 84 85 // Browser context to which this SiteInstance (and all related 86 // SiteInstances) belongs. 87 virtual content::BrowserContext* GetBrowserContext() const = 0; 88 89 // Get the web site that this SiteInstance is rendering pages for. 90 // This includes the scheme and registered domain, but not the port. 91 virtual const GURL& GetSiteURL() const = 0; 92 93 // Gets a SiteInstance for the given URL that shares the current 94 // BrowsingInstance, creating a new SiteInstance if necessary. This ensures 95 // that a BrowsingInstance only has one SiteInstance per site, so that pages 96 // in a BrowsingInstance have the ability to script each other. Callers 97 // should ensure that this SiteInstance becomes ref counted, by storing it in 98 // a scoped_refptr. (By having this method, we can hide the BrowsingInstance 99 // class from the rest of the codebase.) 100 // TODO(creis): This may be an argument to build a pass_refptr<T> class, as 101 // Darin suggests. 102 virtual SiteInstance* GetRelatedSiteInstance(const GURL& url) = 0; 103 104 // Returns whether the given SiteInstance is in the same BrowsingInstance as 105 // this one. If so, JavaScript interactions that are permitted across 106 // origins (e.g., postMessage) should be supported. 107 virtual bool IsRelatedSiteInstance(const SiteInstance* instance) = 0; 108 109 // Returns the total active WebContents count for this SiteInstance and all 110 // related SiteInstances in the same BrowsingInstance. 111 virtual size_t GetRelatedActiveContentsCount() = 0; 112 113 // Factory method to create a new SiteInstance. This will create a new 114 // new BrowsingInstance, so it should only be used when creating a new tab 115 // from scratch (or similar circumstances). Callers should ensure that 116 // this SiteInstance becomes ref counted, by storing it in a scoped_refptr. 117 // 118 // The render process host factory may be NULL. See SiteInstance constructor. 119 // 120 // TODO(creis): This may be an argument to build a pass_refptr<T> class, as 121 // Darin suggests. 122 static SiteInstance* Create(content::BrowserContext* browser_context); 123 124 // Factory method to get the appropriate SiteInstance for the given URL, in 125 // a new BrowsingInstance. Use this instead of Create when you know the URL, 126 // since it allows special site grouping rules to be applied (for example, 127 // to group chrome-ui pages into the same instance). 128 static SiteInstance* CreateForURL( 129 content::BrowserContext* browser_context, const GURL& url); 130 131 // Return whether both URLs are part of the same web site, for the purpose of 132 // assigning them to processes accordingly. The decision is currently based 133 // on the registered domain of the URLs (google.com, bbc.co.uk), as well as 134 // the scheme (https, http). This ensures that two pages will be in 135 // the same process if they can communicate with other via JavaScript. 136 // (e.g., docs.google.com and mail.google.com have DOM access to each other 137 // if they both set their document.domain properties to google.com.) 138 // Note that if the destination is a blank page, we consider that to be part 139 // of the same web site for the purposes for process assignment. 140 static bool IsSameWebSite(content::BrowserContext* browser_context, 141 const GURL& src_url, 142 const GURL& dest_url); 143 144 // Returns the site for the given URL, which includes only the scheme and 145 // registered domain. Returns an empty GURL if the URL has no host. 146 static GURL GetSiteForURL(BrowserContext* context, const GURL& url); 147 148 protected: 149 friend class base::RefCounted<SiteInstance>; 150 151 SiteInstance() {} 152 virtual ~SiteInstance() {} 153}; 154 155} // namespace content. 156 157#endif // CONTENT_PUBLIC_BROWSER_SITE_INSTANCE_H_ 158