// Copyright (c) 2012 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 "content/browser/browsing_instance.h"

#include "base/command_line.h"
#include "base/logging.h"
#include "content/browser/site_instance_impl.h"
#include "content/public/browser/browser_context.h"
#include "content/public/browser/content_browser_client.h"
#include "content/public/common/content_switches.h"
#include "content/public/common/url_constants.h"

namespace content {

BrowsingInstance::BrowsingInstance(BrowserContext* browser_context)
    : browser_context_(browser_context) {
}

bool BrowsingInstance::HasSiteInstance(const GURL& url) {
  std::string site =
      SiteInstanceImpl::GetSiteForURL(browser_context_, url)
          .possibly_invalid_spec();

  return site_instance_map_.find(site) != site_instance_map_.end();
}

SiteInstance* BrowsingInstance::GetSiteInstanceForURL(const GURL& url) {
  std::string site =
      SiteInstanceImpl::GetSiteForURL(browser_context_, url)
          .possibly_invalid_spec();

  SiteInstanceMap::iterator i = site_instance_map_.find(site);
  if (i != site_instance_map_.end())
    return i->second;


  // No current SiteInstance for this site, so let's create one.
  SiteInstanceImpl* instance = new SiteInstanceImpl(this);

  // Set the site of this new SiteInstance, which will register it with us.
  instance->SetSite(url);
  return instance;
}

void BrowsingInstance::RegisterSiteInstance(SiteInstance* site_instance) {
  DCHECK(static_cast<SiteInstanceImpl*>(site_instance)
             ->browsing_instance_.get() ==
         this);
  DCHECK(static_cast<SiteInstanceImpl*>(site_instance)->HasSite());
  std::string site = site_instance->GetSiteURL().possibly_invalid_spec();

  // Only register if we don't have a SiteInstance for this site already.
  // It's possible to have two SiteInstances point to the same site if two
  // tabs are navigated there at the same time.  (We don't call SetSite or
  // register them until DidNavigate.)  If there is a previously existing
  // SiteInstance for this site, we just won't register the new one.
  SiteInstanceMap::iterator i = site_instance_map_.find(site);
  if (i == site_instance_map_.end()) {
    // Not previously registered, so register it.
    site_instance_map_[site] = site_instance;
  }
}

void BrowsingInstance::UnregisterSiteInstance(SiteInstance* site_instance) {
  DCHECK(static_cast<SiteInstanceImpl*>(site_instance)
             ->browsing_instance_.get() ==
         this);
  DCHECK(static_cast<SiteInstanceImpl*>(site_instance)->HasSite());
  std::string site = site_instance->GetSiteURL().possibly_invalid_spec();

  // Only unregister the SiteInstance if it is the same one that is registered
  // for the site.  (It might have been an unregistered SiteInstance.  See the
  // comments in RegisterSiteInstance.)
  SiteInstanceMap::iterator i = site_instance_map_.find(site);
  if (i != site_instance_map_.end() && i->second == site_instance) {
    // Matches, so erase it.
    site_instance_map_.erase(i);
  }
}

BrowsingInstance::~BrowsingInstance() {
  // We should only be deleted when all of the SiteInstances that refer to
  // us are gone.
  DCHECK(site_instance_map_.empty());
}

}  // namespace content
