2015-05-03 19:32:37 +00:00
|
|
|
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
|
|
|
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
2012-05-21 11:12:37 +00:00
|
|
|
/* This Source Code Form is subject to the terms of the Mozilla Public
|
|
|
|
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
|
|
|
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
2001-11-11 01:15:22 +00:00
|
|
|
|
2018-03-06 09:25:52 +00:00
|
|
|
#include "nsCSSFrameConstructor.h"
|
2011-10-28 07:35:45 +00:00
|
|
|
#include "nsTArray.h"
|
|
|
|
#include "nsString.h"
|
2001-11-11 01:15:22 +00:00
|
|
|
#include "nsIDocument.h"
|
|
|
|
#include "nsIContent.h"
|
|
|
|
#include "nsIPresShell.h"
|
2012-05-23 18:46:04 +00:00
|
|
|
#include "nsXBLService.h"
|
2001-11-11 01:15:22 +00:00
|
|
|
#include "nsIServiceManager.h"
|
|
|
|
#include "nsXBLResourceLoader.h"
|
|
|
|
#include "nsXBLPrototypeResources.h"
|
|
|
|
#include "nsIDocumentObserver.h"
|
|
|
|
#include "imgILoader.h"
|
2012-10-12 12:43:01 +00:00
|
|
|
#include "imgRequestProxy.h"
|
2018-03-22 18:20:41 +00:00
|
|
|
#include "mozilla/ComputedStyle.h"
|
2016-09-26 12:03:25 +00:00
|
|
|
#include "mozilla/StyleSheet.h"
|
|
|
|
#include "mozilla/StyleSheetInlines.h"
|
2010-06-28 22:49:35 +00:00
|
|
|
#include "mozilla/css/Loader.h"
|
2001-11-11 01:15:22 +00:00
|
|
|
#include "nsIURI.h"
|
|
|
|
#include "nsNetUtil.h"
|
2007-01-30 00:06:41 +00:00
|
|
|
#include "nsGkAtoms.h"
|
2003-03-06 23:59:18 +00:00
|
|
|
#include "nsXBLPrototypeBinding.h"
|
2004-10-13 23:45:22 +00:00
|
|
|
#include "nsContentUtils.h"
|
2009-03-17 01:38:36 +00:00
|
|
|
#include "nsIScriptSecurityManager.h"
|
2001-11-11 01:15:22 +00:00
|
|
|
|
2014-06-20 10:32:49 +00:00
|
|
|
using namespace mozilla;
|
|
|
|
|
2014-04-25 16:49:00 +00:00
|
|
|
NS_IMPL_CYCLE_COLLECTION(nsXBLResourceLoader, mBoundElements)
|
2007-03-08 11:17:16 +00:00
|
|
|
|
2007-04-25 16:35:27 +00:00
|
|
|
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(nsXBLResourceLoader)
|
2007-03-08 11:17:16 +00:00
|
|
|
NS_INTERFACE_MAP_ENTRY(nsICSSLoaderObserver)
|
|
|
|
NS_INTERFACE_MAP_ENTRY(nsISupports)
|
|
|
|
NS_INTERFACE_MAP_END
|
|
|
|
|
|
|
|
NS_IMPL_CYCLE_COLLECTING_ADDREF(nsXBLResourceLoader)
|
|
|
|
NS_IMPL_CYCLE_COLLECTING_RELEASE(nsXBLResourceLoader)
|
2001-11-11 01:15:22 +00:00
|
|
|
|
2013-02-01 10:56:02 +00:00
|
|
|
struct nsXBLResource
|
|
|
|
{
|
|
|
|
nsXBLResource* mNext;
|
2017-10-02 22:05:19 +00:00
|
|
|
nsAtom* mType;
|
2013-02-01 10:56:02 +00:00
|
|
|
nsString mSrc;
|
|
|
|
|
2017-10-02 22:05:19 +00:00
|
|
|
nsXBLResource(nsAtom* aType, const nsAString& aSrc)
|
2013-02-01 10:56:02 +00:00
|
|
|
{
|
|
|
|
MOZ_COUNT_CTOR(nsXBLResource);
|
|
|
|
mNext = nullptr;
|
|
|
|
mType = aType;
|
|
|
|
mSrc = aSrc;
|
|
|
|
}
|
|
|
|
|
|
|
|
~nsXBLResource()
|
|
|
|
{
|
|
|
|
MOZ_COUNT_DTOR(nsXBLResource);
|
|
|
|
NS_CONTENT_DELETE_LIST_MEMBER(nsXBLResource, this, mNext);
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
2003-03-06 23:59:18 +00:00
|
|
|
nsXBLResourceLoader::nsXBLResourceLoader(nsXBLPrototypeBinding* aBinding,
|
|
|
|
nsXBLPrototypeResources* aResources)
|
2018-04-13 13:01:28 +00:00
|
|
|
:mBinding(aBinding),
|
|
|
|
mResources(aResources),
|
|
|
|
mResourceList(nullptr),
|
|
|
|
mLastResource(nullptr),
|
|
|
|
mLoadingResources(false),
|
|
|
|
mInLoadResourcesFunc(false),
|
2018-06-15 14:01:06 +00:00
|
|
|
mPendingSheets(0),
|
|
|
|
mBoundDocument(nullptr)
|
2001-11-11 01:15:22 +00:00
|
|
|
{
|
|
|
|
}
|
|
|
|
|
|
|
|
nsXBLResourceLoader::~nsXBLResourceLoader()
|
|
|
|
{
|
|
|
|
delete mResourceList;
|
|
|
|
}
|
|
|
|
|
2017-06-05 06:29:31 +00:00
|
|
|
bool
|
2017-06-05 06:30:52 +00:00
|
|
|
nsXBLResourceLoader::LoadResources(nsIContent* aBoundElement)
|
2001-11-11 01:15:22 +00:00
|
|
|
{
|
2011-10-17 14:59:28 +00:00
|
|
|
mInLoadResourcesFunc = true;
|
2001-11-11 01:15:22 +00:00
|
|
|
|
|
|
|
if (mLoadingResources) {
|
2011-10-17 14:59:28 +00:00
|
|
|
mInLoadResourcesFunc = false;
|
2017-06-05 06:29:31 +00:00
|
|
|
return mPendingSheets == 0;
|
2001-11-11 01:15:22 +00:00
|
|
|
}
|
|
|
|
|
2011-10-17 14:59:28 +00:00
|
|
|
mLoadingResources = true;
|
2001-11-11 01:15:22 +00:00
|
|
|
|
|
|
|
// Declare our loaders.
|
2010-07-15 01:55:54 +00:00
|
|
|
nsCOMPtr<nsIDocument> doc = mBinding->XBLDocumentInfo()->GetDocument();
|
2017-06-05 05:06:52 +00:00
|
|
|
mBoundDocument = aBoundElement->OwnerDoc();
|
2001-11-11 01:15:22 +00:00
|
|
|
|
2010-03-02 21:00:53 +00:00
|
|
|
mozilla::css::Loader* cssLoader = doc->CSSLoader();
|
2018-03-28 15:34:34 +00:00
|
|
|
MOZ_ASSERT(cssLoader->GetDocument(), "Loader must have document");
|
2017-06-05 06:30:52 +00:00
|
|
|
|
2004-01-09 23:54:21 +00:00
|
|
|
nsIURI *docURL = doc->GetDocumentURI();
|
2007-08-08 01:16:09 +00:00
|
|
|
nsIPrincipal* docPrincipal = doc->NodePrincipal();
|
2001-11-11 01:15:22 +00:00
|
|
|
|
|
|
|
nsCOMPtr<nsIURI> url;
|
|
|
|
|
|
|
|
for (nsXBLResource* curr = mResourceList; curr; curr = curr->mNext) {
|
2002-01-24 02:03:19 +00:00
|
|
|
if (curr->mSrc.IsEmpty())
|
2001-11-11 01:15:22 +00:00
|
|
|
continue;
|
|
|
|
|
2004-10-13 23:45:22 +00:00
|
|
|
if (NS_FAILED(NS_NewURI(getter_AddRefs(url), curr->mSrc,
|
2017-06-18 11:37:50 +00:00
|
|
|
doc->GetDocumentCharacterSet(), docURL)))
|
2001-11-11 01:15:22 +00:00
|
|
|
continue;
|
|
|
|
|
2007-01-30 00:06:41 +00:00
|
|
|
if (curr->mType == nsGkAtoms::image) {
|
2002-09-17 18:59:41 +00:00
|
|
|
// Now kick off the image load...
|
2013-04-03 01:14:24 +00:00
|
|
|
// Passing nullptr for pretty much everything -- cause we don't care!
|
2017-05-10 03:45:11 +00:00
|
|
|
// XXX: initialDocumentURI is nullptr!
|
2015-10-18 05:24:48 +00:00
|
|
|
RefPtr<imgRequestProxy> req;
|
2017-09-21 00:09:00 +00:00
|
|
|
nsContentUtils::LoadImage(url, doc, doc, docPrincipal, 0, docURL,
|
2014-11-18 13:46:53 +00:00
|
|
|
doc->GetReferrerPolicy(), nullptr,
|
2013-10-16 01:35:44 +00:00
|
|
|
nsIRequest::LOAD_BACKGROUND, EmptyString(),
|
2004-10-13 23:16:58 +00:00
|
|
|
getter_AddRefs(req));
|
2001-11-11 01:15:22 +00:00
|
|
|
}
|
2007-01-30 00:06:41 +00:00
|
|
|
else if (curr->mType == nsGkAtoms::stylesheet) {
|
2001-11-11 01:15:22 +00:00
|
|
|
// Kick off the load of the stylesheet.
|
2002-12-03 05:48:14 +00:00
|
|
|
|
2003-04-18 08:44:25 +00:00
|
|
|
// Always load chrome synchronously
|
2007-07-11 19:44:27 +00:00
|
|
|
// XXXbz should that still do a content policy check?
|
2011-09-29 06:19:26 +00:00
|
|
|
bool chrome;
|
2003-07-18 01:26:47 +00:00
|
|
|
nsresult rv;
|
2003-04-18 08:44:25 +00:00
|
|
|
if (NS_SUCCEEDED(url->SchemeIs("chrome", &chrome)) && chrome)
|
|
|
|
{
|
2009-03-17 01:38:36 +00:00
|
|
|
rv = nsContentUtils::GetSecurityManager()->
|
|
|
|
CheckLoadURIWithPrincipal(docPrincipal, url,
|
|
|
|
nsIScriptSecurityManager::ALLOW_CHROME);
|
|
|
|
if (NS_SUCCEEDED(rv)) {
|
2016-09-26 12:03:25 +00:00
|
|
|
RefPtr<StyleSheet> sheet;
|
2016-02-24 07:01:12 +00:00
|
|
|
rv = cssLoader->LoadSheetSync(url, &sheet);
|
2009-03-17 01:38:36 +00:00
|
|
|
NS_ASSERTION(NS_SUCCEEDED(rv), "Load failed!!!");
|
|
|
|
if (NS_SUCCEEDED(rv))
|
|
|
|
{
|
2011-10-17 14:59:28 +00:00
|
|
|
rv = StyleSheetLoaded(sheet, false, NS_OK);
|
2009-03-17 01:38:36 +00:00
|
|
|
NS_ASSERTION(NS_SUCCEEDED(rv), "Processing the style sheet failed!!!");
|
|
|
|
}
|
2003-04-18 08:44:25 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2017-08-29 13:01:42 +00:00
|
|
|
rv = cssLoader->LoadSheet(url, false, docPrincipal, nullptr, this);
|
2005-09-12 18:41:15 +00:00
|
|
|
if (NS_SUCCEEDED(rv))
|
|
|
|
++mPendingSheets;
|
2003-04-18 08:44:25 +00:00
|
|
|
}
|
2001-11-11 01:15:22 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2011-10-17 14:59:28 +00:00
|
|
|
mInLoadResourcesFunc = false;
|
2017-05-10 03:45:11 +00:00
|
|
|
|
2001-11-11 01:15:22 +00:00
|
|
|
// Destroy our resource list.
|
|
|
|
delete mResourceList;
|
2012-07-30 14:20:58 +00:00
|
|
|
mResourceList = nullptr;
|
2017-06-05 06:29:31 +00:00
|
|
|
|
|
|
|
return mPendingSheets == 0;
|
2001-11-11 01:15:22 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// nsICSSLoaderObserver
|
|
|
|
NS_IMETHODIMP
|
2016-09-26 12:03:25 +00:00
|
|
|
nsXBLResourceLoader::StyleSheetLoaded(StyleSheet* aSheet,
|
2018-04-24 17:17:33 +00:00
|
|
|
bool aWasDeferred,
|
2005-09-12 18:41:15 +00:00
|
|
|
nsresult aStatus)
|
2001-11-11 01:15:22 +00:00
|
|
|
{
|
2004-01-05 23:46:00 +00:00
|
|
|
if (!mResources) {
|
|
|
|
// Our resources got destroyed -- just bail out
|
|
|
|
return NS_OK;
|
|
|
|
}
|
2017-05-10 03:45:11 +00:00
|
|
|
|
2014-06-19 07:02:56 +00:00
|
|
|
mResources->AppendStyleSheet(aSheet);
|
2001-11-11 01:15:22 +00:00
|
|
|
|
|
|
|
if (!mInLoadResourcesFunc)
|
|
|
|
mPendingSheets--;
|
2017-05-10 03:45:11 +00:00
|
|
|
|
2001-11-11 01:15:22 +00:00
|
|
|
if (mPendingSheets == 0) {
|
2017-05-10 03:45:11 +00:00
|
|
|
// All stylesheets are loaded.
|
2018-03-23 16:01:34 +00:00
|
|
|
mResources->ComputeServoStyles(
|
2018-03-29 11:15:46 +00:00
|
|
|
*mBoundDocument->GetShell()->StyleSet());
|
2001-11-11 01:15:22 +00:00
|
|
|
|
|
|
|
// XXX Check for mPendingScripts when scripts also come online.
|
|
|
|
if (!mInLoadResourcesFunc)
|
|
|
|
NotifyBoundElements();
|
|
|
|
}
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
2017-05-10 03:45:11 +00:00
|
|
|
void
|
2017-10-02 22:05:19 +00:00
|
|
|
nsXBLResourceLoader::AddResource(nsAtom* aResourceType, const nsAString& aSrc)
|
2001-11-11 01:15:22 +00:00
|
|
|
{
|
|
|
|
nsXBLResource* res = new nsXBLResource(aResourceType, aSrc);
|
|
|
|
if (!mResourceList)
|
|
|
|
mResourceList = res;
|
|
|
|
else
|
|
|
|
mLastResource->mNext = res;
|
|
|
|
|
|
|
|
mLastResource = res;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2017-05-10 03:45:11 +00:00
|
|
|
nsXBLResourceLoader::AddResourceListener(nsIContent* aBoundElement)
|
2001-11-11 01:15:22 +00:00
|
|
|
{
|
2007-03-11 11:56:09 +00:00
|
|
|
if (aBoundElement) {
|
|
|
|
mBoundElements.AppendObject(aBoundElement);
|
2018-02-14 22:22:46 +00:00
|
|
|
aBoundElement->OwnerDoc()->BlockOnload();
|
2001-11-11 01:15:22 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
nsXBLResourceLoader::NotifyBoundElements()
|
|
|
|
{
|
2012-05-23 18:46:04 +00:00
|
|
|
nsXBLService* xblService = nsXBLService::GetInstance();
|
|
|
|
if (!xblService)
|
|
|
|
return;
|
|
|
|
|
2003-11-17 21:03:32 +00:00
|
|
|
nsIURI* bindingURI = mBinding->BindingURI();
|
2001-11-11 01:15:22 +00:00
|
|
|
|
2012-08-22 15:56:38 +00:00
|
|
|
uint32_t eltCount = mBoundElements.Count();
|
|
|
|
for (uint32_t j = 0; j < eltCount; j++) {
|
2007-03-11 11:56:09 +00:00
|
|
|
nsCOMPtr<nsIContent> content = mBoundElements.ObjectAt(j);
|
2017-04-17 16:01:37 +00:00
|
|
|
MOZ_ASSERT(content->IsElement());
|
2018-02-14 22:22:46 +00:00
|
|
|
content->OwnerDoc()->UnblockOnload(/* aFireSync = */ false);
|
2017-04-17 16:01:37 +00:00
|
|
|
|
2011-09-29 06:19:26 +00:00
|
|
|
bool ready = false;
|
2001-11-11 01:15:22 +00:00
|
|
|
xblService->BindingReady(content, bindingURI, &ready);
|
|
|
|
|
2018-03-29 00:56:57 +00:00
|
|
|
if (!ready) {
|
|
|
|
continue;
|
|
|
|
}
|
2001-11-11 01:15:22 +00:00
|
|
|
|
2018-03-29 00:56:57 +00:00
|
|
|
nsIDocument* doc = content->GetUncomposedDoc();
|
|
|
|
if (!doc) {
|
|
|
|
continue;
|
2001-11-11 01:15:22 +00:00
|
|
|
}
|
2018-03-29 00:56:57 +00:00
|
|
|
|
|
|
|
nsIPresShell* shell = doc->GetShell();
|
|
|
|
if (!shell) {
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
|
|
|
|
shell->PostRecreateFramesFor(content->AsElement());
|
2001-11-11 01:15:22 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Clear out the whole array.
|
2007-03-11 11:56:09 +00:00
|
|
|
mBoundElements.Clear();
|
2001-11-11 01:15:22 +00:00
|
|
|
|
|
|
|
// Delete ourselves.
|
2014-04-10 14:05:21 +00:00
|
|
|
mResources->ClearLoader();
|
2001-11-11 01:15:22 +00:00
|
|
|
}
|
2011-11-03 20:39:08 +00:00
|
|
|
|
|
|
|
nsresult
|
|
|
|
nsXBLResourceLoader::Write(nsIObjectOutputStream* aStream)
|
|
|
|
{
|
|
|
|
nsresult rv;
|
|
|
|
|
|
|
|
for (nsXBLResource* curr = mResourceList; curr; curr = curr->mNext) {
|
|
|
|
if (curr->mType == nsGkAtoms::image)
|
|
|
|
rv = aStream->Write8(XBLBinding_Serialize_Image);
|
|
|
|
else if (curr->mType == nsGkAtoms::stylesheet)
|
|
|
|
rv = aStream->Write8(XBLBinding_Serialize_Stylesheet);
|
|
|
|
else
|
|
|
|
continue;
|
|
|
|
|
|
|
|
NS_ENSURE_SUCCESS(rv, rv);
|
|
|
|
|
|
|
|
rv = aStream->WriteWStringZ(curr->mSrc.get());
|
|
|
|
NS_ENSURE_SUCCESS(rv, rv);
|
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|