Closed Bug 342274 Opened 20 years ago Closed 20 years ago

implement alternative nsIXSLTProcessor interface without access to document loading

Categories

(Core :: XSLT, defect)

1.8 Branch
defect
Not set
normal

Tracking

()

RESOLVED FIXED
mozilla1.8.1beta1

People

(Reporter: myk, Assigned: sicking)

Details

(Keywords: fixed1.8.1, Whiteboard: [sg:investigate preventative] used by post ff1.5 feature)

Attachments

(3 files, 6 obsolete files)

For better security when transforming local but not entirely trusted XSLT stylesheets, the XSLT processor should provide an interface which doesn't have access to document loading.
I suggest we add a SetFlags method that disables the processor from loading any external documents. You would then use the nomral methods on nsIXSLTProcessor to do the transformations.
Attached patch Patch to fix (obsolete) — Splinter Review
Attachment #227780 - Flags: superreview?(peterv)
Attachment #227780 - Flags: review?(peterv)
Attached patch Complete patch to fix (obsolete) — Splinter Review
Attachment #227780 - Attachment is obsolete: true
Attachment #227782 - Flags: superreview?(peterv)
Attachment #227782 - Flags: review?(peterv)
Attachment #227780 - Flags: superreview?(peterv)
Attachment #227780 - Flags: review?(peterv)
Comment on attachment 227782 [details] [diff] [review] Complete patch to fix >Index: content/xslt/public/nsIXSLTProcessorPrivate.idl >=================================================================== >+[scriptable, uuid(b8d727f7-67f4-4dc1-a318-ec0c87280816)] >+interface nsIXSLTProcessorPrivate : nsISupports >+{ >+ /** >+ * Disables all loading of external documents, such as from >+ * <xsl:import> and document() >+ * Defaults to off and is *not* reset by calls to reset() >+ */ >+ const unsigned long DISABLE_ALL_LOADS = 1; TABS!!!!!!!! >Index: content/xslt/src/xslt/txMozillaStylesheetCompiler.cpp >=================================================================== > class txSyncCompileObserver : public txACompileObserver > protected: >+ txMozillaXSLTProcessor* mProcessor; Make that an nsRefPtr. >Index: content/xslt/src/xslt/txMozillaXSLTProcessor.cpp >=================================================================== >@@ -338,17 +339,17 @@ txMozillaXSLTProcessor::TransformDocumen >- nsresult rv = TX_CompileStylesheet(aStyleDOM, getter_AddRefs(mStylesheet)); >+ nsresult rv = TX_CompileStylesheet(aStyleDOM, this, getter_AddRefs(mStylesheet)); Long line. >@@ -589,17 +590,17 @@ txMozillaXSLTProcessor::ImportStylesheet >- nsresult rv = TX_CompileStylesheet(aStyle, getter_AddRefs(mStylesheet)); >+ nsresult rv = TX_CompileStylesheet(aStyle, this, getter_AddRefs(mStylesheet)); Long line. >Index: content/xslt/src/xslt/txMozillaXSLTProcessor.h >=================================================================== >+ PRBool DisableLoads() >+ { >+ return (mFlags & DISABLE_ALL_LOADS) != 0; >+ } IsLoadDisabled Nice patch! Some of your better work!
Attachment #227782 - Flags: superreview?(peterv)
Attachment #227782 - Flags: superreview+
Attachment #227782 - Flags: review?(peterv)
Attachment #227782 - Flags: review+
In preliminary testing, it looks like I'm seeing the same behavior whether I set the flag or not. For example, a microsummary generator for Merriam-Webster's word of the day page that tries to load a remote file via document() fails with the following error in both cases: Security Error: Content at http://www.m-w.com/cgi-bin/mwwod.pl may not load data from http://people.mozilla.com/~myk/microsummaries/generators/fedex-track-package.xml If that generator tries to include or import a file, the processor throws the following error in both cases: ************************************************************ * Call to xpconnect wrapped JSObject produced this error: * [Exception... "Component returned failure code: 0x80600004 [nsIXSLTProcessor.transformToFragment]" nsresult: "0x80600004 (<unknown>)" location: "JS frame :: file:///home/myk/Projects/minefield/mozilla/dist/bin/components/nsMicrosummaryService.js :: MSD__processTemplate :: line 1002" data: no] ************************************************************ The document() error seems unrelated to the changes, but it seems like the import/include error shouldn't happen unless I set the flag. I'll investigate further.
The document() error seems to be because we check the origin against the source document. So if you let http://example.com/index.html use a generator (installed or linked) that contains document('http://example.com/test.xml') you will probably not get an error. Does the import/include error happen even without the patch?
(In reply to comment #6) > The document() error seems to be because we check the origin against the source > document. So if you let http://example.com/index.html use a generator > (installed or linked) that contains document('http://example.com/test.xml') you > will probably not get an error. Indeed, if I don't apply the patch, or if I apply the patch but don't set the flag, I don't get an error, and the document function works. > Does the import/include error happen even without the patch? It did, but I'm not convinced of my results. Unfortunately I'm now having trouble reproducing them, as the following code throws an NS_NOINTERFACE exception: // XXX Should we just have one global instance of the processor? var processor = Cc["@mozilla.org/document-transformer;1?type=xslt"]. createInstance(Ci.nsIXSLTProcessor); + + // Turn off document loading of all kinds (document(), <include>, <import>). + var processorPrivate = processor.QueryInterface(Ci.nsIXSLTProcessorPrivate); + processorPrivate.flags |= Ci.nsIXSLTProcessorPrivate.DISABLE_ALL_LOADS; + processor.importStylesheet(this.template); var fragment = processor.transformToFragment(doc, doc); I'll investigate further tomorrow.
I looked around for code that references nsIXSLTProcessorObsolete but doesn't reference nsIXSLTProcessorPrivate, thinking that perhaps the latter isn't declared somewhere it needs to be. There are a few places like that in the code: 1. content/xslt/src/xslt/txMozillaXSLTProcessor.cpp, line 302: http://lxr.mozilla.org/mozilla/source/content/xslt/src/xslt/txMozillaXSLTProcessor.cpp#302 2. dom/src/base/nsDOMClassInfo.cpp, lines 199 and 2982: http://lxr.mozilla.org/mozilla/source/dom/src/base/nsDOMClassInfo.cpp#199 http://lxr.mozilla.org/mozilla/source/dom/src/base/nsDOMClassInfo.cpp#2982 If I add equivalent code for nsIXSLTProcessorPrivate to those places and rebuild, I no longer get the NS_NOINTERFACE error (not sure they're all needed, but haven't tested each line individually, as I figure Jonas will know). Here's a patch that includes those fixes and has also been updated to work with recent trunk changes. Now that it works, I'll start testing its use in the microsummary service.
Attachment #227782 - Attachment is obsolete: true
Attached patch With security checks (obsolete) — Splinter Review
This is the same as myks patch, but adds security checks to prevent anyone but chrome from getting or setting flags.
Attachment #228208 - Attachment is obsolete: true
With the patch applied, if the microsummary service doesn't set the flag, document() works. If it sets the flag, document() silently fails. But import and include throw the same exception whether or not the flag is set: 0x8060001b, which Mozilla Error Lookup (http://twpol.dyndns.org/mozilla/misc/nserror) claims is NS_ERROR_XSLT_LOAD_BLOCKED_ERROR. So it's not clear that the flag is working for those elements.
With help from Jonas, I corrected my testcase, and now I do see the correct behavior. Without the flag set, a local generator can import/include a local file. With the flag set, it cannot. Here's a patch for the microsummary service that makes it use the new API when importing a stylesheet.
Attachment #228229 - Flags: review?(bugmail)
Comment on attachment 228229 [details] [diff] [review] patch for microsummary service to use new API >Index: browser/components/microsummaries/src/nsMicrosummaryService.js.in >=================================================================== >RCS file: /cvsroot/mozilla/browser/components/microsummaries/src/nsMicrosummaryService.js.in,v >retrieving revision 1.20 >diff -u -r1.20 nsMicrosummaryService.js.in >--- browser/components/microsummaries/src/nsMicrosummaryService.js.in 5 Jul 2006 20:23:57 -0000 1.20 >+++ browser/components/microsummaries/src/nsMicrosummaryService.js.in 6 Jul 2006 00:17:51 -0000 >@@ -1234,6 +1234,12 @@ > // XXX Should we just have one global instance of the processor? > var processor = Cc["@mozilla.org/document-transformer;1?type=xslt"]. > createInstance(Ci.nsIXSLTProcessor); >+ >+ // Turn off document loading of all kinds (document(), <include>, <import>) >+ // for security (otherwise local generators would be able to load local files). >+ var processorPrivate = processor.QueryInterface(Ci.nsIXSLTProcessorPrivate); >+ processorPrivate.flags |= Ci.nsIXSLTProcessorPrivate.DISABLE_ALL_LOADS; >+ Actually, you don't need the QueryInterface call any more, with the way that we ended up doing security.
Attachment #228229 - Flags: superreview+
Attachment #228229 - Flags: review?(bugmail)
Attachment #228229 - Flags: review+
Attachment #228229 - Flags: approval1.8.1?
Opps, diffed wrong tree.
Attachment #228217 - Attachment is obsolete: true
Attachment #228232 - Flags: approval1.8.1?
Attachment #228217 - Flags: approval1.8.1?
Per Jonas, checked in the patch to the trunk without the unnecessary QI.
Attachment #228229 - Attachment is obsolete: true
Attachment #228229 - Flags: approval1.8.1?
Both fixes checked in to trunk.
Status: NEW → RESOLVED
Closed: 20 years ago
Resolution: --- → FIXED
Target Milestone: --- → mozilla1.8.1beta1
Attachment #228241 - Flags: approval1.8.1?
Could this be responsible for regressing Tp on btek?
There is no way that the code I checked in (which is when the Tp regression happened) could be run during the Tp tests. And even if it was there is no way it could affect performance. I suspect it's just a fluke or that the code in gklayout got ordered differently or some such.
Attachment #228232 - Flags: approval1.8.1? → approval1.8.1+
Attachment #228241 - Flags: approval1.8.1? → approval1.8.1+
fwiw: noticed tabs in the IDL file
Attached patch branch version (obsolete) — Splinter Review
This is what i'm landing on the 1.8 branch
Attached patch branch versionSplinter Review
Grr.. forgot to do a final diff
Attachment #228361 - Attachment is obsolete: true
Comment on attachment 228362 [details] [diff] [review] branch version In testing, this patch works as advertised. I should note that <include> and <import> fail silently on the branch, with or without the patch, but with the patch applied and the flag set, they throw an exception, as expected.
Both fixes checked in to branch.
Keywords: fixed1.8.1
Whiteboard: [sg:investigate preventative] used by post ff1.5 feature
Group: security
You need to log in before you can comment on or make changes to this bug.

Attachment

General

Created:
Updated:
Size: