Fix for bug 193678 (support exslt:common - exslt:common functions implementation). r/sr=sicking.

This commit is contained in:
peterv%propagandism.org 2006-11-16 21:42:25 +00:00
Родитель f9da27583e
Коммит 53885d7e4f
19 изменённых файлов: 546 добавлений и 128 удалений

Просмотреть файл

@ -503,6 +503,7 @@ GK_ATOM(nextBidi, "NextBidi")
GK_ATOM(no, "no") GK_ATOM(no, "no")
GK_ATOM(nobr, "nobr") GK_ATOM(nobr, "nobr")
GK_ATOM(node, "node") GK_ATOM(node, "node")
GK_ATOM(nodeSet, "node-set")
GK_ATOM(noembed, "noembed") GK_ATOM(noembed, "noembed")
GK_ATOM(noframes, "noframes") GK_ATOM(noframes, "noframes")
GK_ATOM(nohref, "nohref") GK_ATOM(nohref, "nohref")
@ -516,6 +517,7 @@ GK_ATOM(_not, "not")
GK_ATOM(nowrap, "nowrap") GK_ATOM(nowrap, "nowrap")
GK_ATOM(number, "number") GK_ATOM(number, "number")
GK_ATOM(object, "object") GK_ATOM(object, "object")
GK_ATOM(objectType, "object-type")
GK_ATOM(observer, "observer") GK_ATOM(observer, "observer")
GK_ATOM(observes, "observes") GK_ATOM(observes, "observes")
GK_ATOM(odd, "odd") GK_ATOM(odd, "odd")

Просмотреть файл

@ -61,7 +61,7 @@ public:
return NS_ERROR_FAILURE; return NS_ERROR_FAILURE;
} }
nsresult nsresult
resolveFunctionCall(nsIAtom* aName, PRInt32 aID, FunctionCall*& aFunction) resolveFunctionCall(nsIAtom* aName, PRInt32 aID, FunctionCall** aFunction)
{ {
return NS_ERROR_XPATH_UNKNOWN_FUNCTION; return NS_ERROR_XPATH_UNKNOWN_FUNCTION;
} }

Просмотреть файл

