nsresult txPushNewContext::execute(txExecutionState& aEs) { RefPtr<txAExprResult> exprRes; nsresult rv = mSelect->evaluate(aEs.getEvalContext(), getter_AddRefs(exprRes)); NS_ENSURE_SUCCESS(rv, rv); if (exprRes->getResultType() != txAExprResult::NODESET) { // XXX ErrorReport: nodeset expected return NS_ERROR_XSLT_NODESET_EXPECTED; } txNodeSet* nodes = static_cast<txNodeSet*> (static_cast<txAExprResult*> (exprRes)); if (nodes->isEmpty()) { aEs.gotoInstruction(mBailTarget); return NS_OK; } txNodeSorter sorter; uint32_t i, count = mSortKeys.Length(); for (i = 0; i < count; ++i) { SortKey& sort = mSortKeys[i]; rv = sorter.addSortElement(sort.mSelectExpr, sort.mLangExpr, sort.mDataTypeExpr, sort.mOrderExpr, sort.mCaseOrderExpr, aEs.getEvalContext()); NS_ENSURE_SUCCESS(rv, rv); } RefPtr<txNodeSet> sortedNodes; rv = sorter.sortNodeSet(nodes, &aEs, getter_AddRefs(sortedNodes)); NS_ENSURE_SUCCESS(rv, rv); txNodeSetContext* context = new txNodeSetContext(sortedNodes, &aEs); NS_ENSURE_TRUE(context, NS_ERROR_OUT_OF_MEMORY); context->next(); rv = aEs.pushEvalContext(context); if (NS_FAILED(rv)) { delete context; return rv; } return NS_OK; }
nsresult txSetParam::execute(txExecutionState& aEs) { nsresult rv = NS_OK; if (!aEs.mTemplateParams) { aEs.mTemplateParams = new txVariableMap; NS_ENSURE_TRUE(aEs.mTemplateParams, NS_ERROR_OUT_OF_MEMORY); } RefPtr<txAExprResult> exprRes; if (mValue) { rv = mValue->evaluate(aEs.getEvalContext(), getter_AddRefs(exprRes)); NS_ENSURE_SUCCESS(rv, rv); } else { nsAutoPtr<txRtfHandler> rtfHandler( static_cast<txRtfHandler*>(aEs.popResultHandler())); rv = rtfHandler->getAsRTF(getter_AddRefs(exprRes)); NS_ENSURE_SUCCESS(rv, rv); } rv = aEs.mTemplateParams->bindVariable(mName, exprRes); NS_ENSURE_SUCCESS(rv, rv); return NS_OK; }
nsresult txApplyImportsStart::execute(txExecutionState& aEs) { txExecutionState::TemplateRule* rule = aEs.getCurrentTemplateRule(); // The frame is set to null when there is no current template rule, or // when the current template rule is a default template. However this // instruction isn't used in default templates. if (!rule->mFrame) { // XXX ErrorReport: apply-imports instantiated without a current rule return NS_ERROR_XSLT_EXECUTION_FAILURE; } nsresult rv = aEs.pushParamMap(rule->mParams); NS_ENSURE_SUCCESS(rv, rv); txStylesheet::ImportFrame* frame = 0; txExpandedName mode(rule->mModeNsId, rule->mModeLocalName); txInstruction* templ = aEs.mStylesheet->findTemplate(aEs.getEvalContext()->getContextNode(), mode, &aEs, rule->mFrame, &frame); aEs.pushTemplateRule(frame, mode, rule->mParams); return aEs.runTemplate(templ); }
nsresult txAttribute::execute(txExecutionState& aEs) { nsAutoPtr<txTextHandler> handler( static_cast<txTextHandler*>(aEs.popResultHandler())); nsAutoString name; nsresult rv = mName->evaluateToString(aEs.getEvalContext(), name); NS_ENSURE_SUCCESS(rv, rv); const char16_t* colon; if (!XMLUtils::isValidQName(name, &colon) || TX_StringEqualsAtom(name, nsGkAtoms::xmlns)) { return NS_OK; } nsCOMPtr<nsIAtom> prefix; uint32_t lnameStart = 0; if (colon) { prefix = do_GetAtom(Substring(name.get(), colon)); lnameStart = colon - name.get() + 1; } int32_t nsId = kNameSpaceID_None; if (mNamespace) { nsAutoString nspace; rv = mNamespace->evaluateToString(aEs.getEvalContext(), nspace); NS_ENSURE_SUCCESS(rv, rv); if (!nspace.IsEmpty()) { nsId = txNamespaceManager::getNamespaceID(nspace); } } else if (colon) { nsId = mMappings->lookupNamespace(prefix); } // add attribute if everything was ok return nsId != kNameSpaceID_Unknown ? aEs.mResultHandler->attribute(prefix, Substring(name, lnameStart), nsId, handler->mValue) : NS_OK; }
nsresult txApplyTemplates::execute(txExecutionState& aEs) { txStylesheet::ImportFrame* frame = 0; txInstruction* templ = aEs.mStylesheet->findTemplate(aEs.getEvalContext()->getContextNode(), mMode, &aEs, nullptr, &frame); aEs.pushTemplateRule(frame, mMode, aEs.mTemplateParams); return aEs.runTemplate(templ); }
nsresult txNumber::execute(txExecutionState& aEs) { nsAutoString res; nsresult rv = txXSLTNumber::createNumber(mValue, mCount, mFrom, mLevel, mGroupingSize, mGroupingSeparator, mFormat, aEs.getEvalContext(), res); NS_ENSURE_SUCCESS(rv, rv); return aEs.mResultHandler->characters(res, false); }
nsresult txConditionalGoto::execute(txExecutionState& aEs) { bool exprRes; nsresult rv = mCondition->evaluateToBool(aEs.getEvalContext(), exprRes); NS_ENSURE_SUCCESS(rv, rv); if (!exprRes) { aEs.gotoInstruction(mTarget); } return NS_OK; }
nsresult txApplyDefaultElementTemplate::execute(txExecutionState& aEs) { txExecutionState::TemplateRule* rule = aEs.getCurrentTemplateRule(); txExpandedName mode(rule->mModeNsId, rule->mModeLocalName); txStylesheet::ImportFrame* frame = 0; txInstruction* templ = aEs.mStylesheet->findTemplate(aEs.getEvalContext()->getContextNode(), mode, &aEs, nullptr, &frame); aEs.pushTemplateRule(frame, mode, aEs.mTemplateParams); return aEs.runTemplate(templ); }
nsresult txCopy::execute(txExecutionState& aEs) { nsresult rv = NS_OK; const txXPathNode& node = aEs.getEvalContext()->getContextNode(); switch (txXPathNodeUtils::getNodeType(node)) { case txXPathNodeType::DOCUMENT_NODE: case txXPathNodeType::DOCUMENT_FRAGMENT_NODE: { const nsAFlatString& empty = EmptyString(); // "close" current element to ensure that no attributes are added rv = aEs.mResultHandler->characters(empty, false); NS_ENSURE_SUCCESS(rv, rv); rv = aEs.pushBool(false); NS_ENSURE_SUCCESS(rv, rv); break; } case txXPathNodeType::ELEMENT_NODE: { nsCOMPtr<nsIAtom> localName = txXPathNodeUtils::getLocalName(node); rv = aEs.mResultHandler-> startElement(txXPathNodeUtils::getPrefix(node), localName, nullptr, txXPathNodeUtils::getNamespaceID(node)); NS_ENSURE_SUCCESS(rv, rv); // XXX copy namespace nodes once we have them rv = aEs.pushBool(true); NS_ENSURE_SUCCESS(rv, rv); break; } default: { rv = copyNode(node, aEs); NS_ENSURE_SUCCESS(rv, rv); aEs.gotoInstruction(mBailTarget); } } return NS_OK; }
nsresult txLoopNodeSet::execute(txExecutionState& aEs) { aEs.popTemplateRule(); txNodeSetContext* context = static_cast<txNodeSetContext*>(aEs.getEvalContext()); if (!context->hasNext()) { delete aEs.popEvalContext(); return NS_OK; } context->next(); aEs.gotoInstruction(mTarget); return NS_OK; }
nsresult txSetVariable::execute(txExecutionState& aEs) { nsresult rv = NS_OK; RefPtr<txAExprResult> exprRes; if (mValue) { rv = mValue->evaluate(aEs.getEvalContext(), getter_AddRefs(exprRes)); NS_ENSURE_SUCCESS(rv, rv); } else { nsAutoPtr<txRtfHandler> rtfHandler( static_cast<txRtfHandler*>(aEs.popResultHandler())); rv = rtfHandler->getAsRTF(getter_AddRefs(exprRes)); NS_ENSURE_SUCCESS(rv, rv); } return aEs.bindVariable(mName, exprRes); }
nsresult txCopyOf::execute(txExecutionState& aEs) { RefPtr<txAExprResult> exprRes; nsresult rv = mSelect->evaluate(aEs.getEvalContext(), getter_AddRefs(exprRes)); NS_ENSURE_SUCCESS(rv, rv); switch (exprRes->getResultType()) { case txAExprResult::NODESET: { txNodeSet* nodes = static_cast<txNodeSet*> (static_cast<txAExprResult*> (exprRes)); int32_t i; for (i = 0; i < nodes->size(); ++i) { rv = copyNode(nodes->get(i), aEs); NS_ENSURE_SUCCESS(rv, rv); } break; } case txAExprResult::RESULT_TREE_FRAGMENT: { txResultTreeFragment* rtf = static_cast<txResultTreeFragment*> (static_cast<txAExprResult*>(exprRes)); return rtf->flushToHandler(aEs.mResultHandler); } default: { nsAutoString value; exprRes->stringValue(value); if (!value.IsEmpty()) { return aEs.mResultHandler->characters(value, false); } break; } } return NS_OK; }
nsresult txProcessingInstruction::execute(txExecutionState& aEs) { nsAutoPtr<txTextHandler> handler( static_cast<txTextHandler*>(aEs.popResultHandler())); XMLUtils::normalizePIValue(handler->mValue); nsAutoString name; nsresult rv = mName->evaluateToString(aEs.getEvalContext(), name); NS_ENSURE_SUCCESS(rv, rv); // Check name validity (must be valid NCName and a PITarget) // XXX Need to check for NCName and PITarget const char16_t* colon; if (!XMLUtils::isValidQName(name, &colon)) { // XXX ErrorReport: bad PI-target return NS_ERROR_FAILURE; } return aEs.mResultHandler->processingInstruction(name, handler->mValue); }
nsresult txLREAttribute::execute(txExecutionState& aEs) { RefPtr<txAExprResult> exprRes; nsresult rv = mValue->evaluate(aEs.getEvalContext(), getter_AddRefs(exprRes)); NS_ENSURE_SUCCESS(rv, rv); const nsString* value = exprRes->stringValuePointer(); if (value) { return aEs.mResultHandler->attribute(mPrefix, mLocalName, mLowercaseLocalName, mNamespaceID, *value); } nsAutoString valueStr; exprRes->stringValue(valueStr); return aEs.mResultHandler->attribute(mPrefix, mLocalName, mLowercaseLocalName, mNamespaceID, valueStr); }
nsresult txValueOf::execute(txExecutionState& aEs) { RefPtr<txAExprResult> exprRes; nsresult rv = mExpr->evaluate(aEs.getEvalContext(), getter_AddRefs(exprRes)); NS_ENSURE_SUCCESS(rv, rv); const nsString* value = exprRes->stringValuePointer(); if (value) { if (!value->IsEmpty()) { return aEs.mResultHandler->characters(*value, mDOE); } } else { nsAutoString valueStr; exprRes->stringValue(valueStr); if (!valueStr.IsEmpty()) { return aEs.mResultHandler->characters(valueStr, mDOE); } } return NS_OK; }
nsresult txStartElement::execute(txExecutionState& aEs) { nsAutoString name; nsresult rv = mName->evaluateToString(aEs.getEvalContext(), name); NS_ENSURE_SUCCESS(rv, rv); int32_t nsId = kNameSpaceID_None; nsCOMPtr<nsIAtom> prefix; uint32_t lnameStart = 0; const char16_t* colon; if (XMLUtils::isValidQName(name, &colon)) { if (colon) { prefix = do_GetAtom(Substring(name.get(), colon)); lnameStart = colon - name.get() + 1; } if (mNamespace) { nsAutoString nspace; rv = mNamespace->evaluateToString(aEs.getEvalContext(), nspace); NS_ENSURE_SUCCESS(rv, rv); if (!nspace.IsEmpty()) { nsId = txNamespaceManager::getNamespaceID(nspace); } } else { nsId = mMappings->lookupNamespace(prefix); } } else { nsId = kNameSpaceID_Unknown; } bool success = true; if (nsId != kNameSpaceID_Unknown) { rv = aEs.mResultHandler->startElement(prefix, Substring(name, lnameStart), nsId); } else { rv = NS_ERROR_XSLT_BAD_NODE_NAME; } if (rv == NS_ERROR_XSLT_BAD_NODE_NAME) { success = false; // we call characters with an empty string to "close" any element to // make sure that no attributes are added rv = aEs.mResultHandler->characters(EmptyString(), false); } NS_ENSURE_SUCCESS(rv, rv); rv = aEs.pushBool(success); NS_ENSURE_SUCCESS(rv, rv); return NS_OK; }