diff --git a/src/pugixml.hpp b/src/pugixml.hpp index d3dfea67edf5cb9973473765e4228a57529122a4..cb6180c273bf9fc113d4bc3f5a3118a08b0c6a26 100644 --- a/src/pugixml.hpp +++ b/src/pugixml.hpp @@ -56,11 +56,6 @@ namespace std # endif #endif -// No XPath without STL -#if !defined(PUGIXML_NO_XPATH) && defined(PUGIXML_NO_STL) -# define PUGIXML_NO_XPATH -#endif - // Include exception header for XPath #if !defined(PUGIXML_NO_XPATH) && !defined(PUGIXML_NO_EXCEPTIONS) # include <exception> @@ -2017,6 +2012,7 @@ namespace pugi */ double evaluate_number(const xml_node& n) const; + #ifndef PUGIXML_NO_STL /** * Evaluate expression as string value for the context node \a n. * If expression does not directly evaluate to string, the expression result is converted @@ -2027,7 +2023,19 @@ namespace pugi * \return evaluation result */ string_t evaluate_string(const xml_node& n) const; + #endif + /** + * Evaluate expression as string value for the context node \a n. + * If expression does not directly evaluate to string, the expression result is converted + * as through string() XPath function call. + * Throws std::bad_alloc on out of memory error. + * + * \param n - context node + * \return evaluation result + */ + size_t evaluate_string(char_t* buffer, size_t capacity, const xml_node& n) const; + /** * Evaluate expression as node set for the context node \a n. * If expression does not directly evaluate to node set, throws xpath_exception. diff --git a/src/pugixpath.cpp b/src/pugixpath.cpp index 0a3aadf8083b4ddd0a9898c6e6e5bae656ff52fb..378138df34c86a1e47a0040232cda1287c10da64 100644 --- a/src/pugixpath.cpp +++ b/src/pugixpath.cpp @@ -28,6 +28,12 @@ # include <wchar.h> #endif +#include <new> + +#ifndef PUGIXML_NO_STL +# include <string> +#endif + // int32_t #if !defined(_MSC_VER) || _MSC_VER >= 1600 # include <stdint.h> @@ -50,8 +56,6 @@ typedef __int32 int32_t; # pragma diag_suppress=237 // controlling expression is constant #endif -#include <string> - // String utilities prototypes namespace pugi { @@ -3762,6 +3766,7 @@ namespace pugi return _root->eval_number(c); } +#ifndef PUGIXML_NO_STL string_t xpath_query::evaluate_string(const xml_node& n) const { if (!_root) return string_t(); @@ -3770,7 +3775,21 @@ namespace pugi return _root->eval_string(c).c_str(); } +#endif + size_t xpath_query::evaluate_string(char_t* buffer, size_t capacity, const xml_node& n) const + { + xpath_context c(n, 1, 1); + xpath_string r = _root ? _root->eval_string(c) : xpath_string(); + + size_t size = r.length() + 1; + + // $$ zero-terminate? + if (capacity > 0) memcpy(buffer, r.c_str(), size < capacity ? size : capacity); + + return size; + } + xpath_node_set xpath_query::evaluate_node_set(const xml_node& n) const { if (!_root) return xpath_node_set();