@ -85,7 +85,7 @@ public:
nsresult resolveNamespacePrefix(nsIAtom* aPrefix, PRInt32& aID); nsresult resolveNamespacePrefix(nsIAtom* aPrefix, PRInt32& aID);
nsresult resolveFunctionCall(nsIAtom* aName, PRInt32 aID, nsresult resolveFunctionCall(nsIAtom* aName, PRInt32 aID,
FunctionCall*& aFunction); FunctionCall** aFunction);
PRBool caseInsensitiveNameTests(); PRBool caseInsensitiveNameTests();
void SetErrorOffset(PRUint32 aOffset); void SetErrorOffset(PRUint32 aOffset);
@ -288,12 +288,12 @@ nsresult nsXPathEvaluatorParseContext::resolveNamespacePrefix
extern nsresult extern nsresult
TX_ResolveFunctionCallXPCOM(const nsCString &aContractID, PRInt32 aNamespaceID, TX_ResolveFunctionCallXPCOM(const nsCString &aContractID, PRInt32 aNamespaceID,
nsIAtom *aName, nsISupports *aState, nsIAtom *aName, nsISupports *aState,
FunctionCall *&aFunction); FunctionCall **aFunction);
nsresult nsresult
nsXPathEvaluatorParseContext::resolveFunctionCall(nsIAtom* aName, nsXPathEvaluatorParseContext::resolveFunctionCall(nsIAtom* aName,
PRInt32 aID, PRInt32 aID,
FunctionCall*& aFn) FunctionCall** aFn)
{ {
nsresult rv = NS_ERROR_XPATH_UNKNOWN_FUNCTION; nsresult rv = NS_ERROR_XPATH_UNKNOWN_FUNCTION;

Просмотреть файл

@ -465,7 +465,7 @@ txExprParser::createFunctionCall(txExprLexer& lexer, txIParseContext* aContext,
// check extension functions and xslt // check extension functions and xslt
if (!fnCall) { if (!fnCall) {
rv = aContext->resolveFunctionCall(lName, namespaceID, rv = aContext->resolveFunctionCall(lName, namespaceID,
*getter_Transfers(fnCall)); getter_Transfers(fnCall));
if (rv == NS_ERROR_NOT_IMPLEMENTED) { if (rv == NS_ERROR_NOT_IMPLEMENTED) {
// this should just happen for unparsed-entity-uri() // this should just happen for unparsed-entity-uri()

Просмотреть файл

@ -59,7 +59,8 @@ class txAExprResult : public TxObject
public: public:
friend class txResultRecycler; friend class txResultRecycler;
// Update txLiteralExpr::getReturnType if this enum is changed. // Update txLiteralExpr::getReturnType and sTypes in txEXSLTFunctions.cpp if
// this enum is changed.
enum ResultType { enum ResultType {
NODESET = 0, NODESET = 0,
BOOLEAN, BOOLEAN,

Просмотреть файл

@ -73,7 +73,7 @@ public:
* XSLT. XPath function calls are resolved by the Parser. * XSLT. XPath function calls are resolved by the Parser.
*/ */
virtual nsresult resolveFunctionCall(nsIAtom* aName, PRInt32 aID, virtual nsresult resolveFunctionCall(nsIAtom* aName, PRInt32 aID,
FunctionCall*& aFunction) = 0; FunctionCall** aFunction) = 0;
/** /**
* Should nametests parsed in this context be case-sensitive * Should nametests parsed in this context be case-sensitive

Просмотреть файл

@ -117,7 +117,8 @@ txNodeSetAdaptor::Add(nsIDOMNode *aNode)
{ {
NS_ENSURE_TRUE(mWritable, NS_ERROR_FAILURE); NS_ENSURE_TRUE(mWritable, NS_ERROR_FAILURE);
nsAutoPtr<txXPathNode> node(txXPathNativeNode::createXPathNode(aNode)); nsAutoPtr<txXPathNode> node(txXPathNativeNode::createXPathNode(aNode,
PR_TRUE));
return node ? mNodeSet->add(*node) : NS_ERROR_OUT_OF_MEMORY; return node ? mNodeSet->add(*node) : NS_ERROR_OUT_OF_MEMORY;
} }

Просмотреть файл

@ -260,7 +260,7 @@ LookupFunction(const char *aContractID, nsIAtom* aName, nsIID &aIID,
nsresult nsresult
TX_ResolveFunctionCallXPCOM(const nsCString &aContractID, PRInt32 aNamespaceID, TX_ResolveFunctionCallXPCOM(const nsCString &aContractID, PRInt32 aNamespaceID,
nsIAtom* aName, nsISupports *aState, nsIAtom* aName, nsISupports *aState,
FunctionCall *&aFunction) FunctionCall **aFunction)
{ {
nsIID iid; nsIID iid;
PRUint16 methodIndex; PRUint16 methodIndex;
@ -271,13 +271,17 @@ TX_ResolveFunctionCallXPCOM(const nsCString &aContractID, PRInt32 aNamespaceID,
rv = CallGetService(aContractID.get(), iid, getter_AddRefs(helper)); rv = CallGetService(aContractID.get(), iid, getter_AddRefs(helper));
NS_ENSURE_SUCCESS(rv, rv); NS_ENSURE_SUCCESS(rv, rv);
aFunction = new txXPCOMExtensionFunctionCall(helper, iid, methodIndex, if (!aFunction) {
#ifdef TX_TO_STRING return NS_OK;
aNamespaceID, aName, }
#endif
aState);
return aFunction ? NS_OK : NS_ERROR_OUT_OF_MEMORY; *aFunction = new txXPCOMExtensionFunctionCall(helper, iid, methodIndex,
#ifdef TX_TO_STRING
aNamespaceID, aName,
#endif
aState);
return *aFunction ? NS_OK : NS_ERROR_OUT_OF_MEMORY;
} }
txArgumentType txArgumentType

Просмотреть файл

@ -84,6 +84,7 @@ CPPSRCS = \
txXPathResultComparator.cpp \ txXPathResultComparator.cpp \
txBufferingHandler.cpp \ txBufferingHandler.cpp \
txExecutionState.cpp \ txExecutionState.cpp \
txEXSLTFunctions.cpp \
txInstructions.cpp \ txInstructions.cpp \
txOutputFormat.cpp \ txOutputFormat.cpp \
txRtfHandler.cpp \ txRtfHandler.cpp \

Просмотреть файл

@ -0,0 +1,311 @@
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is mozilla.org code.
*
* The Initial Developer of the Original Code is
* Peter Van der Beken.
* Portions created by the Initial Developer are Copyright (C) 2003
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Peter Van der Beken <peterv@propagandism.org>
*
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#include "nsIAtom.h"
#include "txAtoms.h"
#include "txExecutionState.h"
#include "txExpr.h"
#include "txIXPathContext.h"
#include "txNodeSet.h"
#include "txOutputFormat.h"
#include "txRtfHandler.h"
#include "txXPathTreeWalker.h"
#ifndef TX_EXE
#include "nsComponentManagerUtils.h"
#include "nsContentCID.h"
#include "nsContentCreatorFunctions.h"
#include "nsIContent.h"
#include "nsIDOMDocumentFragment.h"
#include "nsIDOMText.h"
#include "txMozillaXMLOutput.h"
#endif
class txStylesheetCompilerState;
static nsresult
convertRtfToNode(txIEvalContext *aContext, txResultTreeFragment *aRtf)
{
txExecutionState* es =
NS_STATIC_CAST(txExecutionState*, aContext->getPrivateContext());
if (!es) {
NS_ERROR("Need txExecutionState!");
return NS_ERROR_UNEXPECTED;
}
const txXPathNode& document = es->getSourceDocument();
#ifdef TX_EXE
return NS_ERROR_NOT_IMPLEMENTED;
#else
nsIDocument *doc = txXPathNativeNode::getDocument(document);
nsCOMPtr<nsIDOMDocumentFragment> domFragment;
nsresult rv = NS_NewDocumentFragment(getter_AddRefs(domFragment),
doc->NodeInfoManager());
NS_ENSURE_SUCCESS(rv, rv);
txOutputFormat format;
txMozillaXMLOutput mozHandler(&format, domFragment, PR_TRUE);
rv = aRtf->flushToHandler(&mozHandler);
NS_ENSURE_SUCCESS(rv, rv);
nsCOMPtr<nsINode> fragment = do_QueryInterface(domFragment, &rv);
NS_ENSURE_SUCCESS(rv, rv);
// The txResultTreeFragment will own this.
const txXPathNode* node = txXPathNativeNode::createXPathNode(domFragment,
PR_TRUE);
NS_ENSURE_TRUE(node, NS_ERROR_OUT_OF_MEMORY);
aRtf->setNode(node);
return NS_OK;
#endif
}
static nsresult
createTextNode(txIEvalContext *aContext, nsString& aValue,
txXPathNode* *aResult)
{
txExecutionState* es =
NS_STATIC_CAST(txExecutionState*, aContext->getPrivateContext());
if (!es) {
NS_ERROR("Need txExecutionState!");
return NS_ERROR_UNEXPECTED;
}
const txXPathNode& document = es->getSourceDocument();
#ifdef TX_EXE
return NS_ERROR_NOT_IMPLEMENTED;
#else
nsIDocument *doc = txXPathNativeNode::getDocument(document);
nsCOMPtr<nsIContent> text;
nsresult rv = NS_NewTextNode(getter_AddRefs(text), doc->NodeInfoManager());
NS_ENSURE_SUCCESS(rv, rv);
nsCOMPtr<nsIDOMText> domText = do_QueryInterface(text, &rv);
NS_ENSURE_SUCCESS(rv, rv);
*aResult = txXPathNativeNode::createXPathNode(domText, PR_TRUE);
NS_ENSURE_TRUE(*aResult, NS_ERROR_OUT_OF_MEMORY);
return NS_OK;
#endif
}
class txEXSLTNodeSetFunctionCall : public FunctionCall
{
public:
TX_DECL_FUNCTION;
};
nsresult
txEXSLTNodeSetFunctionCall::evaluate(txIEvalContext *aContext,
txAExprResult **aResult)
{
*aResult = nsnull;
if (!requireParams(1, 1, aContext)) {
return NS_ERROR_XPATH_BAD_ARGUMENT_COUNT;
}
txListIterator iter(&params);
Expr* param1 = NS_STATIC_CAST(Expr*, iter.next());
nsRefPtr<txAExprResult> exprResult;
nsresult rv = param1->evaluate(aContext, getter_AddRefs(exprResult));
NS_ENSURE_SUCCESS(rv, rv);
if (exprResult->getResultType() == txAExprResult::NODESET) {
exprResult.swap(*aResult);
}
else {
nsRefPtr<txNodeSet> nodeset;
rv = aContext->recycler()->getNodeSet(getter_AddRefs(nodeset));
NS_ENSURE_SUCCESS(rv, rv);
if (exprResult->getResultType() == txAExprResult::RESULT_TREE_FRAGMENT) {
txResultTreeFragment *rtf =
NS_STATIC_CAST(txResultTreeFragment*,
NS_STATIC_CAST(txAExprResult*, exprResult));
const txXPathNode *node = rtf->getNode();
if (!node) {
rv = convertRtfToNode(aContext, rtf);
NS_ENSURE_SUCCESS(rv, rv);
node = rtf->getNode();
}
nodeset->append(*node);
}
else {
nsAutoString value;
exprResult->stringValue(value);
nsAutoPtr<txXPathNode> node;
rv = createTextNode(aContext, value, getter_Transfers(node));
NS_ENSURE_SUCCESS(rv, rv);
nodeset->append(*node);
}
NS_ADDREF(*aResult = nodeset);
}
return NS_OK;
}
Expr::ResultType
txEXSLTNodeSetFunctionCall::getReturnType()
{
return Expr::NODESET_RESULT;
}
PRBool
txEXSLTNodeSetFunctionCall::isSensitiveTo(ContextSensitivity aContext)
{
return argsSensitiveTo(aContext);
}
#ifdef TX_TO_STRING
nsresult
txEXSLTNodeSetFunctionCall::getNameAtom(nsIAtom **aAtom)
{
NS_ADDREF(*aAtom = txXSLTAtoms::nodeSet);
return NS_OK;
}
#endif
class txEXSLTObjectTypeFunctionCall : public FunctionCall
{
public:
TX_DECL_FUNCTION;
};
// Need to update this array if types are added to the ResultType enum in
// txAExprResult.
static const char * const sTypes[] = {
"node-set",
"boolean",
"number",
"string",
"RTF"
};
nsresult
txEXSLTObjectTypeFunctionCall::evaluate(txIEvalContext *aContext,
txAExprResult **aResult)
{
*aResult = nsnull;
if (!requireParams(1, 1, aContext)) {
return NS_ERROR_XPATH_BAD_ARGUMENT_COUNT;
}
txListIterator iter(&params);
Expr* param1 = NS_STATIC_CAST(Expr*, iter.next());
nsRefPtr<txAExprResult> exprResult;
nsresult rv = param1->evaluate(aContext, getter_AddRefs(exprResult));
NS_ENSURE_SUCCESS(rv, rv);
nsRefPtr<StringResult> strRes;
rv = aContext->recycler()->getStringResult(getter_AddRefs(strRes));
NS_ENSURE_SUCCESS(rv, rv);
AppendASCIItoUTF16(sTypes[exprResult->getResultType()], strRes->mValue);
NS_ADDREF(*aResult = strRes);
return NS_OK;
}
Expr::ResultType
txEXSLTObjectTypeFunctionCall::getReturnType()
{
return Expr::STRING_RESULT;
}
PRBool
txEXSLTObjectTypeFunctionCall::isSensitiveTo(ContextSensitivity aContext)
{
return argsSensitiveTo(aContext);
}
#ifdef TX_TO_STRING
nsresult
txEXSLTObjectTypeFunctionCall::getNameAtom(nsIAtom **aAtom)
{
NS_ADDREF(*aAtom = txXSLTAtoms::objectType);
return NS_OK;
}
#endif
extern nsresult
TX_ConstructEXSLTCommonFunction(nsIAtom *aName,
txStylesheetCompilerState* aState,
FunctionCall **aResult)
{
if (aName == txXSLTAtoms::nodeSet) {
if (aResult) {
*aResult = new txEXSLTNodeSetFunctionCall();
NS_ENSURE_TRUE(*aResult, NS_ERROR_OUT_OF_MEMORY);
}
return NS_OK;
}
if (aName == txXSLTAtoms::objectType) {
if (aResult) {
*aResult = new txEXSLTObjectTypeFunctionCall();
NS_ENSURE_TRUE(*aResult, NS_ERROR_OUT_OF_MEMORY);
}
return NS_OK;
}
return NS_ERROR_XPATH_UNKNOWN_FUNCTION;
}

Просмотреть файл

@ -95,7 +95,6 @@ txExecutionState::txExecutionState(txStylesheet* aStylesheet,
mTemplateRuleCount(0), mTemplateRuleCount(0),
mEvalContext(nsnull), mEvalContext(nsnull),
mInitialEvalContext(nsnull), mInitialEvalContext(nsnull),
// mRTFDocument(nsnull),
mGlobalParams(nsnull), mGlobalParams(nsnull),
mKeyHash(aStylesheet->getKeyMap()), mKeyHash(aStylesheet->getKeyMap()),
mDisableLoads(aDisableLoads) mDisableLoads(aDisableLoads)
@ -107,7 +106,6 @@ txExecutionState::~txExecutionState()
delete mResultHandler; delete mResultHandler;
delete mLocalVariables; delete mLocalVariables;
delete mEvalContext; delete mEvalContext;
// delete mRTFDocument;
PRInt32 i; PRInt32 i;
for (i = 0; i < mTemplateRuleCount; ++i) { for (i = 0; i < mTemplateRuleCount; ++i) {

Просмотреть файл

@ -134,6 +134,13 @@ public:
const nsAString& aKeyValue, PRBool aIndexIfNotFound, const nsAString& aKeyValue, PRBool aIndexIfNotFound,
txNodeSet** aResult); txNodeSet** aResult);
TemplateRule* getCurrentTemplateRule(); TemplateRule* getCurrentTemplateRule();
const txXPathNode& getSourceDocument()
{
NS_ASSERTION(mLoadedDocuments.mSourceDocument,
"Need a source document!");
return *mLoadedDocuments.mSourceDocument;
}
// state-modification functions // state-modification functions
txInstruction* getNextInstruction(); txInstruction* getNextInstruction();

Просмотреть файл

@ -90,7 +90,8 @@ txMozillaXMLOutput::txMozillaXMLOutput(const nsSubstring& aRootName,
mHaveBaseElement(PR_FALSE), mHaveBaseElement(PR_FALSE),
mCreatingNewDocument(PR_TRUE), mCreatingNewDocument(PR_TRUE),
mOpenedElementIsHTML(PR_FALSE), mOpenedElementIsHTML(PR_FALSE),
mRootContentCreated(PR_FALSE) mRootContentCreated(PR_FALSE),
mNoFixup(PR_FALSE)
{ {
if (aObserver) { if (aObserver) {
mNotifier = new txTransformNotifier(); mNotifier = new txTransformNotifier();
@ -106,7 +107,8 @@ txMozillaXMLOutput::txMozillaXMLOutput(const nsSubstring& aRootName,
} }
txMozillaXMLOutput::txMozillaXMLOutput(txOutputFormat* aFormat, txMozillaXMLOutput::txMozillaXMLOutput(txOutputFormat* aFormat,
nsIDOMDocumentFragment* aFragment) nsIDOMDocumentFragment* aFragment,
PRBool aNoFixup)
: mTreeDepth(0), : mTreeDepth(0),
mBadChildLevel(0), mBadChildLevel(0),
mTableState(NORMAL), mTableState(NORMAL),
@ -114,7 +116,8 @@ txMozillaXMLOutput::txMozillaXMLOutput(txOutputFormat* aFormat,
mHaveBaseElement(PR_FALSE), mHaveBaseElement(PR_FALSE),
mCreatingNewDocument(PR_FALSE), mCreatingNewDocument(PR_FALSE),
mOpenedElementIsHTML(PR_FALSE), mOpenedElementIsHTML(PR_FALSE),
mRootContentCreated(PR_FALSE) mRootContentCreated(PR_FALSE),
mNoFixup(aNoFixup)
{ {
mOutputFormat.merge(*aFormat); mOutputFormat.merge(*aFormat);
mOutputFormat.setFromDefaults(); mOutputFormat.setFromDefaults();
@ -317,25 +320,27 @@ txMozillaXMLOutput::endElement()
mCurrentNode)); mCurrentNode));
// Handle html-elements // Handle html-elements
if (element->IsNodeOfType(nsINode::eHTML)) { if (!mNoFixup) {
rv = endHTMLElement(element); if (element->IsNodeOfType(nsINode::eHTML)) {
NS_ENSURE_SUCCESS(rv, rv); rv = endHTMLElement(element);
}
// Handle script elements
if (element->Tag() == nsGkAtoms::script &&
(element->IsNodeOfType(nsINode::eHTML) ||
element->GetNameSpaceID() == kNameSpaceID_SVG)) {
rv = element->DoneAddingChildren(PR_TRUE);
// If the act of insertion evaluated the script, we're fine.
// Else, add this script element to the array of loading scripts.
if (rv == NS_ERROR_HTMLPARSER_BLOCK) {
nsCOMPtr<nsIScriptElement> sele = do_QueryInterface(element);
rv = mNotifier->AddScriptElement(sele);
NS_ENSURE_SUCCESS(rv, rv); NS_ENSURE_SUCCESS(rv, rv);
} }
// Handle script elements
if (element->Tag() == nsGkAtoms::script &&
(element->IsNodeOfType(nsINode::eHTML) ||
element->GetNameSpaceID() == kNameSpaceID_SVG)) {
rv = element->DoneAddingChildren(PR_TRUE);
// If the act of insertion evaluated the script, we're fine.
// Else, add this script element to the array of loading scripts.
if (rv == NS_ERROR_HTMLPARSER_BLOCK) {
nsCOMPtr<nsIScriptElement> sele = do_QueryInterface(element);
rv = mNotifier->AddScriptElement(sele);
NS_ENSURE_SUCCESS(rv, rv);
}
}
} }
if (mCreatingNewDocument) { if (mCreatingNewDocument) {
@ -556,15 +561,18 @@ txMozillaXMLOutput::startElementInternal(nsIAtom* aPrefix,
NS_NewElement(getter_AddRefs(mOpenedElement), aElemType, ni); NS_NewElement(getter_AddRefs(mOpenedElement), aElemType, ni);
// Set up the element and adjust state // Set up the element and adjust state
if (aElemType == kNameSpaceID_XHTML) { if (!mNoFixup) {
mOpenedElementIsHTML = aNsID != kNameSpaceID_XHTML; if (aElemType == kNameSpaceID_XHTML) {
rv = startHTMLElement(mOpenedElement, mOpenedElementIsHTML); mOpenedElementIsHTML = aNsID != kNameSpaceID_XHTML;
NS_ENSURE_SUCCESS(rv, rv); rv = startHTMLElement(mOpenedElement, mOpenedElementIsHTML);
NS_ENSURE_SUCCESS(rv, rv);
} }
else if (aNsID == kNameSpaceID_SVG && aLocalName == txHTMLAtoms::script) { else if (aNsID == kNameSpaceID_SVG &&
nsCOMPtr<nsIScriptElement> sele = do_QueryInterface(mOpenedElement); aLocalName == txHTMLAtoms::script) {
sele->WillCallDoneAddingChildren(); nsCOMPtr<nsIScriptElement> sele = do_QueryInterface(mOpenedElement);
sele->WillCallDoneAddingChildren();
}
} }
if (mCreatingNewDocument) { if (mCreatingNewDocument) {

Просмотреть файл

@ -101,7 +101,8 @@ public:
nsIDOMDocument* aResultDocument, nsIDOMDocument* aResultDocument,
nsITransformObserver* aObserver); nsITransformObserver* aObserver);
txMozillaXMLOutput(txOutputFormat* aFormat, txMozillaXMLOutput(txOutputFormat* aFormat,
nsIDOMDocumentFragment* aFragment); nsIDOMDocumentFragment* aFragment,
PRBool aNoFixup);
virtual ~txMozillaXMLOutput(); virtual ~txMozillaXMLOutput();
TX_DECL_TXAXMLEVENTHANDLER TX_DECL_TXAXMLEVENTHANDLER
@ -164,6 +165,8 @@ private:
// Set to true when we know there's a root content in our document. // Set to true when we know there's a root content in our document.
PRPackedBool mRootContentCreated; PRPackedBool mRootContentCreated;
PRPackedBool mNoFixup;
enum txAction { eCloseElement = 1, eFlushText = 2 }; enum txAction { eCloseElement = 1, eFlushText = 2 };
}; };

Просмотреть файл

@ -205,14 +205,14 @@ txToFragmentHandlerFactory::createHandlerWith(txOutputFormat* aFormat,
format.mMethod = eHTMLOutput; format.mMethod = eHTMLOutput;
} }
*aHandler = new txMozillaXMLOutput(&format, mFragment); *aHandler = new txMozillaXMLOutput(&format, mFragment, PR_FALSE);
break; break;
} }
case eXMLOutput: case eXMLOutput:
case eHTMLOutput: case eHTMLOutput:
{ {
*aHandler = new txMozillaXMLOutput(aFormat, mFragment); *aHandler = new txMozillaXMLOutput(aFormat, mFragment, PR_FALSE);
break; break;
} }
@ -390,7 +390,7 @@ class txXSLTParamContext : public txIParseContext,
public txIEvalContext public txIEvalContext
{ {
public: public:
txXSLTParamContext(txNamespaceMap *aResolver, txXPathNode& aContext, txXSLTParamContext(txNamespaceMap *aResolver, const txXPathNode& aContext,
txResultRecycler* aRecycler) txResultRecycler* aRecycler)
: mResolver(aResolver), : mResolver(aResolver),
mContext(aContext), mContext(aContext),
@ -406,7 +406,7 @@ public:
NS_OK; NS_OK;
} }
nsresult resolveFunctionCall(nsIAtom* aName, PRInt32 aID, nsresult resolveFunctionCall(nsIAtom* aName, PRInt32 aID,
FunctionCall*& aFunction) FunctionCall** aFunction)
{ {
return NS_ERROR_XPATH_UNKNOWN_FUNCTION; return NS_ERROR_XPATH_UNKNOWN_FUNCTION;
} }
@ -455,9 +455,8 @@ public:
private: private:
txNamespaceMap *mResolver; txNamespaceMap *mResolver;
txXPathNode& mContext; const txXPathNode& mContext;
txResultRecycler* mRecycler; txResultRecycler* mRecycler;
}; };

Просмотреть файл

@ -42,6 +42,7 @@
#include "txBufferingHandler.h" #include "txBufferingHandler.h"
#include "txExprResult.h" #include "txExprResult.h"
#include "txXPathNode.h"
class txResultTreeFragment : public txAExprResult class txResultTreeFragment : public txAExprResult
{ {
@ -53,8 +54,20 @@ public:
nsresult flushToHandler(txAXMLEventHandler* aHandler); nsresult flushToHandler(txAXMLEventHandler* aHandler);
void setNode(const txXPathNode* aNode)
{
NS_ASSERTION(!mNode, "Already converted!");
mNode = aNode;
}
const txXPathNode *getNode() const
{
return mNode;
}
private: private:
nsAutoPtr<txResultBuffer> mBuffer; nsAutoPtr<txResultBuffer> mBuffer;
nsAutoPtr<const txXPathNode> mNode;
}; };
class txRtfHandler : public txBufferingHandler class txRtfHandler : public txBufferingHandler

Просмотреть файл

@ -938,80 +938,153 @@ txErrorFunctionCall::getNameAtom(nsIAtom** aAtom)
} }
#endif #endif
nsresult static nsresult
txStylesheetCompilerState::resolveFunctionCall(nsIAtom* aName, PRInt32 aID, TX_ConstructXSLTFunction(nsIAtom* aName, txStylesheetCompilerState* aState,
FunctionCall*& aFunction) FunctionCall** aFunction)
{ {
aFunction = nsnull; if (aName == txXSLTAtoms::document) {
if (aFunction) {
*aFunction =
new DocumentFunctionCall(aState->mElementContext->mBaseURI);
NS_ENSURE_TRUE(*aFunction, NS_ERROR_OUT_OF_MEMORY);
}
if (aID == kNameSpaceID_None) { return NS_OK;
if (aName == txXSLTAtoms::document) { }
aFunction = new DocumentFunctionCall(mElementContext->mBaseURI);
NS_ENSURE_TRUE(aFunction, NS_ERROR_OUT_OF_MEMORY); if (aName == txXSLTAtoms::key) {
if (aFunction) {
return NS_OK; *aFunction =
new txKeyFunctionCall(aState->mElementContext->mMappings);
NS_ENSURE_TRUE(*aFunction, NS_ERROR_OUT_OF_MEMORY);
} }
if (aName == txXSLTAtoms::key) {
aFunction = new txKeyFunctionCall(mElementContext->mMappings); return NS_OK;
NS_ENSURE_TRUE(aFunction, NS_ERROR_OUT_OF_MEMORY); }
return NS_OK; if (aName == txXSLTAtoms::formatNumber) {
if (aFunction) {
*aFunction =
new txFormatNumberFunctionCall(aState->mStylesheet,
aState->mElementContext->mMappings);
NS_ENSURE_TRUE(*aFunction, NS_ERROR_OUT_OF_MEMORY);
} }
if (aName == txXSLTAtoms::formatNumber) {
aFunction = new txFormatNumberFunctionCall(mStylesheet, return NS_OK;
mElementContext->mMappings); }
NS_ENSURE_TRUE(aFunction, NS_ERROR_OUT_OF_MEMORY);
if (aName == txXSLTAtoms::current) {
return NS_OK; if (aFunction) {
*aFunction = new CurrentFunctionCall();
NS_ENSURE_TRUE(*aFunction, NS_ERROR_OUT_OF_MEMORY);
} }
if (aName == txXSLTAtoms::current) {
aFunction = new CurrentFunctionCall(); return NS_OK;
NS_ENSURE_TRUE(aFunction, NS_ERROR_OUT_OF_MEMORY); }
return NS_OK; if (aName == txXSLTAtoms::unparsedEntityUri) {
return NS_ERROR_NOT_IMPLEMENTED;
}
if (aName == txXSLTAtoms::generateId) {
if (aFunction) {
*aFunction = new GenerateIdFunctionCall();
NS_ENSURE_TRUE(*aFunction, NS_ERROR_OUT_OF_MEMORY);
} }
if (aName == txXSLTAtoms::unparsedEntityUri) {
return NS_OK;
return NS_ERROR_NOT_IMPLEMENTED; }
}
if (aName == txXSLTAtoms::generateId) { txXSLTEnvironmentFunctionCall::eType type;
aFunction = new GenerateIdFunctionCall(); if (aName == txXSLTAtoms::systemProperty) {
NS_ENSURE_TRUE(aFunction, NS_ERROR_OUT_OF_MEMORY); type = txXSLTEnvironmentFunctionCall::SYSTEM_PROPERTY;
}
return NS_OK; else if (aName == txXSLTAtoms::elementAvailable) {
} type = txXSLTEnvironmentFunctionCall::ELEMENT_AVAILABLE;
if (aName == txXSLTAtoms::systemProperty) { }
aFunction = new txXSLTEnvironmentFunctionCall( else if (aName == txXSLTAtoms::functionAvailable) {
txXSLTEnvironmentFunctionCall::SYSTEM_PROPERTY, type = txXSLTEnvironmentFunctionCall::FUNCTION_AVAILABLE;
mElementContext->mMappings); }
NS_ENSURE_TRUE(aFunction, NS_ERROR_OUT_OF_MEMORY); else {
return NS_ERROR_XPATH_UNKNOWN_FUNCTION;
return NS_OK; }
}
if (aName == txXSLTAtoms::elementAvailable) { if (!aFunction) {
aFunction = new txXSLTEnvironmentFunctionCall( return NS_OK;
txXSLTEnvironmentFunctionCall::ELEMENT_AVAILABLE, }
mElementContext->mMappings);
NS_ENSURE_TRUE(aFunction, NS_ERROR_OUT_OF_MEMORY); txNamespaceMap *map = aState->mElementContext->mMappings;
*aFunction = new txXSLTEnvironmentFunctionCall(type, map);
return NS_OK;
} return *aFunction ? NS_OK : NS_ERROR_OUT_OF_MEMORY;
if (aName == txXSLTAtoms::functionAvailable) { }
aFunction = new txXSLTEnvironmentFunctionCall(
txXSLTEnvironmentFunctionCall::FUNCTION_AVAILABLE, typedef nsresult (*txFunctionFactory)(nsIAtom* aName,
mElementContext->mMappings); txStylesheetCompilerState* aState,
NS_ENSURE_TRUE(aFunction, NS_ERROR_OUT_OF_MEMORY); FunctionCall** aResult);
struct txFunctionFactoryMapping
return NS_OK; {
} const char* const mNamespaceURI;
if (!fcp()) { PRInt32 mNamespaceID;
return NS_ERROR_XPATH_UNKNOWN_FUNCTION; txFunctionFactory mFactory;
};
extern nsresult
TX_ConstructEXSLTCommonFunction(nsIAtom *aName,
txStylesheetCompilerState* aState,
FunctionCall **aResult);
static txFunctionFactoryMapping kExtensionFunctions[] = {
{ "", kNameSpaceID_Unknown, TX_ConstructXSLTFunction },
{ "http://exslt.org/common", kNameSpaceID_Unknown,
TX_ConstructEXSLTCommonFunction }
};
static nsresult
findFunction(nsIAtom* aName, PRInt32 aNamespaceID,
txStylesheetCompilerState* aState, FunctionCall** aResult)
{
if (kExtensionFunctions[0].mNamespaceID == kNameSpaceID_Unknown) {
PRUint32 i;
for (i = 0; i < NS_ARRAY_LENGTH(kExtensionFunctions); ++i) {
txFunctionFactoryMapping& mapping = kExtensionFunctions[i];
NS_ConvertASCIItoUTF16 namespaceURI(mapping.mNamespaceURI);
mapping.mNamespaceID =
txNamespaceManager::getNamespaceID(namespaceURI);
} }
} }
aFunction = new txErrorFunctionCall(aName, aID); PRUint32 i;
for (i = 0; i < NS_ARRAY_LENGTH(kExtensionFunctions); ++i) {
const txFunctionFactoryMapping& mapping = kExtensionFunctions[i];
if (mapping.mNamespaceID == aNamespaceID) {
return mapping.mFactory(aName, aState, aResult);
}
}
return aFunction ? NS_OK : NS_ERROR_OUT_OF_MEMORY; return NS_ERROR_XPATH_UNKNOWN_FUNCTION;
}
extern PRBool
TX_XSLTFunctionAvailable(nsIAtom* aName, PRInt32 aNameSpaceID)
{
return NS_SUCCEEDED(findFunction(aName, aNameSpaceID, nsnull, nsnull));
}
nsresult
txStylesheetCompilerState::resolveFunctionCall(nsIAtom* aName, PRInt32 aID,
FunctionCall **aFunction)
{
*aFunction = nsnull;
nsresult rv = findFunction(aName, aID, this, aFunction);
if (rv == NS_ERROR_XPATH_UNKNOWN_FUNCTION &&
(aID != kNameSpaceID_None || fcp())) {
*aFunction = new txErrorFunctionCall(aName, aID);
rv = *aFunction ? NS_OK : NS_ERROR_OUT_OF_MEMORY;
}
return rv;
} }
PRBool PRBool

Просмотреть файл

@ -140,7 +140,7 @@ public:
// txIParseContext // txIParseContext
nsresult resolveNamespacePrefix(nsIAtom* aPrefix, PRInt32& aID); nsresult resolveNamespacePrefix(nsIAtom* aPrefix, PRInt32& aID);
nsresult resolveFunctionCall(nsIAtom* aName, PRInt32 aID, nsresult resolveFunctionCall(nsIAtom* aName, PRInt32 aID,
FunctionCall*& aFunction); FunctionCall** aFunction);
PRBool caseInsensitiveNameTests(); PRBool caseInsensitiveNameTests();
/** /**

Просмотреть файл

@ -129,18 +129,15 @@ txXSLTEnvironmentFunctionCall::evaluate(txIEvalContext* aContext,
} }
case FUNCTION_AVAILABLE: case FUNCTION_AVAILABLE:
{ {
extern PRBool TX_XSLTFunctionAvailable(nsIAtom* aName,
PRInt32 aNameSpaceID);
txCoreFunctionCall::eType type; txCoreFunctionCall::eType type;
PRBool val = qname.mNamespaceID == kNameSpaceID_None && PRBool val = (qname.mNamespaceID == kNameSpaceID_None &&
(txCoreFunctionCall::getTypeFromAtom(qname.mLocalName, type) || txCoreFunctionCall::getTypeFromAtom(qname.mLocalName,
qname.mLocalName == txXSLTAtoms::current || type)) ||
qname.mLocalName == txXSLTAtoms::document || TX_XSLTFunctionAvailable(qname.mLocalName,
qname.mLocalName == txXSLTAtoms::elementAvailable || qname.mNamespaceID);
qname.mLocalName == txXSLTAtoms::formatNumber ||
qname.mLocalName == txXSLTAtoms::functionAvailable ||
qname.mLocalName == txXSLTAtoms::generateId ||
qname.mLocalName == txXSLTAtoms::key ||
//qname.mLocalName == txXSLTAtoms::unparsedEntityUri ||
qname.mLocalName == txXSLTAtoms::systemProperty);
aContext->recycler()->getBoolResult(val, aResult); aContext->recycler()->getBoolResult(val, aResult);
break; break;