diff --git a/content/shared/public/nsXULAtomList.h b/content/shared/public/nsXULAtomList.h index 325cb398a7fc..e4bd1dfaaaab 100644 --- a/content/shared/public/nsXULAtomList.h +++ b/content/shared/public/nsXULAtomList.h @@ -260,6 +260,7 @@ XUL_ATOM(content, "content") XUL_ATOM(coalesceduplicatearcs, "coalesceduplicatearcs") XUL_ATOM(allownegativeassertions, "allownegativeassertions") XUL_ATOM(datasources, "datasources") +XUL_ATOM(statedatasource,"statedatasource") XUL_ATOM(commandupdater, "commandupdater") XUL_ATOM(keyset, "keyset") XUL_ATOM(element, "element") diff --git a/content/xul/templates/src/nsXULOutlinerBuilder.cpp b/content/xul/templates/src/nsXULOutlinerBuilder.cpp index 47d340a8dcf3..5ccf9fbde38d 100644 --- a/content/xul/templates/src/nsXULOutlinerBuilder.cpp +++ b/content/xul/templates/src/nsXULOutlinerBuilder.cpp @@ -53,6 +53,9 @@ #include "nsXULTemplateBuilder.h" #include "nsVoidArray.h" +// For security check +#include "nsIDocument.h" + /** * A XUL template builder that serves as an outliner view, allowing * (pretty much) arbitrary RDF to be presented in an outliner. @@ -604,13 +607,50 @@ nsXULOutlinerBuilder::SetOutliner(nsIOutlinerBoxObject* outliner) LoadDataSources(); - // So we can remember open state. - // - // XXX We should fix this so that if the document is - // ``trusted'', we use the localstore. - mPersistStateStore = - do_CreateInstance("@mozilla.org/rdf/datasource;1?name=in-memory-datasource"); + nsCOMPtr doc; + mRoot->GetDocument(*getter_AddRefs(doc)); + NS_ASSERTION(doc, "element has no document"); + if (!doc) + return NS_ERROR_UNEXPECTED; + // Grab the doc's principal... + nsCOMPtr docPrincipal; + nsresult rv = doc->GetPrincipal(getter_AddRefs(docPrincipal)); + if (NS_FAILED(rv)) + return rv; + + PRBool isTrusted = PR_FALSE; + rv = IsSystemPrincipal(docPrincipal.get(), &isTrusted); + if (NS_SUCCEEDED(rv) && isTrusted) { + // Get the datasource we intend to use to remember open state. + nsAutoString datasourceStr; + mRoot->GetAttr(kNameSpaceID_None, nsXULAtoms::statedatasource, datasourceStr); + + // since we are trusted, use the user specified datasource + // if non specified, use localstore, which gives us + // persistance across sessions + if (datasourceStr.Length()) { + gRDFService->GetDataSource(NS_ConvertUCS2toUTF8(datasourceStr).get(), + getter_AddRefs(mPersistStateStore)); + } + else { + gRDFService->GetDataSource("rdf:local-store", + getter_AddRefs(mPersistStateStore)); + } + } + + // Either no specific datasource was specified, or we failed + // to get one because we are not trusted. + // + // XXX if it were possible to ``write an arbitrary datasource + // back'', then we could also allow an untrusted document to + // use a statedatasource from the same codebase. + if (! mPersistStateStore) { + mPersistStateStore = + do_CreateInstance("@mozilla.org/rdf/datasource;1?name=in-memory-datasource"); + } + + NS_ASSERTION(mPersistStateStore, "failed to get a persistant state store"); if (! mPersistStateStore) return NS_ERROR_FAILURE; @@ -986,11 +1026,13 @@ nsXULOutlinerBuilder::ReplaceMatch(nsIRDFResource* aMember, // Use the persist store to remember if the container // is open or closed. PRBool open = PR_FALSE; - mPersistStateStore->HasAssertion(container, - nsXULContentUtils::NC_open, - nsXULContentUtils::true_, - PR_TRUE, - &open); + + if (mPersistStateStore) + mPersistStateStore->HasAssertion(container, + nsXULContentUtils::NC_open, + nsXULContentUtils::true_, + PR_TRUE, + &open); if (open) { parent = mRows.EnsureSubtreeFor(iter); diff --git a/content/xul/templates/src/nsXULTemplateBuilder.cpp b/content/xul/templates/src/nsXULTemplateBuilder.cpp index 64b9a3294f29..9556c2292a3e 100644 --- a/content/xul/templates/src/nsXULTemplateBuilder.cpp +++ b/content/xul/templates/src/nsXULTemplateBuilder.cpp @@ -779,7 +779,11 @@ nsXULTemplateBuilder::LoadDataSources() rv = doc->GetPrincipal(getter_AddRefs(docPrincipal)); if (NS_FAILED(rv)) return rv; - if (docPrincipal.get() == gSystemPrincipal) { + PRBool isTrusted = PR_FALSE; + rv = IsSystemPrincipal(docPrincipal.get(), &isTrusted); + if (NS_FAILED(rv)) return rv; + + if (isTrusted) { // If we're a privileged (e.g., chrome) document, then add the // local store as the first data source in the db. Note that // we _might_ not be able to get a local store if we haven't @@ -829,7 +833,7 @@ nsXULTemplateBuilder::LoadDataSources() // protocol) leaves uriStr unaltered. NS_MakeAbsoluteURI(uriStr, uriStr, docurl); - if (docPrincipal.get() != gSystemPrincipal) { + if (!isTrusted) { // Our document is untrusted, so check to see if we can // load the datasource that they've asked for. nsCOMPtr uri; @@ -2391,3 +2395,13 @@ nsXULTemplateBuilder::CanSetProperty(const nsIID * iid, const PRUnichar *propert return NS_OK; } +nsresult +nsXULTemplateBuilder::IsSystemPrincipal(nsIPrincipal *principal, PRBool *result) +{ + if (!gSystemPrincipal) + return NS_ERROR_UNEXPECTED; + + *result = (principal == gSystemPrincipal); + return NS_OK; +} + diff --git a/content/xul/templates/src/nsXULTemplateBuilder.h b/content/xul/templates/src/nsXULTemplateBuilder.h index 8173b1ca33ee..e24b39021008 100644 --- a/content/xul/templates/src/nsXULTemplateBuilder.h +++ b/content/xul/templates/src/nsXULTemplateBuilder.h @@ -331,6 +331,9 @@ public: nsresult CheckContainer(nsIRDFResource* aTargetResource, PRBool* aIsContainer, PRBool* aIsEmpty); + nsresult + IsSystemPrincipal(nsIPrincipal *principal, PRBool *result); + #ifdef PR_LOGGING nsresult Log(const char* aOperation, diff --git a/content/xul/templates/src/nsXULTreeBuilder.cpp b/content/xul/templates/src/nsXULTreeBuilder.cpp index 47d340a8dcf3..5ccf9fbde38d 100644 --- a/content/xul/templates/src/nsXULTreeBuilder.cpp +++ b/content/xul/templates/src/nsXULTreeBuilder.cpp @@ -53,6 +53,9 @@ #include "nsXULTemplateBuilder.h" #include "nsVoidArray.h" +// For security check +#include "nsIDocument.h" + /** * A XUL template builder that serves as an outliner view, allowing * (pretty much) arbitrary RDF to be presented in an outliner. @@ -604,13 +607,50 @@ nsXULOutlinerBuilder::SetOutliner(nsIOutlinerBoxObject* outliner) LoadDataSources(); - // So we can remember open state. - // - // XXX We should fix this so that if the document is - // ``trusted'', we use the localstore. - mPersistStateStore = - do_CreateInstance("@mozilla.org/rdf/datasource;1?name=in-memory-datasource"); + nsCOMPtr doc; + mRoot->GetDocument(*getter_AddRefs(doc)); + NS_ASSERTION(doc, "element has no document"); + if (!doc) + return NS_ERROR_UNEXPECTED; + // Grab the doc's principal... + nsCOMPtr docPrincipal; + nsresult rv = doc->GetPrincipal(getter_AddRefs(docPrincipal)); + if (NS_FAILED(rv)) + return rv; + + PRBool isTrusted = PR_FALSE; + rv = IsSystemPrincipal(docPrincipal.get(), &isTrusted); + if (NS_SUCCEEDED(rv) && isTrusted) { + // Get the datasource we intend to use to remember open state. + nsAutoString datasourceStr; + mRoot->GetAttr(kNameSpaceID_None, nsXULAtoms::statedatasource, datasourceStr); + + // since we are trusted, use the user specified datasource + // if non specified, use localstore, which gives us + // persistance across sessions + if (datasourceStr.Length()) { + gRDFService->GetDataSource(NS_ConvertUCS2toUTF8(datasourceStr).get(), + getter_AddRefs(mPersistStateStore)); + } + else { + gRDFService->GetDataSource("rdf:local-store", + getter_AddRefs(mPersistStateStore)); + } + } + + // Either no specific datasource was specified, or we failed + // to get one because we are not trusted. + // + // XXX if it were possible to ``write an arbitrary datasource + // back'', then we could also allow an untrusted document to + // use a statedatasource from the same codebase. + if (! mPersistStateStore) { + mPersistStateStore = + do_CreateInstance("@mozilla.org/rdf/datasource;1?name=in-memory-datasource"); + } + + NS_ASSERTION(mPersistStateStore, "failed to get a persistant state store"); if (! mPersistStateStore) return NS_ERROR_FAILURE; @@ -986,11 +1026,13 @@ nsXULOutlinerBuilder::ReplaceMatch(nsIRDFResource* aMember, // Use the persist store to remember if the container // is open or closed. PRBool open = PR_FALSE; - mPersistStateStore->HasAssertion(container, - nsXULContentUtils::NC_open, - nsXULContentUtils::true_, - PR_TRUE, - &open); + + if (mPersistStateStore) + mPersistStateStore->HasAssertion(container, + nsXULContentUtils::NC_open, + nsXULContentUtils::true_, + PR_TRUE, + &open); if (open) { parent = mRows.EnsureSubtreeFor(iter); diff --git a/mailnews/base/public/nsIMsgIncomingServer.idl b/mailnews/base/public/nsIMsgIncomingServer.idl index ae706982d809..0dc0197554c8 100644 --- a/mailnews/base/public/nsIMsgIncomingServer.idl +++ b/mailnews/base/public/nsIMsgIncomingServer.idl @@ -119,7 +119,7 @@ interface nsIMsgIncomingServer : nsISupports { /* are we already getting new Messages on the current server.. This is used to help us prevent multiple get new msg commands from - going off at the same time. */ + going off at the same time. */ attribute boolean serverBusy; /* should we use a secure channel? */ @@ -143,7 +143,7 @@ interface nsIMsgIncomingServer : nsISupports { readonly attribute boolean serverRequiresPasswordForBiff; /* this gets called when the server is expanded in the folder pane */ - void PerformExpand(in nsIMsgWindow aMsgWindow); + void performExpand(in nsIMsgWindow aMsgWindow); /* Write out all known folder data to panacea.dat */ void WriteToFolderCache(in nsIMsgFolderCache folderCache); @@ -238,7 +238,7 @@ interface nsIMsgIncomingServer : nsISupports { /* create pretty name for migrated accounts */ wstring generatePrettyNameForMigration(); - + /* does this server have disk space settings? */ readonly attribute boolean supportsDiskSpace; diff --git a/mailnews/base/resources/content/folderPane.xul b/mailnews/base/resources/content/folderPane.xul index 6925a219df62..06e350363f87 100644 --- a/mailnews/base/resources/content/folderPane.xul +++ b/mailnews/base/resources/content/folderPane.xul @@ -37,6 +37,7 @@ seltype="single">