From 3c0ea7282d2a621b0a927ef4da43fa187863868c Mon Sep 17 00:00:00 2001 From: Andrea Marchesini Date: Wed, 29 Mar 2017 08:24:01 +0200 Subject: [PATCH] Bug 1347817 - Principal must always have a valid origin - part 4 - origin passed as argument when a principal is created, r=bholley --- caps/BasePrincipal.cpp | 28 ++++++++++++++++++++++++++-- caps/BasePrincipal.h | 35 ++++++++++++++++++----------------- caps/ContentPrincipal.cpp | 17 ++++++++--------- caps/ContentPrincipal.h | 9 +++++---- caps/ExpandedPrincipal.cpp | 6 +++--- caps/NullPrincipal.cpp | 2 +- ipc/glue/BackgroundUtils.cpp | 3 +-- 7 files changed, 62 insertions(+), 38 deletions(-) diff --git a/caps/BasePrincipal.cpp b/caps/BasePrincipal.cpp index 4dd3cb3163b0..418e18b8ce21 100644 --- a/caps/BasePrincipal.cpp +++ b/caps/BasePrincipal.cpp @@ -14,6 +14,7 @@ #include "nsIContentSecurityPolicy.h" #include "nsIObjectInputStream.h" #include "nsIObjectOutputStream.h" +#include "nsIStandardURL.h" #include "ContentPrincipal.h" #include "nsNetUtil.h" @@ -368,8 +369,31 @@ BasePrincipal::AddonHasPermission(const nsAString& aPerm) } already_AddRefed -BasePrincipal::CreateCodebasePrincipal(nsIURI* aURI, const OriginAttributes& aAttrs) +BasePrincipal::CreateCodebasePrincipal(nsIURI* aURI, + const OriginAttributes& aAttrs) { + MOZ_ASSERT(aURI); + + nsAutoCString originNoSuffix; + nsresult rv = + ContentPrincipal::GenerateOriginNoSuffixFromURI(aURI, originNoSuffix); + if (NS_WARN_IF(NS_FAILED(rv))) { + // If the generation of the origin fails, we still want to have a valid + // principal. Better to return a null principal here. + return NullPrincipal::Create(aAttrs); + } + + return CreateCodebasePrincipal(aURI, aAttrs, originNoSuffix); +} + +already_AddRefed +BasePrincipal::CreateCodebasePrincipal(nsIURI* aURI, + const OriginAttributes& aAttrs, + const nsACString& aOriginNoSuffix) +{ + MOZ_ASSERT(aURI); + MOZ_ASSERT(!aOriginNoSuffix.IsEmpty()); + // If the URI is supposed to inherit the security context of whoever loads it, // we shouldn't make a codebase principal for it. bool inheritsPrincipal; @@ -393,7 +417,7 @@ BasePrincipal::CreateCodebasePrincipal(nsIURI* aURI, const OriginAttributes& aAt // Mint a codebase principal. RefPtr codebase = new ContentPrincipal(); - rv = codebase->Init(aURI, aAttrs); + rv = codebase->Init(aURI, aAttrs, aOriginNoSuffix); NS_ENSURE_SUCCESS(rv, nullptr); return codebase.forget(); } diff --git a/caps/BasePrincipal.h b/caps/BasePrincipal.h index 1304a32da445..3f3c8344121b 100644 --- a/caps/BasePrincipal.h +++ b/caps/BasePrincipal.h @@ -75,9 +75,16 @@ public: virtual bool IsCodebasePrincipal() const { return false; }; static BasePrincipal* Cast(nsIPrincipal* aPrin) { return static_cast(aPrin); } + + static already_AddRefed + CreateCodebasePrincipal(const nsACString& aOrigin); + + // These following method may not create a codebase principal in case it's + // not possible to generate a correct origin from the passed URI. If this + // happens, a NullPrincipal is returned. + static already_AddRefed CreateCodebasePrincipal(nsIURI* aURI, const OriginAttributes& aAttrs); - static already_AddRefed CreateCodebasePrincipal(const nsACString& aOrigin); const OriginAttributes& OriginAttributesRef() final { return mOriginAttributes; } uint32_t AppId() const { return mOriginAttributes.mAppId; } @@ -130,6 +137,10 @@ protected: nsCOMPtr mPreloadCSP; private: + static already_AddRefed + CreateCodebasePrincipal(nsIURI* aURI, const OriginAttributes& aAttrs, + const nsACString& aOriginNoSuffix); + nsCOMPtr mOriginNoSuffix; nsCOMPtr mOriginSuffix; @@ -157,20 +168,13 @@ BasePrincipal::FastEquals(nsIPrincipal* aOther) return this == other; } - if (mOriginNoSuffix) { - if (Kind() == eCodebasePrincipal) { - return mOriginNoSuffix == other->mOriginNoSuffix && - mOriginSuffix == other->mOriginSuffix; - } - - MOZ_ASSERT(Kind() == eExpandedPrincipal); - return mOriginNoSuffix == other->mOriginNoSuffix; + if (Kind() == eCodebasePrincipal) { + return mOriginNoSuffix == other->mOriginNoSuffix && + mOriginSuffix == other->mOriginSuffix; } - // If mOriginNoSuffix is null on one of our principals, we must fall back - // to the slow path. - return Subsumes(aOther, DontConsiderDocumentDomain) && - other->Subsumes(this, DontConsiderDocumentDomain); + MOZ_ASSERT(Kind() == eExpandedPrincipal); + return mOriginNoSuffix == other->mOriginNoSuffix; } inline bool @@ -194,14 +198,11 @@ BasePrincipal::FastSubsumes(nsIPrincipal* aOther) // We deal with two special cases first: // Null principals only subsume each other if they are equal, and are only // equal if they're the same object. - // Also, if mOriginNoSuffix is null, FastEquals falls back to the slow path - // using Subsumes, so we don't want to use it in that case to avoid an - // infinite recursion. auto other = Cast(aOther); if (Kind() == eNullPrincipal && other->Kind() == eNullPrincipal) { return this == other; } - if (mOriginNoSuffix && FastEquals(aOther)) { + if (FastEquals(aOther)) { return true; } diff --git a/caps/ContentPrincipal.cpp b/caps/ContentPrincipal.cpp index 1cad5b833519..a3af0816e711 100644 --- a/caps/ContentPrincipal.cpp +++ b/caps/ContentPrincipal.cpp @@ -95,7 +95,8 @@ ContentPrincipal::~ContentPrincipal() nsresult ContentPrincipal::Init(nsIURI *aCodebase, - const OriginAttributes& aOriginAttributes) + const OriginAttributes& aOriginAttributes, + const nsACString& aOriginNoSuffix) { NS_ENSURE_ARG(aCodebase); @@ -115,13 +116,7 @@ ContentPrincipal::Init(nsIURI *aCodebase, mCodebase = NS_TryToMakeImmutable(aCodebase); mCodebaseImmutable = URIIsImmutable(mCodebase); - nsAutoCString originNoSuffix; - nsresult rv = GenerateOriginNoSuffixFromURI(mCodebase, originNoSuffix); - if (NS_WARN_IF(NS_FAILED(rv))) { - return rv; - } - - FinishInit(originNoSuffix, aOriginAttributes); + FinishInit(aOriginNoSuffix, aOriginAttributes); return NS_OK; } @@ -485,7 +480,11 @@ ContentPrincipal::Read(nsIObjectInputStream* aStream) rv = NS_ReadOptionalObject(aStream, true, getter_AddRefs(supports)); NS_ENSURE_SUCCESS(rv, rv); - rv = Init(codebase, attrs); + nsAutoCString originNoSuffix; + rv = GenerateOriginNoSuffixFromURI(codebase, originNoSuffix); + NS_ENSURE_SUCCESS(rv, rv); + + rv = Init(codebase, attrs, originNoSuffix); NS_ENSURE_SUCCESS(rv, rv); mCSP = do_QueryInterface(supports, &rv); diff --git a/caps/ContentPrincipal.h b/caps/ContentPrincipal.h index c46a400fe087..1d75cb8bdad7 100644 --- a/caps/ContentPrincipal.h +++ b/caps/ContentPrincipal.h @@ -32,7 +32,8 @@ public: // Init() must be called before the principal is in a usable state. nsresult Init(nsIURI* aCodebase, - const mozilla::OriginAttributes& aOriginAttributes); + const mozilla::OriginAttributes& aOriginAttributes, + const nsACString& aOriginNoSuffix); virtual nsresult GetScriptLocation(nsACString& aStr) override; @@ -41,6 +42,9 @@ public: */ static void InitializeStatics(); + static nsresult + GenerateOriginNoSuffixFromURI(nsIURI* aURI, nsACString& aOrigin); + nsCOMPtr mDomain; nsCOMPtr mCodebase; // If mCodebaseImmutable is true, mCodebase is non-null and immutable @@ -55,9 +59,6 @@ protected: bool MayLoadInternal(nsIURI* aURI) override; private: - static nsresult - GenerateOriginNoSuffixFromURI(nsIURI* aURI, nsACString& aOriginNoSuffix); - mozilla::Maybe mAddonIdCache; }; diff --git a/caps/ExpandedPrincipal.cpp b/caps/ExpandedPrincipal.cpp index 26e9e18ffd0e..b49166a95197 100644 --- a/caps/ExpandedPrincipal.cpp +++ b/caps/ExpandedPrincipal.cpp @@ -23,7 +23,7 @@ struct OriginComparator bool LessThan(nsIPrincipal* a, nsIPrincipal* b) const { nsAutoCString originA; - nsresult rv = a->GetOrigin(originA); + DebugOnly rv = a->GetOrigin(originA); MOZ_ASSERT(NS_SUCCEEDED(rv)); nsAutoCString originB; rv = b->GetOrigin(originB); @@ -34,7 +34,7 @@ struct OriginComparator bool Equals(nsIPrincipal* a, nsIPrincipal* b) const { nsAutoCString originA; - nsresult rv = a->GetOrigin(originA); + DebugOnly rv = a->GetOrigin(originA); MOZ_ASSERT(NS_SUCCEEDED(rv)); nsAutoCString originB; rv = b->GetOrigin(originB); @@ -71,7 +71,7 @@ ExpandedPrincipal::Create(nsTArray>& aWhiteList, } nsAutoCString subOrigin; - nsresult rv = ep->mPrincipals.ElementAt(i)->GetOrigin(subOrigin); + DebugOnly rv = ep->mPrincipals.ElementAt(i)->GetOrigin(subOrigin); MOZ_ASSERT(NS_SUCCEEDED(rv)); origin.Append(subOrigin); } diff --git a/caps/NullPrincipal.cpp b/caps/NullPrincipal.cpp index 980fc7833365..084262feb61b 100644 --- a/caps/NullPrincipal.cpp +++ b/caps/NullPrincipal.cpp @@ -85,7 +85,7 @@ NullPrincipal::Init(const OriginAttributes& aOriginAttributes, nsIURI* aURI) } nsAutoCString originNoSuffix; - nsresult rv = mURI->GetSpec(originNoSuffix); + DebugOnly rv = mURI->GetSpec(originNoSuffix); MOZ_ASSERT(NS_SUCCEEDED(rv)); FinishInit(originNoSuffix, aOriginAttributes); diff --git a/ipc/glue/BackgroundUtils.cpp b/ipc/glue/BackgroundUtils.cpp index d7a99677b47e..cebac1f3cb9b 100644 --- a/ipc/glue/BackgroundUtils.cpp +++ b/ipc/glue/BackgroundUtils.cpp @@ -89,8 +89,7 @@ PrincipalInfoToPrincipal(const PrincipalInfo& aPrincipalInfo, attrs = info.attrs(); } principal = BasePrincipal::CreateCodebasePrincipal(uri, attrs); - rv = principal ? NS_OK : NS_ERROR_FAILURE; - if (NS_WARN_IF(NS_FAILED(rv))) { + if (NS_WARN_IF(!principal)) { return nullptr; }