michael@0: /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ michael@0: /* This Source Code Form is subject to the terms of the Mozilla Public michael@0: * License, v. 2.0. If a copy of the MPL was not distributed with this michael@0: * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ michael@0: michael@0: #include "txExpr.h" michael@0: #include "txIXPathContext.h" michael@0: #include "txNodeSet.h" michael@0: michael@0: //-------------/ michael@0: //- UnionExpr -/ michael@0: //-------------/ michael@0: michael@0: //-----------------------------/ michael@0: //- Virtual methods from Expr -/ michael@0: //-----------------------------/ michael@0: michael@0: /** michael@0: * Evaluates this Expr based on the given context node and processor state michael@0: * @param context the context node for evaluation of this Expr michael@0: * @param ps the ContextState containing the stack information needed michael@0: * for evaluation michael@0: * @return the result of the evaluation michael@0: **/ michael@0: nsresult michael@0: UnionExpr::evaluate(txIEvalContext* aContext, txAExprResult** aResult) michael@0: { michael@0: *aResult = nullptr; michael@0: nsRefPtr nodes; michael@0: nsresult rv = aContext->recycler()->getNodeSet(getter_AddRefs(nodes)); michael@0: NS_ENSURE_SUCCESS(rv, rv); michael@0: michael@0: uint32_t i, len = mExpressions.Length(); michael@0: for (i = 0; i < len; ++i) { michael@0: nsRefPtr exprResult; michael@0: rv = mExpressions[i]->evaluate(aContext, getter_AddRefs(exprResult)); michael@0: NS_ENSURE_SUCCESS(rv, rv); michael@0: michael@0: if (exprResult->getResultType() != txAExprResult::NODESET) { michael@0: //XXX ErrorReport: report nonnodeset error michael@0: return NS_ERROR_XSLT_NODESET_EXPECTED; michael@0: } michael@0: michael@0: nsRefPtr resultSet, ownedSet; michael@0: resultSet = static_cast michael@0: (static_cast(exprResult)); michael@0: exprResult = nullptr; michael@0: rv = aContext->recycler()-> michael@0: getNonSharedNodeSet(resultSet, getter_AddRefs(ownedSet)); michael@0: NS_ENSURE_SUCCESS(rv, rv); michael@0: michael@0: rv = nodes->addAndTransfer(ownedSet); michael@0: NS_ENSURE_SUCCESS(rv, rv); michael@0: } michael@0: michael@0: *aResult = nodes; michael@0: NS_ADDREF(*aResult); michael@0: michael@0: return NS_OK; michael@0: } //-- evaluate michael@0: michael@0: Expr::ExprType michael@0: UnionExpr::getType() michael@0: { michael@0: return UNION_EXPR; michael@0: } michael@0: michael@0: TX_IMPL_EXPR_STUBS_LIST(UnionExpr, NODESET_RESULT, mExpressions) michael@0: michael@0: bool michael@0: UnionExpr::isSensitiveTo(ContextSensitivity aContext) michael@0: { michael@0: uint32_t i, len = mExpressions.Length(); michael@0: for (i = 0; i < len; ++i) { michael@0: if (mExpressions[i]->isSensitiveTo(aContext)) { michael@0: return true; michael@0: } michael@0: } michael@0: michael@0: return false; michael@0: } michael@0: michael@0: #ifdef TX_TO_STRING michael@0: void michael@0: UnionExpr::toString(nsAString& dest) michael@0: { michael@0: uint32_t i; michael@0: for (i = 0; i < mExpressions.Length(); ++i) { michael@0: if (i > 0) michael@0: dest.AppendLiteral(" | "); michael@0: mExpressions[i]->toString(dest); michael@0: } michael@0: } michael@0: #endif