Classes | Namespaces | Macros | Typedefs | Enumerations | Functions | Variables
pugixml.cpp File Reference
#include "pugixml.hpp"
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <assert.h>
#include <math.h>
#include <float.h>
#include <istream>
#include <ostream>
#include <string>
#include <new>
#include <stdint.h>
Include dependency graph for pugixml.cpp:

Go to the source code of this file.

Classes

struct  xml_memory_management_function_storage< T >
 
struct  buffer_holder
 
struct  xml_memory_page
 
struct  xml_memory_string_header
 
struct  xml_allocator
 
struct  pugi::xml_attribute_struct
 A 'name=value' XML attribute structure. More...
 
struct  pugi::xml_node_struct
 An XML document tree node. More...
 
struct  xml_extra_buffer
 
struct  xml_document_struct
 
struct  opt_false
 
struct  opt_true
 
struct  utf8_counter
 
struct  utf8_writer
 
struct  utf16_counter
 
struct  utf16_writer
 
struct  utf32_counter
 
struct  utf32_writer
 
struct  latin1_writer
 
struct  wchar_selector< 2 >
 
struct  wchar_selector< 4 >
 
struct  utf_decoder< Traits, opt_swap >
 
struct  gap
 
struct  strconv_pcdata_impl< opt_trim, opt_eol, opt_escape >
 
struct  strconv_attribute_impl< opt_escape >
 
struct  xml_parser
 
class  xml_buffered_writer
 
struct  xml_stream_chunk< T >
 
struct  equal_to
 
struct  not_equal_to
 
struct  less
 
struct  less_equal
 
struct  xpath_memory_block
 
class  xpath_allocator
 
struct  xpath_allocator_capture
 
struct  xpath_stack
 
struct  xpath_stack_data
 
class  xpath_string
 
struct  document_order_comparator
 
struct  duplicate_comparator
 
struct  namespace_uri_predicate
 
struct  xpath_variable_boolean
 
struct  xpath_variable_number
 
struct  xpath_variable_string
 
struct  xpath_variable_node_set
 
class  xpath_node_set_raw
 
struct  xpath_context
 
struct  xpath_lexer_string
 
class  xpath_lexer
 
struct  axis_to_type< N >
 
class  xpath_ast_node
 
struct  xpath_parser
 
struct  xpath_parser::binary_op_t
 
struct  xpath_query_impl
 

Namespaces

namespace  pugi
 

Macros

#define SOURCE_PUGIXML_CPP
 
#define PUGI__NO_INLINE
 
#define PUGI__UNLIKELY(cond)   (cond)
 
#define PUGI__STATIC_ASSERT(cond)   { static const char condition_failed[(cond) ? 1 : -1] = {0}; (void)condition_failed[0]; }
 
#define PUGI__DMC_VOLATILE
 
#define PUGI__NS_BEGIN   namespace pugi { namespace impl { namespace {
 
#define PUGI__NS_END   } } }
 
#define PUGI__FN
 
#define PUGI__FN_NO_INLINE   PUGI__NO_INLINE
 
#define PUGI__IS_CHARTYPE_IMPL(c, ct, table)   (table[static_cast<unsigned char>(c)] & (ct))
 
#define PUGI__IS_CHARTYPE(c, ct)   PUGI__IS_CHARTYPE_IMPL(c, ct, chartype_table)
 
#define PUGI__IS_CHARTYPEX(c, ct)   PUGI__IS_CHARTYPE_IMPL(c, ct, chartypex_table)
 
#define PUGI__ENDSWITH(c, e)   ((c) == (e) || ((c) == 0 && endch == (e)))
 
#define PUGI__SKIPWS()   { while (PUGI__IS_CHARTYPE(*s, ct_space)) ++s; }
 
#define PUGI__OPTSET(OPT)   ( optmsk & (OPT) )
 
#define PUGI__PUSHNODE(TYPE)   { cursor = append_new_node(cursor, alloc, TYPE); if (!cursor) PUGI__THROW_ERROR(status_out_of_memory, s); }
 
#define PUGI__POPNODE()   { cursor = cursor->parent; }
 
#define PUGI__SCANFOR(X)   { while (*s != 0 && !(X)) ++s; }
 
#define PUGI__SCANWHILE(X)   { while (X) ++s; }
 
#define PUGI__SCANWHILE_UNROLL(X)   { while (X) { ++s; if (PUGI__UNLIKELY(!(X))) break; ++s; if (PUGI__UNLIKELY(!(X))) break; ++s; if (PUGI__UNLIKELY(!(X))) break; ++s; } }
 
#define PUGI__ENDSEG()   { ch = *s; *s = 0; ++s; }
 
#define PUGI__THROW_ERROR(err, m)   return error_offset = m, error_status = err, static_cast<char_t*>(0)
 
#define PUGI__CHECK_ERROR(err, m)   { if (*s == 0) PUGI__THROW_ERROR(err, m); }
 

Typedefs

typedef xml_memory_management_function_storage< int > xml_memory
 
typedef wchar_selector< sizeof(wchar_t)>::counter wchar_counter
 
typedef wchar_selector< sizeof(wchar_t)>::writer wchar_writer
 
typedef char_t *(* strconv_pcdata_t) (char_t *)
 
typedef char_t *(* strconv_attribute_t) (char_t *, char_t)
 

Enumerations

enum  chartype_t {
  ct_parse_pcdata = 1 , ct_parse_attr = 2 , ct_parse_attr_ws = 4 , ct_space = 8 ,
  ct_parse_cdata = 16 , ct_parse_comment = 32 , ct_symbol = 64 , ct_start_symbol = 128
}
 
enum  chartypex_t {
  ctx_special_pcdata = 1 , ctx_special_attr = 2 , ctx_start_symbol = 4 , ctx_digit = 8 ,
  ctx_symbol = 16
}
 
enum  lexeme_t {
  lex_none = 0 , lex_equal , lex_not_equal , lex_less ,
  lex_greater , lex_less_or_equal , lex_greater_or_equal , lex_plus ,
  lex_minus , lex_multiply , lex_union , lex_var_ref ,
  lex_open_brace , lex_close_brace , lex_quoted_string , lex_number ,
  lex_slash , lex_double_slash , lex_open_square_brace , lex_close_square_brace ,
  lex_string , lex_comma , lex_axis_attribute , lex_dot ,
  lex_double_dot , lex_double_colon , lex_eof
}
 
enum  ast_type_t {
  ast_unknown , ast_op_or , ast_op_and , ast_op_equal ,
  ast_op_not_equal , ast_op_less , ast_op_greater , ast_op_less_or_equal ,
  ast_op_greater_or_equal , ast_op_add , ast_op_subtract , ast_op_multiply ,
  ast_op_divide , ast_op_mod , ast_op_negate , ast_op_union ,
  ast_predicate , ast_filter , ast_filter_posinv , ast_string_constant ,
  ast_number_constant , ast_variable , ast_func_last , ast_func_position ,
  ast_func_count , ast_func_id , ast_func_local_name_0 , ast_func_local_name_1 ,
  ast_func_namespace_uri_0 , ast_func_namespace_uri_1 , ast_func_name_0 , ast_func_name_1 ,
  ast_func_string_0 , ast_func_string_1 , ast_func_concat , ast_func_starts_with ,
  ast_func_contains , ast_func_substring_before , ast_func_substring_after , ast_func_substring_2 ,
  ast_func_substring_3 , ast_func_string_length_0 , ast_func_string_length_1 , ast_func_normalize_space_0 ,
  ast_func_normalize_space_1 , ast_func_translate , ast_func_boolean , ast_func_not ,
  ast_func_true , ast_func_false , ast_func_lang , ast_func_number_0 ,
  ast_func_number_1 , ast_func_sum , ast_func_floor , ast_func_ceiling ,
  ast_func_round , ast_step , ast_step_root
}
 
enum  axis_t {
  axis_ancestor , axis_ancestor_or_self , axis_attribute , axis_child ,
  axis_descendant , axis_descendant_or_self , axis_following , axis_following_sibling ,
  axis_namespace , axis_parent , axis_preceding , axis_preceding_sibling ,
  axis_self
}
 
enum  nodetest_t {
  nodetest_none , nodetest_name , nodetest_type_node , nodetest_type_comment ,
  nodetest_type_pi , nodetest_type_text , nodetest_pi , nodetest_all ,
  nodetest_all_in_namespace
}
 

Functions

PUGI__NS_BEGIN PUGI__FN void * default_allocate (size_t size)
 
PUGI__FN void default_deallocate (void *ptr)
 
PUGI__NS_END PUGI__NS_BEGIN PUGI__FN size_t strlength (const char_t *s)
 
PUGI__FN bool strequal (const char_t *src, const char_t *dst)
 
PUGI__FN bool strequalrange (const char_t *lhs, const char_t *rhs, size_t count)
 
PUGI__FN size_t strlength_wide (const wchar_t *s)
 
xml_allocatorget_allocator (const xml_node_struct *node)
 
PUGI__NS_END PUGI__NS_BEGIN xml_attribute_struct * allocate_attribute (xml_allocator &alloc)
 
xml_node_struct * allocate_node (xml_allocator &alloc, xml_node_type type)
 
void destroy_attribute (xml_attribute_struct *a, xml_allocator &alloc)
 
void destroy_node (xml_node_struct *n, xml_allocator &alloc)
 
void append_node (xml_node_struct *child, xml_node_struct *node)
 
void prepend_node (xml_node_struct *child, xml_node_struct *node)
 
void insert_node_after (xml_node_struct *child, xml_node_struct *node)
 
void insert_node_before (xml_node_struct *child, xml_node_struct *node)
 
void remove_node (xml_node_struct *node)
 
PUGI__FN_NO_INLINE xml_node_struct * append_new_node (xml_node_struct *node, xml_allocator &alloc, xml_node_type type=node_element)
 
PUGI__FN_NO_INLINE xml_attribute_struct * append_new_attribute (xml_node_struct *node, xml_allocator &alloc)
 
PUGI__NS_END PUGI__NS_BEGIN uint16_t endian_swap (uint16_t value)
 
uint32_t endian_swap (uint32_t value)
 
template<typename T >
PUGI__FN void convert_utf_endian_swap (T *result, const T *data, size_t length)
 
PUGI__FN bool is_little_endian ()
 
PUGI__FN xml_encoding get_wchar_encoding ()
 
PUGI__FN xml_encoding guess_buffer_encoding (uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3)
 
PUGI__FN xml_encoding get_buffer_encoding (xml_encoding encoding, const void *contents, size_t size)
 
PUGI__FN bool get_mutable_buffer (char_t *&out_buffer, size_t &out_length, const void *contents, size_t size, bool is_mutable)
 
template<typename opt_swap >
PUGI__FN bool convert_buffer_utf16 (char_t *&out_buffer, size_t &out_length, const void *contents, size_t size, opt_swap)
 
template<typename opt_swap >
PUGI__FN bool convert_buffer_utf32 (char_t *&out_buffer, size_t &out_length, const void *contents, size_t size, opt_swap)
 
PUGI__FN size_t get_latin1_7bit_prefix_length (const uint8_t *data, size_t size)
 
PUGI__FN bool convert_buffer_latin1 (char_t *&out_buffer, size_t &out_length, const void *contents, size_t size, bool is_mutable)
 
PUGI__FN bool convert_buffer (char_t *&out_buffer, size_t &out_length, xml_encoding encoding, const void *contents, size_t size, bool is_mutable)
 
PUGI__FN size_t as_utf8_begin (const wchar_t *str, size_t length)
 
PUGI__FN void as_utf8_end (char *buffer, size_t size, const wchar_t *str, size_t length)
 
PUGI__FN std::string as_utf8_impl (const wchar_t *str, size_t length)
 
PUGI__FN std::basic_string< wchar_t > as_wide_impl (const char *str, size_t size)
 
bool strcpy_insitu_allow (size_t length, uintptr_t allocated, char_t *target)
 
PUGI__FN bool strcpy_insitu (char_t *&dest, uintptr_t &header, uintptr_t header_mask, const char_t *source)
 
PUGI__FN char_t * strconv_escape (char_t *s, gap &g)
 
PUGI__FN char_t * strconv_comment (char_t *s, char_t endch)
 
PUGI__FN char_t * strconv_cdata (char_t *s, char_t endch)
 
PUGI__FN strconv_pcdata_t get_strconv_pcdata (unsigned int optmask)
 
PUGI__FN strconv_attribute_t get_strconv_attribute (unsigned int optmask)
 
xml_parse_result make_parse_result (xml_parse_status status, ptrdiff_t offset=0)
 
PUGI__FN xml_encoding get_write_native_encoding ()
 
PUGI__FN xml_encoding get_write_encoding (xml_encoding encoding)
 
PUGI__FN size_t get_valid_length (const char_t *data, size_t length)
 
PUGI__FN size_t convert_buffer_output (char_t *, uint8_t *r_u8, uint16_t *r_u16, uint32_t *r_u32, const char_t *data, size_t length, xml_encoding encoding)
 
PUGI__FN void text_output_escaped (xml_buffered_writer &writer, const char_t *s, chartypex_t type)
 
PUGI__FN void text_output (xml_buffered_writer &writer, const char_t *s, chartypex_t type, unsigned int flags)
 
PUGI__FN void text_output_cdata (xml_buffered_writer &writer, const char_t *s)
 
PUGI__FN void node_output_attributes (xml_buffered_writer &writer, const xml_node &node, unsigned int flags)
 
PUGI__FN void node_output (xml_buffered_writer &writer, const xml_node &node, const char_t *indent, unsigned int flags, unsigned int depth)
 
bool has_declaration (const xml_node &node)
 
bool allow_insert_child (xml_node_type parent, xml_node_type child)
 
PUGI__FN bool allow_move (const xml_node &parent, const xml_node &child)
 
PUGI__FN void recursive_copy_skip (xml_node &dest, const xml_node &source, const xml_node &skip)
 
bool is_text_node (xml_node_struct *node)
 
PUGI__FN int get_integer_base (const char_t *value)
 
PUGI__FN int get_value_int (const char_t *value, int def)
 
PUGI__FN unsigned int get_value_uint (const char_t *value, unsigned int def)
 
PUGI__FN double get_value_double (const char_t *value, double def)
 
PUGI__FN float get_value_float (const char_t *value, float def)
 
PUGI__FN bool get_value_bool (const char_t *value, bool def)
 
PUGI__FN bool set_value_buffer (char_t *&dest, uintptr_t &header, uintptr_t header_mask, char(&buf)[128])
 
PUGI__FN bool set_value_convert (char_t *&dest, uintptr_t &header, uintptr_t header_mask, int value)
 
PUGI__FN bool set_value_convert (char_t *&dest, uintptr_t &header, uintptr_t header_mask, unsigned int value)
 
PUGI__FN bool set_value_convert (char_t *&dest, uintptr_t &header, uintptr_t header_mask, double value)
 
PUGI__FN bool set_value_convert (char_t *&dest, uintptr_t &header, uintptr_t header_mask, bool value)
 
PUGI__FN xml_parse_status get_file_size (FILE *file, size_t &out_result)
 
PUGI__FN size_t zero_terminate_buffer (void *buffer, size_t size, xml_encoding encoding)
 
PUGI__FN xml_parse_result load_file_impl (xml_document &doc, FILE *file, unsigned int options, xml_encoding encoding)
 
template<typename T >
PUGI__FN xml_parse_status load_stream_data_noseek (std::basic_istream< T > &stream, void **out_buffer, size_t *out_size)
 
template<typename T >
PUGI__FN xml_parse_status load_stream_data_seek (std::basic_istream< T > &stream, void **out_buffer, size_t *out_size)
 
template<typename T >
PUGI__FN xml_parse_result load_stream_impl (xml_document &doc, std::basic_istream< T > &stream, unsigned int options, xml_encoding encoding)
 
PUGI__FN char * convert_path_heap (const wchar_t *str)
 
PUGI__FN FILE * open_file_wide (const wchar_t *path, const wchar_t *mode)
 
PUGI__FN bool save_file_impl (const xml_document &doc, FILE *file, const char_t *indent, unsigned int flags, xml_encoding encoding)
 
PUGI__FN xml_parse_result load_buffer_impl (xml_document_struct *doc, xml_node_struct *root, void *contents, size_t size, unsigned int options, xml_encoding encoding, bool is_mutable, bool own, char_t **out_buffer)
 
static PUGI__FN void pugi::unspecified_bool_xml_attribute (xml_attribute ***)
 
static PUGI__FN void pugi::unspecified_bool_xml_node (xml_node ***)
 
static PUGI__FN void pugi::unspecified_bool_xml_text (xml_text ***)
 
PUGI__FN std::string PUGIXML_FUNCTION pugi::as_utf8 (const wchar_t *str)
 
PUGI__FN std::string PUGIXML_FUNCTION pugi::as_utf8 (const std::basic_string< wchar_t > &str)
 
PUGI__FN std::basic_string< wchar_t > PUGIXML_FUNCTION pugi::as_wide (const char *str)
 
PUGI__FN std::basic_string< wchar_t > PUGIXML_FUNCTION pugi::as_wide (const std::string &str)
 
PUGI__FN void PUGIXML_FUNCTION pugi::set_memory_management_functions (allocation_function allocate, deallocation_function deallocate)
 
PUGI__FN allocation_function PUGIXML_FUNCTION pugi::get_memory_allocation_function ()
 
PUGI__FN deallocation_function PUGIXML_FUNCTION pugi::get_memory_deallocation_function ()
 
template<typename T >
void swap (T &lhs, T &rhs)
 
template<typename I , typename Pred >
min_element (I begin, I end, const Pred &pred)
 
template<typename I >
void reverse (I begin, I end)
 
template<typename I >
unique (I begin, I end)
 
template<typename I >
void copy_backwards (I begin, I end, I target)
 
template<typename I , typename Pred , typename T >
void insertion_sort (I begin, I end, const Pred &pred, T *)
 
template<typename I , typename Pred >
void partition (I begin, I middle, I end, const Pred &pred, I *out_eqbeg, I *out_eqend)
 
template<typename I , typename Pred >
void median3 (I first, I middle, I last, const Pred &pred)
 
template<typename I , typename Pred >
void median (I first, I middle, I last, const Pred &pred)
 
template<typename I , typename Pred >
void sort (I begin, I end, const Pred &pred)
 
PUGI__FN xpath_string xpath_string_const (const char_t *str)
 
PUGI__NS_END PUGI__NS_BEGIN PUGI__FN bool starts_with (const char_t *string, const char_t *pattern)
 
PUGI__FN const char_t * find_char (const char_t *s, char_t c)
 
PUGI__FN const char_t * find_substring (const char_t *s, const char_t *p)
 
PUGI__FN char_t tolower_ascii (char_t ch)
 
PUGI__FN xpath_string string_value (const xpath_node &na, xpath_allocator *alloc)
 
PUGI__FN unsigned int node_height (xml_node n)
 
PUGI__FN bool node_is_before (xml_node ln, unsigned int lh, xml_node rn, unsigned int rh)
 
PUGI__FN bool node_is_ancestor (xml_node parent, xml_node node)
 
PUGI__FN const void * document_order (const xpath_node &xnode)
 
PUGI__FN double gen_nan ()
 
PUGI__FN bool is_nan (double value)
 
PUGI__FN const char_t * convert_number_to_string_special (double value)
 
PUGI__FN bool convert_number_to_boolean (double value)
 
PUGI__FN void truncate_zeros (char *begin, char *end)
 
PUGI__FN void convert_number_to_mantissa_exponent (double value, char *buffer, size_t buffer_size, char **out_mantissa, int *out_exponent)
 
PUGI__FN xpath_string convert_number_to_string (double value, xpath_allocator *alloc)
 
PUGI__FN bool check_string_to_number_format (const char_t *string)
 
PUGI__FN double convert_string_to_number (const char_t *string)
 
PUGI__FN bool convert_string_to_number_scratch (char_t(&buffer)[32], const char_t *begin, const char_t *end, double *out_result)
 
PUGI__FN double round_nearest (double value)
 
PUGI__FN double round_nearest_nzero (double value)
 
PUGI__FN const char_t * qualified_name (const xpath_node &node)
 
PUGI__FN const char_t * local_name (const xpath_node &node)
 
PUGI__FN const char_t * namespace_uri (const xml_node &node)
 
PUGI__FN const char_t * namespace_uri (const xml_attribute &attr, const xml_node &parent)
 
PUGI__FN const char_t * namespace_uri (const xpath_node &node)
 
PUGI__FN void normalize_space (char_t *buffer)
 
PUGI__FN void translate (char_t *buffer, const char_t *from, const char_t *to)
 
PUGI__FN unsigned int hash_string (const char_t *str)
 
template<typename T >
PUGI__FN T * new_xpath_variable (const char_t *name)
 
PUGI__FN xpath_variable * new_xpath_variable (xpath_value_type type, const char_t *name)
 
template<typename T >
PUGI__FN void delete_xpath_variable (T *var)
 
PUGI__FN void delete_xpath_variable (xpath_value_type type, xpath_variable *var)
 
PUGI__FN xpath_variable * get_variable_scratch (char_t(&buffer)[32], xpath_variable_set *set, const char_t *begin, const char_t *end)
 
PUGI__NS_END PUGI__NS_BEGIN PUGI__FN xpath_node_set::type_t xpath_sort (xpath_node *begin, xpath_node *end, xpath_node_set::type_t type, bool rev)
 
PUGI__FN xpath_node xpath_first (const xpath_node *begin, const xpath_node *end, xpath_node_set::type_t type)
 
PUGI__FN xpath_string evaluate_string_impl (xpath_query_impl *impl, const xpath_node &n, xpath_stack_data &sd)
 
static PUGI__FN void pugi::unspecified_bool_xpath_node (xpath_node ***)
 
static PUGI__FN void pugi::unspecified_bool_xpath_query (xpath_query ***)
 

Variables

PUGI__NS_END static PUGI__NS_BEGIN const size_t xml_memory_page_size
 
static const uintptr_t xml_memory_page_alignment = 32
 
static const uintptr_t xml_memory_page_pointer_mask = ~(xml_memory_page_alignment - 1)
 
static const uintptr_t xml_memory_page_name_allocated_mask = 16
 
static const uintptr_t xml_memory_page_value_allocated_mask = 8
 
static const uintptr_t xml_memory_page_type_mask = 7
 
static const unsigned char chartype_table [256]
 
static const unsigned char chartypex_table [256]
 
static const xpath_node_set dummy_node_set
 

Macro Definition Documentation

◆ PUGI__CHECK_ERROR

#define PUGI__CHECK_ERROR (   err,
 
)    { if (*s == 0) PUGI__THROW_ERROR(err, m); }

Definition at line 1909 of file pugixml.cpp.

◆ PUGI__DMC_VOLATILE

#define PUGI__DMC_VOLATILE

Definition at line 101 of file pugixml.cpp.

◆ PUGI__ENDSEG

#define PUGI__ENDSEG ( )    { ch = *s; *s = 0; ++s; }

Definition at line 1907 of file pugixml.cpp.

◆ PUGI__ENDSWITH

#define PUGI__ENDSWITH (   c,
 
)    ((c) == (e) || ((c) == 0 && endch == (e)))

Definition at line 1899 of file pugixml.cpp.

◆ PUGI__FN

#define PUGI__FN

Definition at line 128 of file pugixml.cpp.

◆ PUGI__FN_NO_INLINE

#define PUGI__FN_NO_INLINE   PUGI__NO_INLINE

Definition at line 129 of file pugixml.cpp.

◆ PUGI__IS_CHARTYPE

#define PUGI__IS_CHARTYPE (   c,
  ct 
)    PUGI__IS_CHARTYPE_IMPL(c, ct, chartype_table)

Definition at line 1195 of file pugixml.cpp.

◆ PUGI__IS_CHARTYPE_IMPL

#define PUGI__IS_CHARTYPE_IMPL (   c,
  ct,
  table 
)    (table[static_cast<unsigned char>(c)] & (ct))

Definition at line 1192 of file pugixml.cpp.

◆ PUGI__IS_CHARTYPEX

#define PUGI__IS_CHARTYPEX (   c,
  ct 
)    PUGI__IS_CHARTYPE_IMPL(c, ct, chartypex_table)

Definition at line 1196 of file pugixml.cpp.

◆ PUGI__NO_INLINE

#define PUGI__NO_INLINE

Definition at line 84 of file pugixml.cpp.

◆ PUGI__NS_BEGIN

#define PUGI__NS_BEGIN   namespace pugi { namespace impl { namespace {

Definition at line 125 of file pugixml.cpp.

◆ PUGI__NS_END

#define PUGI__NS_END   } } }

Definition at line 126 of file pugixml.cpp.

◆ PUGI__OPTSET

#define PUGI__OPTSET (   OPT)    ( optmsk & (OPT) )

Definition at line 1901 of file pugixml.cpp.

◆ PUGI__POPNODE

#define PUGI__POPNODE ( )    { cursor = cursor->parent; }

Definition at line 1903 of file pugixml.cpp.

◆ PUGI__PUSHNODE

#define PUGI__PUSHNODE (   TYPE)    { cursor = append_new_node(cursor, alloc, TYPE); if (!cursor) PUGI__THROW_ERROR(status_out_of_memory, s); }

Definition at line 1902 of file pugixml.cpp.

◆ PUGI__SCANFOR

#define PUGI__SCANFOR (   X)    { while (*s != 0 && !(X)) ++s; }

Definition at line 1904 of file pugixml.cpp.

◆ PUGI__SCANWHILE

#define PUGI__SCANWHILE (   X)    { while (X) ++s; }

Definition at line 1905 of file pugixml.cpp.

◆ PUGI__SCANWHILE_UNROLL

#define PUGI__SCANWHILE_UNROLL (   X)    { while (X) { ++s; if (PUGI__UNLIKELY(!(X))) break; ++s; if (PUGI__UNLIKELY(!(X))) break; ++s; if (PUGI__UNLIKELY(!(X))) break; ++s; } }

Definition at line 1906 of file pugixml.cpp.

◆ PUGI__SKIPWS

#define PUGI__SKIPWS ( )    { while (PUGI__IS_CHARTYPE(*s, ct_space)) ++s; }

Definition at line 1900 of file pugixml.cpp.

◆ PUGI__STATIC_ASSERT

#define PUGI__STATIC_ASSERT (   cond)    { static const char condition_failed[(cond) ? 1 : -1] = {0}; (void)condition_failed[0]; }

Definition at line 95 of file pugixml.cpp.

◆ PUGI__THROW_ERROR

#define PUGI__THROW_ERROR (   err,
 
)    return error_offset = m, error_status = err, static_cast<char_t*>(0)

Definition at line 1908 of file pugixml.cpp.

◆ PUGI__UNLIKELY

#define PUGI__UNLIKELY (   cond)    (cond)

Definition at line 91 of file pugixml.cpp.

◆ SOURCE_PUGIXML_CPP

#define SOURCE_PUGIXML_CPP

pugixml parser - version 1.4

Copyright (C) 2006-2014, by Arseny Kapoulkine (arsen.nosp@m.y.ka.nosp@m.poulk.nosp@m.ine@.nosp@m.gmail.nosp@m..com) Report bugs and download new versions at http://pugixml.org/

This library is distributed under the MIT License. See notice at the end of this file.

This work is based on the pugxml parser, which is: Copyright (C) 2003, by Kristen Wegner (krist.nosp@m.en@t.nosp@m.ima.n.nosp@m.et)

Definition at line 15 of file pugixml.cpp.

Typedef Documentation

◆ strconv_attribute_t

typedef char_t *(* strconv_attribute_t) (char_t *, char_t)

Definition at line 2038 of file pugixml.cpp.

◆ strconv_pcdata_t

typedef char_t *(* strconv_pcdata_t) (char_t *)

Definition at line 1967 of file pugixml.cpp.

◆ wchar_counter

typedef wchar_selector<sizeof(wchar_t)>::counter wchar_counter

Definition at line 949 of file pugixml.cpp.

◆ wchar_writer

typedef wchar_selector<sizeof(wchar_t)>::writer wchar_writer

Definition at line 950 of file pugixml.cpp.

◆ xml_memory

Definition at line 170 of file pugixml.cpp.

Enumeration Type Documentation

◆ ast_type_t

enum ast_type_t
Enumerator
ast_unknown 
ast_op_or 
ast_op_and 
ast_op_equal 
ast_op_not_equal 
ast_op_less 
ast_op_greater 
ast_op_less_or_equal 
ast_op_greater_or_equal 
ast_op_add 
ast_op_subtract 
ast_op_multiply 
ast_op_divide 
ast_op_mod 
ast_op_negate 
ast_op_union 
ast_predicate 
ast_filter 
ast_filter_posinv 
ast_string_constant 
ast_number_constant 
ast_variable 
ast_func_last 
ast_func_position 
ast_func_count 
ast_func_id 
ast_func_local_name_0 
ast_func_local_name_1 
ast_func_namespace_uri_0 
ast_func_namespace_uri_1 
ast_func_name_0 
ast_func_name_1 
ast_func_string_0 
ast_func_string_1 
ast_func_concat 
ast_func_starts_with 
ast_func_contains 
ast_func_substring_before 
ast_func_substring_after 
ast_func_substring_2 
ast_func_substring_3 
ast_func_string_length_0 
ast_func_string_length_1 
ast_func_normalize_space_0 
ast_func_normalize_space_1 
ast_func_translate 
ast_func_boolean 
ast_func_not 
ast_func_true 
ast_func_false 
ast_func_lang 
ast_func_number_0 
ast_func_number_1 
ast_func_sum 
ast_func_floor 
ast_func_ceiling 
ast_func_round 
ast_step 
ast_step_root 

Definition at line 7818 of file pugixml.cpp.

7819 {
7821 ast_op_or, // left or right
7822 ast_op_and, // left and right
7823 ast_op_equal, // left = right
7824 ast_op_not_equal, // left != right
7825 ast_op_less, // left < right
7826 ast_op_greater, // left > right
7827 ast_op_less_or_equal, // left <= right
7828 ast_op_greater_or_equal, // left >= right
7829 ast_op_add, // left + right
7830 ast_op_subtract, // left - right
7831 ast_op_multiply, // left * right
7832 ast_op_divide, // left / right
7833 ast_op_mod, // left % right
7834 ast_op_negate, // left - right
7835 ast_op_union, // left | right
7836 ast_predicate, // apply predicate to set; next points to next predicate
7837 ast_filter, // select * from left where right
7838 ast_filter_posinv, // select * from left where right; proximity position invariant
7839 ast_string_constant, // string constant
7840 ast_number_constant, // number constant
7841 ast_variable, // variable
7842 ast_func_last, // last()
7843 ast_func_position, // position()
7844 ast_func_count, // count(left)
7845 ast_func_id, // id(left)
7846 ast_func_local_name_0, // local-name()
7847 ast_func_local_name_1, // local-name(left)
7848 ast_func_namespace_uri_0, // namespace-uri()
7849 ast_func_namespace_uri_1, // namespace-uri(left)
7850 ast_func_name_0, // name()
7851 ast_func_name_1, // name(left)
7852 ast_func_string_0, // string()
7853 ast_func_string_1, // string(left)
7854 ast_func_concat, // concat(left, right, siblings)
7855 ast_func_starts_with, // starts_with(left, right)
7856 ast_func_contains, // contains(left, right)
7857 ast_func_substring_before, // substring-before(left, right)
7858 ast_func_substring_after, // substring-after(left, right)
7859 ast_func_substring_2, // substring(left, right)
7860 ast_func_substring_3, // substring(left, right, third)
7861 ast_func_string_length_0, // string-length()
7862 ast_func_string_length_1, // string-length(left)
7863 ast_func_normalize_space_0, // normalize-space()
7864 ast_func_normalize_space_1, // normalize-space(left)
7865 ast_func_translate, // translate(left, right, third)
7866 ast_func_boolean, // boolean(left)
7867 ast_func_not, // not(left)
7868 ast_func_true, // true()
7869 ast_func_false, // false()
7870 ast_func_lang, // lang(left)
7871 ast_func_number_0, // number()
7872 ast_func_number_1, // number(left)
7873 ast_func_sum, // sum(left)
7874 ast_func_floor, // floor(left)
7875 ast_func_ceiling, // ceiling(left)
7876 ast_func_round, // round(left)
7877 ast_step, // process set left with step
7878 ast_step_root // select root node
7879 };
@ ast_op_and
Definition pugixml.cpp:7822
@ ast_number_constant
Definition pugixml.cpp:7840
@ ast_filter
Definition pugixml.cpp:7837
@ ast_func_substring_3
Definition pugixml.cpp:7860
@ ast_func_sum
Definition pugixml.cpp:7873
@ ast_func_name_1
Definition pugixml.cpp:7851
@ ast_func_floor
Definition pugixml.cpp:7874
@ ast_op_divide
Definition pugixml.cpp:7832
@ ast_func_concat
Definition pugixml.cpp:7854
@ ast_op_equal
Definition pugixml.cpp:7823
@ ast_unknown
Definition pugixml.cpp:7820
@ ast_func_name_0
Definition pugixml.cpp:7850
@ ast_predicate
Definition pugixml.cpp:7836
@ ast_filter_posinv
Definition pugixml.cpp:7838
@ ast_func_not
Definition pugixml.cpp:7867
@ ast_variable
Definition pugixml.cpp:7841
@ ast_func_string_1
Definition pugixml.cpp:7853
@ ast_func_string_0
Definition pugixml.cpp:7852
@ ast_func_number_0
Definition pugixml.cpp:7871
@ ast_op_union
Definition pugixml.cpp:7835
@ ast_func_substring_before
Definition pugixml.cpp:7857
@ ast_func_string_length_0
Definition pugixml.cpp:7861
@ ast_func_local_name_1
Definition pugixml.cpp:7847
@ ast_func_namespace_uri_0
Definition pugixml.cpp:7848
@ ast_func_lang
Definition pugixml.cpp:7870
@ ast_func_true
Definition pugixml.cpp:7868
@ ast_func_normalize_space_1
Definition pugixml.cpp:7864
@ ast_op_not_equal
Definition pugixml.cpp:7824
@ ast_func_contains
Definition pugixml.cpp:7856
@ ast_op_greater
Definition pugixml.cpp:7826
@ ast_op_negate
Definition pugixml.cpp:7834
@ ast_func_substring_2
Definition pugixml.cpp:7859
@ ast_func_position
Definition pugixml.cpp:7843
@ ast_string_constant
Definition pugixml.cpp:7839
@ ast_func_ceiling
Definition pugixml.cpp:7875
@ ast_op_subtract
Definition pugixml.cpp:7830
@ ast_func_last
Definition pugixml.cpp:7842
@ ast_func_normalize_space_0
Definition pugixml.cpp:7863
@ ast_func_boolean
Definition pugixml.cpp:7866
@ ast_op_less_or_equal
Definition pugixml.cpp:7827
@ ast_step
Definition pugixml.cpp:7877
@ ast_op_multiply
Definition pugixml.cpp:7831
@ ast_func_count
Definition pugixml.cpp:7844
@ ast_func_substring_after
Definition pugixml.cpp:7858
@ ast_func_namespace_uri_1
Definition pugixml.cpp:7849
@ ast_step_root
Definition pugixml.cpp:7878
@ ast_func_translate
Definition pugixml.cpp:7865
@ ast_func_round
Definition pugixml.cpp:7876
@ ast_func_number_1
Definition pugixml.cpp:7872
@ ast_func_string_length_1
Definition pugixml.cpp:7862
@ ast_func_starts_with
Definition pugixml.cpp:7855
@ ast_op_add
Definition pugixml.cpp:7829
@ ast_op_or
Definition pugixml.cpp:7821
@ ast_op_greater_or_equal
Definition pugixml.cpp:7828
@ ast_func_false
Definition pugixml.cpp:7869
@ ast_func_local_name_0
Definition pugixml.cpp:7846
@ ast_op_mod
Definition pugixml.cpp:7833
@ ast_func_id
Definition pugixml.cpp:7845
@ ast_op_less
Definition pugixml.cpp:7825

◆ axis_t

enum axis_t
Enumerator
axis_ancestor 
axis_ancestor_or_self 
axis_attribute 
axis_child 
axis_descendant 
axis_descendant_or_self 
axis_following 
axis_following_sibling 
axis_namespace 
axis_parent 
axis_preceding 
axis_preceding_sibling 
axis_self 

Definition at line 7881 of file pugixml.cpp.

7882 {
7886 axis_child,
7895 axis_self
7896 };
@ axis_preceding
Definition pugixml.cpp:7893
@ axis_ancestor_or_self
Definition pugixml.cpp:7884
@ axis_attribute
Definition pugixml.cpp:7885
@ axis_following_sibling
Definition pugixml.cpp:7890
@ axis_child
Definition pugixml.cpp:7886
@ axis_descendant
Definition pugixml.cpp:7887
@ axis_descendant_or_self
Definition pugixml.cpp:7888
@ axis_self
Definition pugixml.cpp:7895
@ axis_following
Definition pugixml.cpp:7889
@ axis_ancestor
Definition pugixml.cpp:7883
@ axis_preceding_sibling
Definition pugixml.cpp:7894
@ axis_namespace
Definition pugixml.cpp:7891
@ axis_parent
Definition pugixml.cpp:7892

◆ chartype_t

enum chartype_t
Enumerator
ct_parse_pcdata 
ct_parse_attr 
ct_parse_attr_ws 
ct_space 
ct_parse_cdata 
ct_parse_comment 
ct_symbol 
ct_start_symbol 

Definition at line 1125 of file pugixml.cpp.

1126 {
1127 ct_parse_pcdata = 1, // \0, &, \r, <
1128 ct_parse_attr = 2, // \0, &, \r, ', "
1129 ct_parse_attr_ws = 4, // \0, &, \r, ', ", \n, tab
1130 ct_space = 8, // \r, \n, space, tab
1131 ct_parse_cdata = 16, // \0, ], >, \r
1132 ct_parse_comment = 32, // \0, -, >, \r
1133 ct_symbol = 64, // Any symbol > 127, a-z, A-Z, 0-9, _, :, -, .
1134 ct_start_symbol = 128 // Any symbol > 127, a-z, A-Z, _, :
1135 };
@ ct_parse_comment
Definition pugixml.cpp:1132
@ ct_start_symbol
Definition pugixml.cpp:1134
@ ct_parse_attr
Definition pugixml.cpp:1128
@ ct_parse_attr_ws
Definition pugixml.cpp:1129
@ ct_parse_cdata
Definition pugixml.cpp:1131
@ ct_parse_pcdata
Definition pugixml.cpp:1127
@ ct_space
Definition pugixml.cpp:1130
@ ct_symbol
Definition pugixml.cpp:1133

◆ chartypex_t

Enumerator
ctx_special_pcdata 
ctx_special_attr 
ctx_start_symbol 
ctx_digit 
ctx_symbol 

Definition at line 1158 of file pugixml.cpp.

1159 {
1160 ctx_special_pcdata = 1, // Any symbol >= 0 and < 32 (except \t, \r, \n), &, <, >
1161 ctx_special_attr = 2, // Any symbol >= 0 and < 32 (except \t), &, <, >, "
1162 ctx_start_symbol = 4, // Any symbol > 127, a-z, A-Z, _
1163 ctx_digit = 8, // 0-9
1164 ctx_symbol = 16 // Any symbol > 127, a-z, A-Z, 0-9, _, -, .
1165 };
@ ctx_digit
Definition pugixml.cpp:1163
@ ctx_special_attr
Definition pugixml.cpp:1161
@ ctx_symbol
Definition pugixml.cpp:1164
@ ctx_start_symbol
Definition pugixml.cpp:1162
@ ctx_special_pcdata
Definition pugixml.cpp:1160

◆ lexeme_t

enum lexeme_t
Enumerator
lex_none 
lex_equal 
lex_not_equal 
lex_less 
lex_greater 
lex_less_or_equal 
lex_greater_or_equal 
lex_plus 
lex_minus 
lex_multiply 
lex_union 
lex_var_ref 
lex_open_brace 
lex_close_brace 
lex_quoted_string 
lex_number 
lex_slash 
lex_double_slash 
lex_open_square_brace 
lex_close_square_brace 
lex_string 
lex_comma 
lex_axis_attribute 
lex_dot 
lex_double_dot 
lex_double_colon 
lex_eof 

Definition at line 7464 of file pugixml.cpp.

7465 {
7466 lex_none = 0,
7467 lex_equal,
7469 lex_less,
7473 lex_plus,
7474 lex_minus,
7476 lex_union,
7481 lex_number,
7482 lex_slash,
7486 lex_string,
7487 lex_comma,
7489 lex_dot,
7492 lex_eof
7493 };
@ lex_multiply
Definition pugixml.cpp:7475
@ lex_double_slash
Definition pugixml.cpp:7483
@ lex_quoted_string
Definition pugixml.cpp:7480
@ lex_not_equal
Definition pugixml.cpp:7468
@ lex_axis_attribute
Definition pugixml.cpp:7488
@ lex_less
Definition pugixml.cpp:7469
@ lex_equal
Definition pugixml.cpp:7467
@ lex_greater_or_equal
Definition pugixml.cpp:7472
@ lex_none
Definition pugixml.cpp:7466
@ lex_union
Definition pugixml.cpp:7476
@ lex_comma
Definition pugixml.cpp:7487
@ lex_close_brace
Definition pugixml.cpp:7479
@ lex_slash
Definition pugixml.cpp:7482
@ lex_var_ref
Definition pugixml.cpp:7477
@ lex_dot
Definition pugixml.cpp:7489
@ lex_minus
Definition pugixml.cpp:7474
@ lex_string
Definition pugixml.cpp:7486
@ lex_eof
Definition pugixml.cpp:7492
@ lex_plus
Definition pugixml.cpp:7473
@ lex_number
Definition pugixml.cpp:7481
@ lex_greater
Definition pugixml.cpp:7470
@ lex_double_dot
Definition pugixml.cpp:7490
@ lex_less_or_equal
Definition pugixml.cpp:7471
@ lex_close_square_brace
Definition pugixml.cpp:7485
@ lex_open_square_brace
Definition pugixml.cpp:7484
@ lex_open_brace
Definition pugixml.cpp:7478
@ lex_double_colon
Definition pugixml.cpp:7491

◆ nodetest_t

enum nodetest_t
Enumerator
nodetest_none 
nodetest_name 
nodetest_type_node 
nodetest_type_comment 
nodetest_type_pi 
nodetest_type_text 
nodetest_pi 
nodetest_all 
nodetest_all_in_namespace 

Definition at line 7898 of file pugixml.cpp.

7899 {
7909 };
@ nodetest_all
Definition pugixml.cpp:7907
@ nodetest_name
Definition pugixml.cpp:7901
@ nodetest_none
Definition pugixml.cpp:7900
@ nodetest_type_text
Definition pugixml.cpp:7905
@ nodetest_all_in_namespace
Definition pugixml.cpp:7908
@ nodetest_pi
Definition pugixml.cpp:7906
@ nodetest_type_comment
Definition pugixml.cpp:7903
@ nodetest_type_node
Definition pugixml.cpp:7902
@ nodetest_type_pi
Definition pugixml.cpp:7904

Function Documentation

◆ allocate_attribute()

PUGI__NS_END PUGI__NS_BEGIN xml_attribute_struct * allocate_attribute ( xml_allocator alloc)
inline

Definition at line 558 of file pugixml.cpp.

559 {
560 xml_memory_page* page;
561 void* memory = alloc.allocate_memory(sizeof(xml_attribute_struct), page);
562
563 return new (memory) xml_attribute_struct(page);
564 }
void * allocate_memory(size_t size, xml_memory_page *&out_page)
Definition pugixml.cpp:348

References xml_allocator::allocate_memory().

Referenced by append_new_attribute().

◆ allocate_node()

xml_node_struct * allocate_node ( xml_allocator alloc,
xml_node_type  type 
)
inline

Definition at line 566 of file pugixml.cpp.

567 {
568 xml_memory_page* page;
569 void* memory = alloc.allocate_memory(sizeof(xml_node_struct), page);
570
571 return new (memory) xml_node_struct(page, type);
572 }

References xml_allocator::allocate_memory().

Referenced by append_new_node().

◆ allow_insert_child()

bool allow_insert_child ( xml_node_type  parent,
xml_node_type  child 
)
inline

Definition at line 3430 of file pugixml.cpp.

3431 {
3432 if (parent != node_document && parent != node_element) return false;
3433 if (child == node_document || child == node_null) return false;
3434 if (parent != node_document && (child == node_declaration || child == node_doctype)) return false;
3435
3436 return true;
3437 }

Referenced by allow_move().

◆ allow_move()

PUGI__FN bool allow_move ( const xml_node &  parent,
const xml_node &  child 
)

Definition at line 3439 of file pugixml.cpp.

3440 {
3441 // check that child can be a child of parent
3442 if (!allow_insert_child(parent.type(), child.type()))
3443 return false;
3444
3445 // check that node is not moved between documents
3446 if (parent.root() != child.root())
3447 return false;
3448
3449 // check that new parent is not in the child subtree
3450 xml_node cur = parent;
3451
3452 while (cur)
3453 {
3454 if (cur == child)
3455 return false;
3456
3457 cur = cur.parent();
3458 }
3459
3460 return true;
3461 }
bool allow_insert_child(xml_node_type parent, xml_node_type child)
Definition pugixml.cpp:3430

References allow_insert_child().

◆ append_new_attribute()

PUGI__FN_NO_INLINE xml_attribute_struct * append_new_attribute ( xml_node_struct *  node,
xml_allocator alloc 
)

Definition at line 712 of file pugixml.cpp.

713 {
714 xml_attribute_struct* a = allocate_attribute(alloc);
715 if (!a) return 0;
716
717 xml_attribute_struct* first_attribute = node->first_attribute;
718
719 if (first_attribute)
720 {
721 xml_attribute_struct* last_attribute = first_attribute->prev_attribute_c;
722
723 last_attribute->next_attribute = a;
724 a->prev_attribute_c = last_attribute;
725 first_attribute->prev_attribute_c = a;
726 }
727 else
728 {
729 node->first_attribute = a;
730 a->prev_attribute_c = a;
731 }
732
733 return a;
734 }
PUGI__NS_END PUGI__NS_BEGIN xml_attribute_struct * allocate_attribute(xml_allocator &alloc)
Definition pugixml.cpp:558

References allocate_attribute().

Referenced by xml_parser::parse_tree().

◆ append_new_node()

PUGI__FN_NO_INLINE xml_node_struct * append_new_node ( xml_node_struct *  node,
xml_allocator alloc,
xml_node_type  type = node_element 
)

Definition at line 702 of file pugixml.cpp.

703 {
704 xml_node_struct* child = allocate_node(alloc, type);
705 if (!child) return 0;
706
707 append_node(child, node);
708
709 return child;
710 }
xml_node_struct * allocate_node(xml_allocator &alloc, xml_node_type type)
Definition pugixml.cpp:566
void append_node(xml_node_struct *child, xml_node_struct *node)
Definition pugixml.cpp:612

References allocate_node(), and append_node().

◆ append_node()

void append_node ( xml_node_struct *  child,
xml_node_struct *  node 
)
inline

Definition at line 612 of file pugixml.cpp.

613 {
614 child->parent = node;
615
616 xml_node_struct* head = node->first_child;
617
618 if (head)
619 {
620 xml_node_struct* tail = head->prev_sibling_c;
621
622 tail->next_sibling = child;
623 child->prev_sibling_c = tail;
624 head->prev_sibling_c = child;
625 }
626 else
627 {
628 node->first_child = child;
629 child->prev_sibling_c = child;
630 }
631
632 child->next_sibling = 0;
633 }

Referenced by append_new_node().

◆ as_utf8_begin()

PUGI__FN size_t as_utf8_begin ( const wchar_t *  str,
size_t  length 
)

Definition at line 1594 of file pugixml.cpp.

1595 {
1596 // get length in utf8 characters
1597 return utf_decoder<utf8_counter>::decode_wchar_block(str, length, 0);
1598 }
static Traits::value_type decode_wchar_block(const wchar_t *data, size_t size, typename Traits::value_type result)
Definition pugixml.cpp:1105

References utf_decoder< Traits, opt_swap >::decode_wchar_block().

Referenced by as_utf8_impl(), and convert_path_heap().

◆ as_utf8_end()

PUGI__FN void as_utf8_end ( char *  buffer,
size_t  size,
const wchar_t *  str,
size_t  length 
)

Definition at line 1600 of file pugixml.cpp.

1601 {
1602 // convert to utf8
1603 uint8_t* begin = reinterpret_cast<uint8_t*>(buffer);
1604 uint8_t* end = utf_decoder<utf8_writer>::decode_wchar_block(str, length, begin);
1605
1606 assert(begin + size == end);
1607 (void)!end;
1608
1609 // zero-terminate
1610 buffer[size] = 0;
1611 }
unsigned char uint8_t
Definition stdint_msvc.h:79

References utf_decoder< Traits, opt_swap >::decode_wchar_block().

Referenced by as_utf8_impl(), and convert_path_heap().

◆ as_utf8_impl()

PUGI__FN std::string as_utf8_impl ( const wchar_t *  str,
size_t  length 
)

Definition at line 1614 of file pugixml.cpp.

1615 {
1616 // first pass: get length in utf8 characters
1617 size_t size = as_utf8_begin(str, length);
1618
1619 // allocate resulting string
1620 std::string result;
1621 result.resize(size);
1622
1623 // second pass: convert to utf8
1624 if (size > 0) as_utf8_end(&result[0], size, str, length);
1625
1626 return result;
1627 }
PUGI__FN void as_utf8_end(char *buffer, size_t size, const wchar_t *str, size_t length)
Definition pugixml.cpp:1600
PUGI__FN size_t as_utf8_begin(const wchar_t *str, size_t length)
Definition pugixml.cpp:1594

References as_utf8_begin(), and as_utf8_end().

◆ as_wide_impl()

PUGI__FN std::basic_string< wchar_t > as_wide_impl ( const char *  str,
size_t  size 
)

Definition at line 1629 of file pugixml.cpp.

1630 {
1631 const uint8_t* data = reinterpret_cast<const uint8_t*>(str);
1632
1633 // first pass: get length in wchar_t units
1634 size_t length = utf_decoder<wchar_counter>::decode_utf8_block(data, size, 0);
1635
1636 // allocate resulting string
1637 std::basic_string<wchar_t> result;
1638 result.resize(length);
1639
1640 // second pass: convert to wchar_t
1641 if (length > 0)
1642 {
1643 wchar_writer::value_type begin = reinterpret_cast<wchar_writer::value_type>(&result[0]);
1644 wchar_writer::value_type end = utf_decoder<wchar_writer>::decode_utf8_block(data, size, begin);
1645
1646 assert(begin + length == end);
1647 (void)!end;
1648 }
1649
1650 return result;
1651 }
static Traits::value_type decode_utf8_block(const uint8_t *data, size_t size, typename Traits::value_type result)
Definition pugixml.cpp:954

References utf_decoder< Traits, opt_swap >::decode_utf8_block().

◆ check_string_to_number_format()

PUGI__FN bool check_string_to_number_format ( const char_t *  string)

Definition at line 6938 of file pugixml.cpp.

6939 {
6940 // parse leading whitespace
6941 while (PUGI__IS_CHARTYPE(*string, ct_space)) ++string;
6942
6943 // parse sign
6944 if (*string == '-') ++string;
6945
6946 if (!*string) return false;
6947
6948 // if there is no integer part, there should be a decimal part with at least one digit
6949 if (!PUGI__IS_CHARTYPEX(string[0], ctx_digit) && (string[0] != '.' || !PUGI__IS_CHARTYPEX(string[1], ctx_digit))) return false;
6950
6951 // parse integer part
6952 while (PUGI__IS_CHARTYPEX(*string, ctx_digit)) ++string;
6953
6954 // parse decimal part
6955 if (*string == '.')
6956 {
6957 ++string;
6958
6959 while (PUGI__IS_CHARTYPEX(*string, ctx_digit)) ++string;
6960 }
6961
6962 // parse trailing whitespace
6963 while (PUGI__IS_CHARTYPE(*string, ct_space)) ++string;
6964
6965 return *string == 0;
6966 }
#define PUGI__IS_CHARTYPE(c, ct)
Definition pugixml.cpp:1195
#define PUGI__IS_CHARTYPEX(c, ct)
Definition pugixml.cpp:1196

References ct_space, ctx_digit, PUGI__IS_CHARTYPE, and PUGI__IS_CHARTYPEX.

Referenced by convert_string_to_number().

◆ convert_buffer()

PUGI__FN bool convert_buffer ( char_t *&  out_buffer,
size_t &  out_length,
xml_encoding  encoding,
const void *  contents,
size_t  size,
bool  is_mutable 
)

Definition at line 1561 of file pugixml.cpp.

1562 {
1563 // fast path: no conversion required
1564 if (encoding == encoding_utf8) return get_mutable_buffer(out_buffer, out_length, contents, size, is_mutable);
1565
1566 // source encoding is utf16
1567 if (encoding == encoding_utf16_be || encoding == encoding_utf16_le)
1568 {
1569 xml_encoding native_encoding = is_little_endian() ? encoding_utf16_le : encoding_utf16_be;
1570
1571 return (native_encoding == encoding) ?
1572 convert_buffer_utf16(out_buffer, out_length, contents, size, opt_false()) :
1573 convert_buffer_utf16(out_buffer, out_length, contents, size, opt_true());
1574 }
1575
1576 // source encoding is utf32
1577 if (encoding == encoding_utf32_be || encoding == encoding_utf32_le)
1578 {
1579 xml_encoding native_encoding = is_little_endian() ? encoding_utf32_le : encoding_utf32_be;
1580
1581 return (native_encoding == encoding) ?
1582 convert_buffer_utf32(out_buffer, out_length, contents, size, opt_false()) :
1583 convert_buffer_utf32(out_buffer, out_length, contents, size, opt_true());
1584 }
1585
1586 // source encoding is latin1
1587 if (encoding == encoding_latin1) return convert_buffer_latin1(out_buffer, out_length, contents, size, is_mutable);
1588
1589 assert(!"Invalid encoding");
1590 return false;
1591 }
PUGI__FN bool get_mutable_buffer(char_t *&out_buffer, size_t &out_length, const void *contents, size_t size, bool is_mutable)
Definition pugixml.cpp:1264
PUGI__FN bool is_little_endian()
Definition pugixml.cpp:1198
PUGI__FN bool convert_buffer_utf32(char_t *&out_buffer, size_t &out_length, const void *contents, size_t size, opt_swap)
Definition pugixml.cpp:1490
PUGI__FN bool convert_buffer_latin1(char_t *&out_buffer, size_t &out_length, const void *contents, size_t size, bool is_mutable)
Definition pugixml.cpp:1524
PUGI__FN bool convert_buffer_utf16(char_t *&out_buffer, size_t &out_length, const void *contents, size_t size, opt_swap)
Definition pugixml.cpp:1465

References convert_buffer_latin1(), convert_buffer_utf16(), convert_buffer_utf32(), get_mutable_buffer(), and is_little_endian().

◆ convert_buffer_latin1()

PUGI__FN bool convert_buffer_latin1 ( char_t *&  out_buffer,
size_t &  out_length,
const void *  contents,
size_t  size,
bool  is_mutable 
)

Definition at line 1524 of file pugixml.cpp.

1525 {
1526 const uint8_t* data = static_cast<const uint8_t*>(contents);
1527 size_t data_length = size;
1528
1529 // get size of prefix that does not need utf8 conversion
1530 size_t prefix_length = get_latin1_7bit_prefix_length(data, data_length);
1531 assert(prefix_length <= data_length);
1532
1533 const uint8_t* postfix = data + prefix_length;
1534 size_t postfix_length = data_length - prefix_length;
1535
1536 // if no conversion is needed, just return the original buffer
1537 if (postfix_length == 0) return get_mutable_buffer(out_buffer, out_length, contents, size, is_mutable);
1538
1539 // first pass: get length in utf8 units
1540 size_t length = prefix_length + utf_decoder<utf8_counter>::decode_latin1_block(postfix, postfix_length, 0);
1541
1542 // allocate buffer of suitable length
1543 char_t* buffer = static_cast<char_t*>(xml_memory::allocate((length + 1) * sizeof(char_t)));
1544 if (!buffer) return false;
1545
1546 // second pass: convert latin1 input to utf8
1547 memcpy(buffer, data, prefix_length);
1548
1549 uint8_t* obegin = reinterpret_cast<uint8_t*>(buffer);
1550 uint8_t* oend = utf_decoder<utf8_writer>::decode_latin1_block(postfix, postfix_length, obegin + prefix_length);
1551
1552 assert(oend == obegin + length);
1553 *oend = 0;
1554
1555 out_buffer = buffer;
1556 out_length = length + 1;
1557
1558 return true;
1559 }
PUGI__FN size_t get_latin1_7bit_prefix_length(const uint8_t *data, size_t size)
Definition pugixml.cpp:1515
static Traits::value_type decode_latin1_block(const uint8_t *data, size_t size, typename Traits::value_type result)
Definition pugixml.cpp:1085
static allocation_function allocate
Definition pugixml.cpp:163

References xml_memory_management_function_storage< T >::allocate, utf_decoder< Traits, opt_swap >::decode_latin1_block(), get_latin1_7bit_prefix_length(), and get_mutable_buffer().

Referenced by convert_buffer().

◆ convert_buffer_output()

PUGI__FN size_t convert_buffer_output ( char_t *  ,
uint8_t r_u8,
uint16_t r_u16,
uint32_t r_u32,
const char_t *  data,
size_t  length,
xml_encoding  encoding 
)

Definition at line 2977 of file pugixml.cpp.

2978 {
2979 if (encoding == encoding_utf16_be || encoding == encoding_utf16_le)
2980 {
2981 uint16_t* dest = r_u16;
2982
2983 // convert to native utf16
2984 uint16_t* end = utf_decoder<utf16_writer>::decode_utf8_block(reinterpret_cast<const uint8_t*>(data), length, dest);
2985
2986 // swap if necessary
2987 xml_encoding native_encoding = is_little_endian() ? encoding_utf16_le : encoding_utf16_be;
2988
2989 if (native_encoding != encoding) convert_utf_endian_swap(dest, dest, static_cast<size_t>(end - dest));
2990
2991 return static_cast<size_t>(end - dest) * sizeof(uint16_t);
2992 }
2993
2994 if (encoding == encoding_utf32_be || encoding == encoding_utf32_le)
2995 {
2996 uint32_t* dest = r_u32;
2997
2998 // convert to native utf32
2999 uint32_t* end = utf_decoder<utf32_writer>::decode_utf8_block(reinterpret_cast<const uint8_t*>(data), length, dest);
3000
3001 // swap if necessary
3002 xml_encoding native_encoding = is_little_endian() ? encoding_utf32_le : encoding_utf32_be;
3003
3004 if (native_encoding != encoding) convert_utf_endian_swap(dest, dest, static_cast<size_t>(end - dest));
3005
3006 return static_cast<size_t>(end - dest) * sizeof(uint32_t);
3007 }
3008
3009 if (encoding == encoding_latin1)
3010 {
3011 uint8_t* dest = r_u8;
3012 uint8_t* end = utf_decoder<latin1_writer>::decode_utf8_block(reinterpret_cast<const uint8_t*>(data), length, dest);
3013
3014 return static_cast<size_t>(end - dest);
3015 }
3016
3017 assert(!"Invalid encoding");
3018 return 0;
3019 }
PUGI__FN void convert_utf_endian_swap(T *result, const T *data, size_t length)
Definition pugixml.cpp:1111
unsigned short uint16_t
Definition stdint_msvc.h:80
unsigned int uint32_t
Definition stdint_msvc.h:81

References convert_utf_endian_swap(), utf_decoder< Traits, opt_swap >::decode_utf8_block(), and is_little_endian().

Referenced by xml_buffered_writer::flush().

◆ convert_buffer_utf16()

template<typename opt_swap >
PUGI__FN bool convert_buffer_utf16 ( char_t *&  out_buffer,
size_t &  out_length,
const void *  contents,
size_t  size,
opt_swap   
)

Definition at line 1465 of file pugixml.cpp.

1466 {
1467 const uint16_t* data = static_cast<const uint16_t*>(contents);
1468 size_t data_length = size / sizeof(uint16_t);
1469
1470 // first pass: get length in utf8 units
1471 size_t length = utf_decoder<utf8_counter, opt_swap>::decode_utf16_block(data, data_length, 0);
1472
1473 // allocate buffer of suitable length
1474 char_t* buffer = static_cast<char_t*>(xml_memory::allocate((length + 1) * sizeof(char_t)));
1475 if (!buffer) return false;
1476
1477 // second pass: convert utf16 input to utf8
1478 uint8_t* obegin = reinterpret_cast<uint8_t*>(buffer);
1479 uint8_t* oend = utf_decoder<utf8_writer, opt_swap>::decode_utf16_block(data, data_length, obegin);
1480
1481 assert(oend == obegin + length);
1482 *oend = 0;
1483
1484 out_buffer = buffer;
1485 out_length = length + 1;
1486
1487 return true;
1488 }
static Traits::value_type decode_utf16_block(const uint16_t *data, size_t size, typename Traits::value_type result)
Definition pugixml.cpp:1016

References xml_memory_management_function_storage< T >::allocate, and utf_decoder< Traits, opt_swap >::decode_utf16_block().

Referenced by convert_buffer().

◆ convert_buffer_utf32()

template<typename opt_swap >
PUGI__FN bool convert_buffer_utf32 ( char_t *&  out_buffer,
size_t &  out_length,
const void *  contents,
size_t  size,
opt_swap   
)

Definition at line 1490 of file pugixml.cpp.

1491 {
1492 const uint32_t* data = static_cast<const uint32_t*>(contents);
1493 size_t data_length = size / sizeof(uint32_t);
1494
1495 // first pass: get length in utf8 units
1496 size_t length = utf_decoder<utf8_counter, opt_swap>::decode_utf32_block(data, data_length, 0);
1497
1498 // allocate buffer of suitable length
1499 char_t* buffer = static_cast<char_t*>(xml_memory::allocate((length + 1) * sizeof(char_t)));
1500 if (!buffer) return false;
1501
1502 // second pass: convert utf32 input to utf8
1503 uint8_t* obegin = reinterpret_cast<uint8_t*>(buffer);
1504 uint8_t* oend = utf_decoder<utf8_writer, opt_swap>::decode_utf32_block(data, data_length, obegin);
1505
1506 assert(oend == obegin + length);
1507 *oend = 0;
1508
1509 out_buffer = buffer;
1510 out_length = length + 1;
1511
1512 return true;
1513 }
static Traits::value_type decode_utf32_block(const uint32_t *data, size_t size, typename Traits::value_type result)
Definition pugixml.cpp:1060

References xml_memory_management_function_storage< T >::allocate, and utf_decoder< Traits, opt_swap >::decode_utf32_block().

Referenced by convert_buffer().

◆ convert_number_to_boolean()

PUGI__FN bool convert_number_to_boolean ( double  value)

Definition at line 6812 of file pugixml.cpp.

6813 {
6814 return (value != 0 && !is_nan(value));
6815 }
PUGI__FN bool is_nan(double value)
Definition pugixml.cpp:6767

References is_nan().

Referenced by xpath_ast_node::eval_boolean().

◆ convert_number_to_mantissa_exponent()

PUGI__FN void convert_number_to_mantissa_exponent ( double  value,
char *  buffer,
size_t  buffer_size,
char **  out_mantissa,
int *  out_exponent 
)

Definition at line 6840 of file pugixml.cpp.

6841 {
6842 // get a scientific notation value with IEEE DBL_DIG decimals
6843 sprintf(buffer, "%.*e", DBL_DIG, value);
6844 assert(strlen(buffer) < buffer_size);
6845 (void)!buffer_size;
6846
6847 // get the exponent (possibly negative)
6848 char* exponent_string = strchr(buffer, 'e');
6849 assert(exponent_string);
6850
6851 int exponent = atoi(exponent_string + 1);
6852
6853 // extract mantissa string: skip sign
6854 char* mantissa = buffer[0] == '-' ? buffer + 1 : buffer;
6855 assert(mantissa[0] != '0' && mantissa[1] == '.');
6856
6857 // divide mantissa by 10 to eliminate integer part
6858 mantissa[1] = mantissa[0];
6859 mantissa++;
6860 exponent++;
6861
6862 // remove extra mantissa digits and zero-terminate mantissa
6863 truncate_zeros(mantissa, exponent_string);
6864
6865 // fill results
6866 *out_mantissa = mantissa;
6867 *out_exponent = exponent;
6868 }
PUGI__FN void truncate_zeros(char *begin, char *end)
Definition pugixml.cpp:6817

References truncate_zeros().

Referenced by convert_number_to_string().

◆ convert_number_to_string()

PUGI__FN xpath_string convert_number_to_string ( double  value,
xpath_allocator alloc 
)

Definition at line 6871 of file pugixml.cpp.

6872 {
6873 // try special number conversion
6874 const char_t* special = convert_number_to_string_special(value);
6875 if (special) return xpath_string_const(special);
6876
6877 // get mantissa + exponent form
6878 char mantissa_buffer[32];
6879
6880 char* mantissa;
6881 int exponent;
6882 convert_number_to_mantissa_exponent(value, mantissa_buffer, sizeof(mantissa_buffer), &mantissa, &exponent);
6883
6884 // allocate a buffer of suitable length for the number
6885 size_t result_size = strlen(mantissa_buffer) + (exponent > 0 ? exponent : -exponent) + 4;
6886 char_t* result = static_cast<char_t*>(alloc->allocate(sizeof(char_t) * result_size));
6887 assert(result);
6888
6889 // make the number!
6890 char_t* s = result;
6891
6892 // sign
6893 if (value < 0) *s++ = '-';
6894
6895 // integer part
6896 if (exponent <= 0)
6897 {
6898 *s++ = '0';
6899 }
6900 else
6901 {
6902 while (exponent > 0)
6903 {
6904 assert(*mantissa == 0 || static_cast<unsigned int>(static_cast<unsigned int>(*mantissa) - '0') <= 9);
6905 *s++ = *mantissa ? *mantissa++ : '0';
6906 exponent--;
6907 }
6908 }
6909
6910 // fractional part
6911 if (*mantissa)
6912 {
6913 // decimal point
6914 *s++ = '.';
6915
6916 // extra zeroes from negative exponent
6917 while (exponent < 0)
6918 {
6919 *s++ = '0';
6920 exponent++;
6921 }
6922
6923 // extra mantissa digits
6924 while (*mantissa)
6925 {
6926 assert(static_cast<unsigned int>(*mantissa - '0') <= 9);
6927 *s++ = *mantissa++;
6928 }
6929 }
6930
6931 // zero-terminate
6932 assert(s < result + result_size);
6933 *s = 0;
6934
6935 return xpath_string(result, true);
6936 }
void * allocate(size_t size)
Definition pugixml.cpp:6250
PUGI__FN const char_t * convert_number_to_string_special(double value)
Definition pugixml.cpp:6780
PUGI__FN void convert_number_to_mantissa_exponent(double value, char *buffer, size_t buffer_size, char **out_mantissa, int *out_exponent)
Definition pugixml.cpp:6840
PUGI__FN xpath_string xpath_string_const(const char_t *str)
Definition pugixml.cpp:6527

References xpath_allocator::allocate(), convert_number_to_mantissa_exponent(), convert_number_to_string_special(), and xpath_string_const().

Referenced by xpath_ast_node::eval_string().

◆ convert_number_to_string_special()

PUGI__FN const char_t * convert_number_to_string_special ( double  value)

Definition at line 6780 of file pugixml.cpp.

6781 {
6782 #if defined(PUGI__MSVC_CRT_VERSION) || defined(__BORLANDC__)
6783 if (_finite(value)) return (value == 0) ? PUGIXML_TEXT("0") : 0;
6784 if (_isnan(value)) return PUGIXML_TEXT("NaN");
6785 return value > 0 ? PUGIXML_TEXT("Infinity") : PUGIXML_TEXT("-Infinity");
6786 #elif defined(fpclassify) && defined(FP_NAN) && defined(FP_INFINITE) && defined(FP_ZERO)
6787 switch (fpclassify(value))
6788 {
6789 case FP_NAN:
6790 return PUGIXML_TEXT("NaN");
6791
6792 case FP_INFINITE:
6793 return value > 0 ? PUGIXML_TEXT("Infinity") : PUGIXML_TEXT("-Infinity");
6794
6795 case FP_ZERO:
6796 return PUGIXML_TEXT("0");
6797
6798 default:
6799 return 0;
6800 }
6801 #else
6802 // fallback
6803 const volatile double v = value;
6804
6805 if (v == 0) return PUGIXML_TEXT("0");
6806 if (v != v) return PUGIXML_TEXT("NaN");
6807 if (v * 2 == v) return value > 0 ? PUGIXML_TEXT("Infinity") : PUGIXML_TEXT("-Infinity");
6808 return 0;
6809 #endif
6810 }

Referenced by convert_number_to_string().

◆ convert_path_heap()

PUGI__FN char * convert_path_heap ( const wchar_t *  str)

Definition at line 3959 of file pugixml.cpp.

3960 {
3961 assert(str);
3962
3963 // first pass: get length in utf8 characters
3964 size_t length = strlength_wide(str);
3965 size_t size = as_utf8_begin(str, length);
3966
3967 // allocate resulting string
3968 char* result = static_cast<char*>(xml_memory::allocate(size + 1));
3969 if (!result) return 0;
3970
3971 // second pass: convert to utf8
3972 as_utf8_end(result, size, str, length);
3973
3974 return result;
3975 }
PUGI__FN size_t strlength_wide(const wchar_t *s)
Definition pugixml.cpp:210

References xml_memory_management_function_storage< T >::allocate, as_utf8_begin(), as_utf8_end(), and strlength_wide().

Referenced by open_file_wide().

◆ convert_string_to_number()

PUGI__FN double convert_string_to_number ( const char_t *  string)

Definition at line 6968 of file pugixml.cpp.

6969 {
6970 // check string format
6971 if (!check_string_to_number_format(string)) return gen_nan();
6972
6973 // parse string
6974 #ifdef PUGIXML_WCHAR_MODE
6975 return wcstod(string, 0);
6976 #else
6977 return atof(string);
6978 #endif
6979 }
PUGI__FN double gen_nan()
Definition pugixml.cpp:6754
PUGI__FN bool check_string_to_number_format(const char_t *string)
Definition pugixml.cpp:6938

References check_string_to_number_format(), and gen_nan().

Referenced by xpath_ast_node::compare_eq(), xpath_ast_node::compare_rel(), convert_string_to_number_scratch(), and xpath_ast_node::eval_number().

◆ convert_string_to_number_scratch()

PUGI__FN bool convert_string_to_number_scratch ( char_t(&)  buffer[32],
const char_t *  begin,
const char_t *  end,
double *  out_result 
)

Definition at line 6981 of file pugixml.cpp.

6982 {
6983 size_t length = static_cast<size_t>(end - begin);
6984 char_t* scratch = buffer;
6985
6986 if (length >= sizeof(buffer) / sizeof(buffer[0]))
6987 {
6988 // need to make dummy on-heap copy
6989 scratch = static_cast<char_t*>(xml_memory::allocate((length + 1) * sizeof(char_t)));
6990 if (!scratch) return false;
6991 }
6992
6993 // copy string to zero-terminated buffer and perform conversion
6994 memcpy(scratch, begin, length * sizeof(char_t));
6995 scratch[length] = 0;
6996
6997 *out_result = convert_string_to_number(scratch);
6998
6999 // free dummy buffer
7000 if (scratch != buffer) xml_memory::deallocate(scratch);
7001
7002 return true;
7003 }
PUGI__FN double convert_string_to_number(const char_t *string)
Definition pugixml.cpp:6968
static deallocation_function deallocate
Definition pugixml.cpp:164

References xml_memory_management_function_storage< T >::allocate, convert_string_to_number(), and xml_memory_management_function_storage< T >::deallocate.

Referenced by xpath_parser::parse_primary_expression().

◆ convert_utf_endian_swap()

template<typename T >
PUGI__FN void convert_utf_endian_swap ( T *  result,
const T *  data,
size_t  length 
)

Definition at line 1111 of file pugixml.cpp.

1112 {
1113 for (size_t i = 0; i < length; ++i) result[i] = endian_swap(data[i]);
1114 }
PUGI__NS_END PUGI__NS_BEGIN uint16_t endian_swap(uint16_t value)
Definition pugixml.cpp:752

References endian_swap().

Referenced by convert_buffer_output().

◆ copy_backwards()

template<typename I >
void copy_backwards ( begin,
end,
target 
)

Definition at line 6037 of file pugixml.cpp.

6038 {
6039 while (begin != end) *--target = *--end;
6040 }

Referenced by insertion_sort().

◆ default_allocate()

PUGI__NS_BEGIN PUGI__FN void * default_allocate ( size_t  size)

Definition at line 150 of file pugixml.cpp.

151 {
152 return malloc(size);
153 }

◆ default_deallocate()

PUGI__FN void default_deallocate ( void *  ptr)

Definition at line 155 of file pugixml.cpp.

156 {
157 free(ptr);
158 }

◆ delete_xpath_variable() [1/2]

template<typename T >
PUGI__FN void delete_xpath_variable ( T *  var)

Definition at line 7244 of file pugixml.cpp.

7245 {
7246 var->~T();
7248 }

References xml_memory_management_function_storage< T >::deallocate.

Referenced by delete_xpath_variable().

◆ delete_xpath_variable() [2/2]

PUGI__FN void delete_xpath_variable ( xpath_value_type  type,
xpath_variable *  var 
)

Definition at line 7250 of file pugixml.cpp.

7251 {
7252 switch (type)
7253 {
7254 case xpath_type_node_set:
7256 break;
7257
7258 case xpath_type_number:
7259 delete_xpath_variable(static_cast<xpath_variable_number*>(var));
7260 break;
7261
7262 case xpath_type_string:
7263 delete_xpath_variable(static_cast<xpath_variable_string*>(var));
7264 break;
7265
7266 case xpath_type_boolean:
7268 break;
7269
7270 default:
7271 assert(!"Invalid variable type");
7272 }
7273 }
PUGI__FN void delete_xpath_variable(T *var)
Definition pugixml.cpp:7244

References delete_xpath_variable().

◆ destroy_attribute()

void destroy_attribute ( xml_attribute_struct *  a,
xml_allocator alloc 
)
inline

Definition at line 574 of file pugixml.cpp.

575 {
576 uintptr_t header = a->header;
577
578 if (header & impl::xml_memory_page_name_allocated_mask) alloc.deallocate_string(a->name);
579 if (header & impl::xml_memory_page_value_allocated_mask) alloc.deallocate_string(a->value);
580
581 alloc.deallocate_memory(a, sizeof(xml_attribute_struct), reinterpret_cast<xml_memory_page*>(header & xml_memory_page_pointer_mask));
582 }
static const uintptr_t xml_memory_page_pointer_mask
Definition pugixml.cpp:270
_W64 unsigned int uintptr_t
void deallocate_memory(void *ptr, size_t size, xml_memory_page *page)
Definition pugixml.cpp:361
void deallocate_string(char_t *string)
Definition pugixml.cpp:424

References xml_allocator::deallocate_memory(), xml_allocator::deallocate_string(), and xml_memory_page_pointer_mask.

Referenced by destroy_node().

◆ destroy_node()

void destroy_node ( xml_node_struct *  n,
xml_allocator alloc 
)
inline

Definition at line 584 of file pugixml.cpp.

585 {
586 uintptr_t header = n->header;
587
588 if (header & impl::xml_memory_page_name_allocated_mask) alloc.deallocate_string(n->name);
589 if (header & impl::xml_memory_page_value_allocated_mask) alloc.deallocate_string(n->value);
590
591 for (xml_attribute_struct* attr = n->first_attribute; attr; )
592 {
593 xml_attribute_struct* next = attr->next_attribute;
594
595 destroy_attribute(attr, alloc);
596
597 attr = next;
598 }
599
600 for (xml_node_struct* child = n->first_child; child; )
601 {
602 xml_node_struct* next = child->next_sibling;
603
604 destroy_node(child, alloc);
605
606 child = next;
607 }
608
609 alloc.deallocate_memory(n, sizeof(xml_node_struct), reinterpret_cast<xml_memory_page*>(header & xml_memory_page_pointer_mask));
610 }
void destroy_node(xml_node_struct *n, xml_allocator &alloc)
Definition pugixml.cpp:584
void destroy_attribute(xml_attribute_struct *a, xml_allocator &alloc)
Definition pugixml.cpp:574

References xml_allocator::deallocate_memory(), xml_allocator::deallocate_string(), destroy_attribute(), destroy_node(), and xml_memory_page_pointer_mask.

Referenced by destroy_node().

◆ document_order()

PUGI__FN const void * document_order ( const xpath_node &  xnode)

Definition at line 6667 of file pugixml.cpp.

6668 {
6669 xml_node_struct* node = xnode.node().internal_object();
6670
6671 if (node)
6672 {
6673 if (node->name && (node->header & xml_memory_page_name_allocated_mask) == 0) return node->name;
6674 if (node->value && (node->header & xml_memory_page_value_allocated_mask) == 0) return node->value;
6675 return 0;
6676 }
6677
6678 xml_attribute_struct* attr = xnode.attribute().internal_object();
6679
6680 if (attr)
6681 {
6682 if ((attr->header & xml_memory_page_name_allocated_mask) == 0) return attr->name;
6683 if ((attr->header & xml_memory_page_value_allocated_mask) == 0) return attr->value;
6684 return 0;
6685 }
6686
6687 return 0;
6688 }
static const uintptr_t xml_memory_page_name_allocated_mask
Definition pugixml.cpp:271
static const uintptr_t xml_memory_page_value_allocated_mask
Definition pugixml.cpp:272

References xml_memory_page_name_allocated_mask, and xml_memory_page_value_allocated_mask.

Referenced by document_order_comparator::operator()().

◆ endian_swap() [1/2]

PUGI__NS_END PUGI__NS_BEGIN uint16_t endian_swap ( uint16_t  value)
inline

Definition at line 752 of file pugixml.cpp.

753 {
754 return static_cast<uint16_t>(((value & 0xff) << 8) | (value >> 8));
755 }

Referenced by convert_utf_endian_swap(), utf_decoder< Traits, opt_swap >::decode_utf16_block(), and utf_decoder< Traits, opt_swap >::decode_utf32_block().

◆ endian_swap() [2/2]

uint32_t endian_swap ( uint32_t  value)
inline

Definition at line 757 of file pugixml.cpp.

758 {
759 return ((value & 0xff) << 24) | ((value & 0xff00) << 8) | ((value & 0xff0000) >> 8) | (value >> 24);
760 }

◆ evaluate_string_impl()

PUGI__FN xpath_string evaluate_string_impl ( xpath_query_impl impl,
const xpath_node &  n,
xpath_stack_data sd 
)

Definition at line 10123 of file pugixml.cpp.

10124 {
10125 if (!impl) return xpath_string();
10126
10127 #ifdef PUGIXML_NO_EXCEPTIONS
10128 if (setjmp(sd.error_handler)) return xpath_string();
10129 #endif
10130
10131 xpath_context c(n, 1, 1);
10132
10133 return impl->root->eval_string(c, sd.stack);
10134 }
xpath_string eval_string(const xpath_context &c, const xpath_stack &stack)
Definition pugixml.cpp:8876
xpath_ast_node * root
xpath_stack stack
Definition pugixml.cpp:6373

References xpath_ast_node::eval_string(), xpath_query_impl::root, and xpath_stack_data::stack.

◆ find_char()

PUGI__FN const char_t * find_char ( const char_t *  s,
char_t  c 
)

Definition at line 6545 of file pugixml.cpp.

6546 {
6547 #ifdef PUGIXML_WCHAR_MODE
6548 return wcschr(s, c);
6549 #else
6550 return strchr(s, c);
6551 #endif
6552 }

Referenced by local_name(), namespace_uri_predicate::namespace_uri_predicate(), and translate().

◆ find_substring()

PUGI__FN const char_t * find_substring ( const char_t *  s,
const char_t *  p 
)

Definition at line 6554 of file pugixml.cpp.

6555 {
6556 #ifdef PUGIXML_WCHAR_MODE
6557 // MSVC6 wcsstr bug workaround (if s is empty it always returns 0)
6558 return (*p == 0) ? s : wcsstr(s, p);
6559 #else
6560 return strstr(s, p);
6561 #endif
6562 }

Referenced by xpath_ast_node::eval_boolean(), and xpath_ast_node::eval_string().

◆ gen_nan()

PUGI__FN double gen_nan ( )

Definition at line 6754 of file pugixml.cpp.

6755 {
6756 #if defined(__STDC_IEC_559__) || ((FLT_RADIX - 0 == 2) && (FLT_MAX_EXP - 0 == 128) && (FLT_MANT_DIG - 0 == 24))
6757 union { float f; uint32_t i; } u[sizeof(float) == sizeof(uint32_t) ? 1 : -1];
6758 u[0].i = 0x7fc00000;
6759 return u[0].f;
6760 #else
6761 // fallback
6762 const volatile double zero = 0.0;
6763 return zero / zero;
6764 #endif
6765 }

Referenced by convert_string_to_number().

◆ get_allocator()

xml_allocator & get_allocator ( const xml_node_struct *  node)
inline

Definition at line 548 of file pugixml.cpp.

549 {
550 assert(node);
551
552 return *reinterpret_cast<xml_memory_page*>(node->header & xml_memory_page_pointer_mask)->allocator;
553 }

References xml_memory_page_pointer_mask.

◆ get_buffer_encoding()

PUGI__FN xml_encoding get_buffer_encoding ( xml_encoding  encoding,
const void *  contents,
size_t  size 
)

Definition at line 1239 of file pugixml.cpp.

1240 {
1241 // replace wchar encoding with utf implementation
1242 if (encoding == encoding_wchar) return get_wchar_encoding();
1243
1244 // replace utf16 encoding with utf16 with specific endianness
1245 if (encoding == encoding_utf16) return is_little_endian() ? encoding_utf16_le : encoding_utf16_be;
1246
1247 // replace utf32 encoding with utf32 with specific endianness
1248 if (encoding == encoding_utf32) return is_little_endian() ? encoding_utf32_le : encoding_utf32_be;
1249
1250 // only do autodetection if no explicit encoding is requested
1251 if (encoding != encoding_auto) return encoding;
1252
1253 // skip encoding autodetection if input buffer is too small
1254 if (size < 4) return encoding_utf8;
1255
1256 // try to guess encoding (based on XML specification, Appendix F.1)
1257 const uint8_t* data = static_cast<const uint8_t*>(contents);
1258
1259 PUGI__DMC_VOLATILE uint8_t d0 = data[0], d1 = data[1], d2 = data[2], d3 = data[3];
1260
1261 return guess_buffer_encoding(d0, d1, d2, d3);
1262 }
PUGI__FN xml_encoding get_wchar_encoding()
Definition pugixml.cpp:1205
#define PUGI__DMC_VOLATILE
Definition pugixml.cpp:101
PUGI__FN xml_encoding guess_buffer_encoding(uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3)
Definition pugixml.cpp:1215

References get_wchar_encoding(), guess_buffer_encoding(), is_little_endian(), and PUGI__DMC_VOLATILE.

Referenced by load_file_impl(), and load_stream_impl().

◆ get_file_size()

PUGI__FN xml_parse_status get_file_size ( FILE *  file,
size_t &  out_result 
)

Definition at line 3701 of file pugixml.cpp.

3702 {
3703 #if defined(PUGI__MSVC_CRT_VERSION) && PUGI__MSVC_CRT_VERSION >= 1400 && !defined(_WIN32_WCE)
3704 // there are 64-bit versions of fseek/ftell, let's use them
3705 typedef __int64 length_type;
3706
3707 _fseeki64(file, 0, SEEK_END);
3708 length_type length = _ftelli64(file);
3709 _fseeki64(file, 0, SEEK_SET);
3710 #elif defined(__MINGW32__) && !defined(__NO_MINGW_LFS) && !defined(__STRICT_ANSI__)
3711 // there are 64-bit versions of fseek/ftell, let's use them
3712 typedef off64_t length_type;
3713
3714 fseeko64(file, 0, SEEK_END);
3715 length_type length = ftello64(file);
3716 fseeko64(file, 0, SEEK_SET);
3717 #else
3718 // if this is a 32-bit OS, long is enough; if this is a unix system, long is 64-bit, which is enough; otherwise we can't do anything anyway.
3719 typedef long length_type;
3720
3721 fseek(file, 0, SEEK_END);
3722 length_type length = ftell(file);
3723 fseek(file, 0, SEEK_SET);
3724 #endif
3725
3726 // check for I/O errors
3727 if (length < 0) return status_io_error;
3728
3729 // check for overflow
3730 size_t result = static_cast<size_t>(length);
3731
3732 if (static_cast<length_type>(result) != length) return status_out_of_memory;
3733
3734 // finalize
3735 out_result = result;
3736
3737 return status_ok;
3738 }

Referenced by load_file_impl().

◆ get_integer_base()

PUGI__FN int get_integer_base ( const char_t *  value)

Definition at line 3524 of file pugixml.cpp.

3525 {
3526 const char_t* s = value;
3527
3528 while (PUGI__IS_CHARTYPE(*s, ct_space))
3529 s++;
3530
3531 if (*s == '-')
3532 s++;
3533
3534 return (s[0] == '0' && (s[1] == 'x' || s[1] == 'X')) ? 16 : 10;
3535 }

References ct_space, and PUGI__IS_CHARTYPE.

Referenced by get_value_int(), and get_value_uint().

◆ get_latin1_7bit_prefix_length()

PUGI__FN size_t get_latin1_7bit_prefix_length ( const uint8_t data,
size_t  size 
)

Definition at line 1515 of file pugixml.cpp.

1516 {
1517 for (size_t i = 0; i < size; ++i)
1518 if (data[i] > 127)
1519 return i;
1520
1521 return size;
1522 }

Referenced by convert_buffer_latin1().

◆ get_mutable_buffer()

PUGI__FN bool get_mutable_buffer ( char_t *&  out_buffer,
size_t &  out_length,
const void *  contents,
size_t  size,
bool  is_mutable 
)

Definition at line 1264 of file pugixml.cpp.

1265 {
1266 size_t length = size / sizeof(char_t);
1267
1268 if (is_mutable)
1269 {
1270 out_buffer = static_cast<char_t*>(const_cast<void*>(contents));
1271 out_length = length;
1272 }
1273 else
1274 {
1275 char_t* buffer = static_cast<char_t*>(xml_memory::allocate((length + 1) * sizeof(char_t)));
1276 if (!buffer) return false;
1277
1278 memcpy(buffer, contents, length * sizeof(char_t));
1279 buffer[length] = 0;
1280
1281 out_buffer = buffer;
1282 out_length = length + 1;
1283 }
1284
1285 return true;
1286 }

References xml_memory_management_function_storage< T >::allocate.

Referenced by convert_buffer(), and convert_buffer_latin1().

◆ get_strconv_attribute()

PUGI__FN strconv_attribute_t get_strconv_attribute ( unsigned int  optmask)

Definition at line 2189 of file pugixml.cpp.

2190 {
2191 PUGI__STATIC_ASSERT(parse_escapes == 0x10 && parse_eol == 0x20 && parse_wconv_attribute == 0x40 && parse_wnorm_attribute == 0x80);
2192
2193 switch ((optmask >> 4) & 15) // get bitmask for flags (wconv wnorm eol escapes)
2194 {
2211 default: assert(false); return 0; // should not get here
2212 }
2213 }
#define PUGI__STATIC_ASSERT(cond)
Definition pugixml.cpp:95

References PUGI__STATIC_ASSERT.

Referenced by xml_parser::parse_tree().

◆ get_strconv_pcdata()

PUGI__FN strconv_pcdata_t get_strconv_pcdata ( unsigned int  optmask)

Definition at line 2020 of file pugixml.cpp.

2021 {
2022 PUGI__STATIC_ASSERT(parse_escapes == 0x10 && parse_eol == 0x20 && parse_trim_pcdata == 0x0800);
2023
2024 switch (((optmask >> 4) & 3) | ((optmask >> 9) & 4)) // get bitmask for flags (eol escapes trim)
2025 {
2034 default: assert(false); return 0; // should not get here
2035 }
2036 }

References PUGI__STATIC_ASSERT.

Referenced by xml_parser::parse_tree().

◆ get_valid_length()

PUGI__FN size_t get_valid_length ( const char_t *  data,
size_t  length 
)

Definition at line 2961 of file pugixml.cpp.

2962 {
2963 assert(length > 4);
2964
2965 for (size_t i = 1; i <= 4; ++i)
2966 {
2967 uint8_t ch = static_cast<uint8_t>(data[length - i]);
2968
2969 // either a standalone character or a leading one
2970 if ((ch & 0xc0) != 0x80) return length - i;
2971 }
2972
2973 // there are four non-leading characters at the end, sequence tail is broken so might as well process the whole chunk
2974 return length;
2975 }

Referenced by xml_buffered_writer::write().

◆ get_value_bool()

PUGI__FN bool get_value_bool ( const char_t *  value,
bool  def 
)

Definition at line 3585 of file pugixml.cpp.

3586 {
3587 if (!value) return def;
3588
3589 // only look at first char
3590 char_t first = *value;
3591
3592 // 1*, t* (true), T* (True), y* (yes), Y* (YES)
3593 return (first == '1' || first == 't' || first == 'T' || first == 'y' || first == 'Y');
3594 }

◆ get_value_double()

PUGI__FN double get_value_double ( const char_t *  value,
double  def 
)

Definition at line 3563 of file pugixml.cpp.

3564 {
3565 if (!value) return def;
3566
3567 #ifdef PUGIXML_WCHAR_MODE
3568 return wcstod(value, 0);
3569 #else
3570 return strtod(value, 0);
3571 #endif
3572 }

◆ get_value_float()

PUGI__FN float get_value_float ( const char_t *  value,
float  def 
)

Definition at line 3574 of file pugixml.cpp.

3575 {
3576 if (!value) return def;
3577
3578 #ifdef PUGIXML_WCHAR_MODE
3579 return static_cast<float>(wcstod(value, 0));
3580 #else
3581 return static_cast<float>(strtod(value, 0));
3582 #endif
3583 }

◆ get_value_int()

PUGI__FN int get_value_int ( const char_t *  value,
int  def 
)

Definition at line 3537 of file pugixml.cpp.

3538 {
3539 if (!value) return def;
3540
3541 int base = get_integer_base(value);
3542
3543 #ifdef PUGIXML_WCHAR_MODE
3544 return static_cast<int>(wcstol(value, 0, base));
3545 #else
3546 return static_cast<int>(strtol(value, 0, base));
3547 #endif
3548 }
PUGI__FN int get_integer_base(const char_t *value)
Definition pugixml.cpp:3524

References get_integer_base().

◆ get_value_uint()

PUGI__FN unsigned int get_value_uint ( const char_t *  value,
unsigned int  def 
)

Definition at line 3550 of file pugixml.cpp.

3551 {
3552 if (!value) return def;
3553
3554 int base = get_integer_base(value);
3555
3556 #ifdef PUGIXML_WCHAR_MODE
3557 return static_cast<unsigned int>(wcstoul(value, 0, base));
3558 #else
3559 return static_cast<unsigned int>(strtoul(value, 0, base));
3560 #endif
3561 }

References get_integer_base().

◆ get_variable_scratch()

PUGI__FN xpath_variable * get_variable_scratch ( char_t(&)  buffer[32],
xpath_variable_set *  set,
const char_t *  begin,
const char_t *  end 
)

Definition at line 7275 of file pugixml.cpp.

7276 {
7277 size_t length = static_cast<size_t>(end - begin);
7278 char_t* scratch = buffer;
7279
7280 if (length >= sizeof(buffer) / sizeof(buffer[0]))
7281 {
7282 // need to make dummy on-heap copy
7283 scratch = static_cast<char_t*>(xml_memory::allocate((length + 1) * sizeof(char_t)));
7284 if (!scratch) return 0;
7285 }
7286
7287 // copy string to zero-terminated buffer and perform lookup
7288 memcpy(scratch, begin, length * sizeof(char_t));
7289 scratch[length] = 0;
7290
7291 xpath_variable* result = set->get(scratch);
7292
7293 // free dummy buffer
7294 if (scratch != buffer) xml_memory::deallocate(scratch);
7295
7296 return result;
7297 }

References xml_memory_management_function_storage< T >::allocate, and xml_memory_management_function_storage< T >::deallocate.

Referenced by xpath_parser::parse_primary_expression().

◆ get_wchar_encoding()

PUGI__FN xml_encoding get_wchar_encoding ( )

Definition at line 1205 of file pugixml.cpp.

1206 {
1207 PUGI__STATIC_ASSERT(sizeof(wchar_t) == 2 || sizeof(wchar_t) == 4);
1208
1209 if (sizeof(wchar_t) == 2)
1210 return is_little_endian() ? encoding_utf16_le : encoding_utf16_be;
1211 else
1212 return is_little_endian() ? encoding_utf32_le : encoding_utf32_be;
1213 }

References is_little_endian(), and PUGI__STATIC_ASSERT.

Referenced by get_buffer_encoding(), get_write_encoding(), get_write_native_encoding(), and zero_terminate_buffer().

◆ get_write_encoding()

PUGI__FN xml_encoding get_write_encoding ( xml_encoding  encoding)

Definition at line 2870 of file pugixml.cpp.

2871 {
2872 // replace wchar encoding with utf implementation
2873 if (encoding == encoding_wchar) return get_wchar_encoding();
2874
2875 // replace utf16 encoding with utf16 with specific endianness
2876 if (encoding == encoding_utf16) return is_little_endian() ? encoding_utf16_le : encoding_utf16_be;
2877
2878 // replace utf32 encoding with utf32 with specific endianness
2879 if (encoding == encoding_utf32) return is_little_endian() ? encoding_utf32_le : encoding_utf32_be;
2880
2881 // only do autodetection if no explicit encoding is requested
2882 if (encoding != encoding_auto) return encoding;
2883
2884 // assume utf8 encoding
2885 return encoding_utf8;
2886 }

References get_wchar_encoding(), and is_little_endian().

◆ get_write_native_encoding()

PUGI__FN xml_encoding get_write_native_encoding ( )

Definition at line 2861 of file pugixml.cpp.

2862 {
2863 #ifdef PUGIXML_WCHAR_MODE
2864 return get_wchar_encoding();
2865 #else
2866 return encoding_utf8;
2867 #endif
2868 }

References get_wchar_encoding().

Referenced by xml_buffered_writer::flush(), and xml_buffered_writer::write().

◆ guess_buffer_encoding()

PUGI__FN xml_encoding guess_buffer_encoding ( uint8_t  d0,
uint8_t  d1,
uint8_t  d2,
uint8_t  d3 
)

Definition at line 1215 of file pugixml.cpp.

1216 {
1217 // look for BOM in first few bytes
1218 if (d0 == 0 && d1 == 0 && d2 == 0xfe && d3 == 0xff) return encoding_utf32_be;
1219 if (d0 == 0xff && d1 == 0xfe && d2 == 0 && d3 == 0) return encoding_utf32_le;
1220 if (d0 == 0xfe && d1 == 0xff) return encoding_utf16_be;
1221 if (d0 == 0xff && d1 == 0xfe) return encoding_utf16_le;
1222 if (d0 == 0xef && d1 == 0xbb && d2 == 0xbf) return encoding_utf8;
1223
1224 // look for <, <? or <?xm in various encodings
1225 if (d0 == 0 && d1 == 0 && d2 == 0 && d3 == 0x3c) return encoding_utf32_be;
1226 if (d0 == 0x3c && d1 == 0 && d2 == 0 && d3 == 0) return encoding_utf32_le;
1227 if (d0 == 0 && d1 == 0x3c && d2 == 0 && d3 == 0x3f) return encoding_utf16_be;
1228 if (d0 == 0x3c && d1 == 0 && d2 == 0x3f && d3 == 0) return encoding_utf16_le;
1229 if (d0 == 0x3c && d1 == 0x3f && d2 == 0x78 && d3 == 0x6d) return encoding_utf8;
1230
1231 // look for utf16 < followed by node name (this may fail, but is better than utf8 since it's zero terminated so early)
1232 if (d0 == 0 && d1 == 0x3c) return encoding_utf16_be;
1233 if (d0 == 0x3c && d1 == 0) return encoding_utf16_le;
1234
1235 // no known BOM detected, assume utf8
1236 return encoding_utf8;
1237 }

Referenced by get_buffer_encoding().

◆ has_declaration()

bool has_declaration ( const xml_node &  node)
inline

Definition at line 3417 of file pugixml.cpp.

3418 {
3419 for (xml_node child = node.first_child(); child; child = child.next_sibling())
3420 {
3421 xml_node_type type = child.type();
3422
3423 if (type == node_declaration) return true;
3424 if (type == node_element) return false;
3425 }
3426
3427 return false;
3428 }

◆ hash_string()

PUGI__FN unsigned int hash_string ( const char_t *  str)

Definition at line 7188 of file pugixml.cpp.

7189 {
7190 // Jenkins one-at-a-time hash (http://en.wikipedia.org/wiki/Jenkins_hash_function#one-at-a-time)
7191 unsigned int result = 0;
7192
7193 while (*str)
7194 {
7195 result += static_cast<unsigned int>(*str++);
7196 result += result << 10;
7197 result ^= result >> 6;
7198 }
7199
7200 result += result << 3;
7201 result ^= result >> 11;
7202 result += result << 15;
7203
7204 return result;
7205 }

◆ insert_node_after()

void insert_node_after ( xml_node_struct *  child,
xml_node_struct *  node 
)
inline

Definition at line 653 of file pugixml.cpp.

654 {
655 xml_node_struct* parent = node->parent;
656
657 child->parent = parent;
658
659 if (node->next_sibling)
660 node->next_sibling->prev_sibling_c = child;
661 else
662 parent->first_child->prev_sibling_c = child;
663
664 child->next_sibling = node->next_sibling;
665 child->prev_sibling_c = node;
666
667 node->next_sibling = child;
668 }

◆ insert_node_before()

void insert_node_before ( xml_node_struct *  child,
xml_node_struct *  node 
)
inline

Definition at line 670 of file pugixml.cpp.

671 {
672 xml_node_struct* parent = node->parent;
673
674 child->parent = parent;
675
676 if (node->prev_sibling_c->next_sibling)
677 node->prev_sibling_c->next_sibling = child;
678 else
679 parent->first_child = child;
680
681 child->prev_sibling_c = node->prev_sibling_c;
682 child->next_sibling = node;
683
684 node->prev_sibling_c = child;
685 }

◆ insertion_sort()

template<typename I , typename Pred , typename T >
void insertion_sort ( begin,
end,
const Pred &  pred,
T *   
)

Definition at line 6042 of file pugixml.cpp.

6043 {
6044 assert(begin != end);
6045
6046 for (I it = begin + 1; it != end; ++it)
6047 {
6048 T val = *it;
6049
6050 if (pred(val, *begin))
6051 {
6052 // move to front
6053 copy_backwards(begin, it, it + 1);
6054 *begin = val;
6055 }
6056 else
6057 {
6058 I hole = it;
6059
6060 // move hole backwards
6061 while (pred(val, *(hole - 1)))
6062 {
6063 *hole = *(hole - 1);
6064 hole--;
6065 }
6066
6067 // fill hole with element
6068 *hole = val;
6069 }
6070 }
6071 }
void copy_backwards(I begin, I end, I target)
Definition pugixml.cpp:6037

References copy_backwards().

Referenced by sort().

◆ is_little_endian()

PUGI__FN bool is_little_endian ( )

Definition at line 1198 of file pugixml.cpp.

1199 {
1200 unsigned int ui = 1;
1201
1202 return *reinterpret_cast<unsigned char*>(&ui) == 1;
1203 }

Referenced by convert_buffer(), convert_buffer_output(), get_buffer_encoding(), get_wchar_encoding(), and get_write_encoding().

◆ is_nan()

PUGI__FN bool is_nan ( double  value)

Definition at line 6767 of file pugixml.cpp.

6768 {
6769 #if defined(PUGI__MSVC_CRT_VERSION) || defined(__BORLANDC__)
6770 return !!_isnan(value);
6771 #elif defined(fpclassify) && defined(FP_NAN)
6772 return fpclassify(value) == FP_NAN;
6773 #else
6774 // fallback
6775 const volatile double v = value;
6776 return v != v;
6777 #endif
6778 }

Referenced by convert_number_to_boolean(), and xpath_ast_node::eval_string().

◆ is_text_node()

bool is_text_node ( xml_node_struct *  node)
inline

Definition at line 3516 of file pugixml.cpp.

3517 {
3518 xml_node_type type = static_cast<xml_node_type>((node->header & impl::xml_memory_page_type_mask) + 1);
3519
3520 return type == node_pcdata || type == node_cdata;
3521 }

◆ load_buffer_impl()

PUGI__FN xml_parse_result load_buffer_impl ( xml_document_struct doc,
xml_node_struct *  root,
void *  contents,
size_t  size,
unsigned int  options,
xml_encoding  encoding,
bool  is_mutable,
bool  own,
char_t **  out_buffer 
)

Definition at line 4011 of file pugixml.cpp.

4012 {
4013 // check input buffer
4014 assert(contents || size == 0);
4015
4016 // get actual encoding
4017 xml_encoding buffer_encoding = impl::get_buffer_encoding(encoding, contents, size);
4018
4019 // get private buffer
4020 char_t* buffer = 0;
4021 size_t length = 0;
4022
4023 if (!impl::convert_buffer(buffer, length, buffer_encoding, contents, size, is_mutable)) return impl::make_parse_result(status_out_of_memory);
4024
4025 // delete original buffer if we performed a conversion
4026 if (own && buffer != contents && contents) impl::xml_memory::deallocate(contents);
4027
4028 // store buffer for offset_debug
4029 doc->buffer = buffer;
4030
4031 // parse
4032 xml_parse_result res = impl::xml_parser::parse(buffer, length, doc, root, options);
4033
4034 // remember encoding
4035 res.encoding = buffer_encoding;
4036
4037 // grab onto buffer if it's our buffer, user is responsible for deallocating contents himself
4038 if (own || buffer != contents) *out_buffer = buffer;
4039
4040 return res;
4041 }
const char_t * buffer
Definition pugixml.cpp:543

References xml_document_struct::buffer.

◆ load_file_impl()

PUGI__FN xml_parse_result load_file_impl ( xml_document &  doc,
FILE *  file,
unsigned int  options,
xml_encoding  encoding 
)

Definition at line 3764 of file pugixml.cpp.

3765 {
3766 if (!file) return make_parse_result(status_file_not_found);
3767
3768 // get file size (can result in I/O errors)
3769 size_t size = 0;
3770 xml_parse_status size_status = get_file_size(file, size);
3771
3772 if (size_status != status_ok)
3773 {
3774 fclose(file);
3775 return make_parse_result(size_status);
3776 }
3777
3778 size_t max_suffix_size = sizeof(char_t);
3779
3780 // allocate buffer for the whole file
3781 char* contents = static_cast<char*>(xml_memory::allocate(size + max_suffix_size));
3782
3783 if (!contents)
3784 {
3785 fclose(file);
3786 return make_parse_result(status_out_of_memory);
3787 }
3788
3789 // read file in memory
3790 size_t read_size = fread(contents, 1, size, file);
3791 fclose(file);
3792
3793 if (read_size != size)
3794 {
3795 xml_memory::deallocate(contents);
3796 return make_parse_result(status_io_error);
3797 }
3798
3799 xml_encoding real_encoding = get_buffer_encoding(encoding, contents, size);
3800
3801 return doc.load_buffer_inplace_own(contents, zero_terminate_buffer(contents, size, real_encoding), options, real_encoding);
3802 }
PUGI__FN size_t zero_terminate_buffer(void *buffer, size_t size, xml_encoding encoding)
Definition pugixml.cpp:3740
PUGI__FN xml_parse_status get_file_size(FILE *file, size_t &out_result)
Definition pugixml.cpp:3701
xml_parse_result make_parse_result(xml_parse_status status, ptrdiff_t offset=0)
Definition pugixml.cpp:2215
PUGI__FN xml_encoding get_buffer_encoding(xml_encoding encoding, const void *contents, size_t size)
Definition pugixml.cpp:1239

References xml_memory_management_function_storage< T >::allocate, xml_memory_management_function_storage< T >::deallocate, get_buffer_encoding(), get_file_size(), make_parse_result(), and zero_terminate_buffer().

◆ load_stream_data_noseek()

template<typename T >
PUGI__FN xml_parse_status load_stream_data_noseek ( std::basic_istream< T > &  stream,
void **  out_buffer,
size_t *  out_size 
)

Definition at line 3837 of file pugixml.cpp.

3838 {
3840
3841 // read file to a chunk list
3842 size_t total = 0;
3843 xml_stream_chunk<T>* last = 0;
3844
3845 while (!stream.eof())
3846 {
3847 // allocate new chunk
3849 if (!chunk) return status_out_of_memory;
3850
3851 // append chunk to list
3852 if (last) last = last->next = chunk;
3853 else chunks.data = last = chunk;
3854
3855 // read data to chunk
3856 stream.read(chunk->data, static_cast<std::streamsize>(sizeof(chunk->data) / sizeof(T)));
3857 chunk->size = static_cast<size_t>(stream.gcount()) * sizeof(T);
3858
3859 // read may set failbit | eofbit in case gcount() is less than read length, so check for other I/O errors
3860 if (stream.bad() || (!stream.eof() && stream.fail())) return status_io_error;
3861
3862 // guard against huge files (chunk size is small enough to make this overflow check work)
3863 if (total + chunk->size < total) return status_out_of_memory;
3864 total += chunk->size;
3865 }
3866
3867 size_t max_suffix_size = sizeof(char_t);
3868
3869 // copy chunk list to a contiguous buffer
3870 char* buffer = static_cast<char*>(xml_memory::allocate(total + max_suffix_size));
3871 if (!buffer) return status_out_of_memory;
3872
3873 char* write = buffer;
3874
3875 for (xml_stream_chunk<T>* chunk = static_cast<xml_stream_chunk<T>*>(chunks.data); chunk; chunk = chunk->next)
3876 {
3877 assert(write + chunk->size <= buffer + total);
3878 memcpy(write, chunk->data, chunk->size);
3879 write += chunk->size;
3880 }
3881
3882 assert(write == buffer + total);
3883
3884 // return buffer
3885 *out_buffer = buffer;
3886 *out_size = total;
3887
3888 return status_ok;
3889 }
static xml_stream_chunk * create()
Definition pugixml.cpp:3807
T data[xml_memory_page_size/sizeof(T)]
Definition pugixml.cpp:3834
xml_stream_chunk * next
Definition pugixml.cpp:3831

References xml_memory_management_function_storage< T >::allocate, xml_stream_chunk< T >::create(), buffer_holder::data, xml_stream_chunk< T >::data, xml_stream_chunk< T >::next, and xml_stream_chunk< T >::size.

Referenced by load_stream_impl().

◆ load_stream_data_seek()

template<typename T >
PUGI__FN xml_parse_status load_stream_data_seek ( std::basic_istream< T > &  stream,
void **  out_buffer,
size_t *  out_size 
)

Definition at line 3891 of file pugixml.cpp.

3892 {
3893 // get length of remaining data in stream
3894 typename std::basic_istream<T>::pos_type pos = stream.tellg();
3895 stream.seekg(0, std::ios::end);
3896 std::streamoff length = stream.tellg() - pos;
3897 stream.seekg(pos);
3898
3899 if (stream.fail() || pos < 0) return status_io_error;
3900
3901 // guard against huge files
3902 size_t read_length = static_cast<size_t>(length);
3903
3904 if (static_cast<std::streamsize>(read_length) != length || length < 0) return status_out_of_memory;
3905
3906 size_t max_suffix_size = sizeof(char_t);
3907
3908 // read stream data into memory (guard against stream exceptions with buffer holder)
3909 buffer_holder buffer(xml_memory::allocate(read_length * sizeof(T) + max_suffix_size), xml_memory::deallocate);
3910 if (!buffer.data) return status_out_of_memory;
3911
3912 stream.read(static_cast<T*>(buffer.data), static_cast<std::streamsize>(read_length));
3913
3914 // read may set failbit | eofbit in case gcount() is less than read_length (i.e. line ending conversion), so check for other I/O errors
3915 if (stream.bad() || (!stream.eof() && stream.fail())) return status_io_error;
3916
3917 // return buffer
3918 size_t actual_length = static_cast<size_t>(stream.gcount());
3919 assert(actual_length <= read_length);
3920
3921 *out_buffer = buffer.release();
3922 *out_size = actual_length * sizeof(T);
3923
3924 return status_ok;
3925 }

References xml_memory_management_function_storage< T >::allocate, buffer_holder::data, xml_memory_management_function_storage< T >::deallocate, and buffer_holder::release().

Referenced by load_stream_impl().

◆ load_stream_impl()

template<typename T >
PUGI__FN xml_parse_result load_stream_impl ( xml_document &  doc,
std::basic_istream< T > &  stream,
unsigned int  options,
xml_encoding  encoding 
)

Definition at line 3927 of file pugixml.cpp.

3928 {
3929 void* buffer = 0;
3930 size_t size = 0;
3931 xml_parse_status status = status_ok;
3932
3933 // if stream has an error bit set, bail out (otherwise tellg() can fail and we'll clear error bits)
3934 if (stream.fail()) return make_parse_result(status_io_error);
3935
3936 // load stream to memory (using seek-based implementation if possible, since it's faster and takes less memory)
3937 if (stream.tellg() < 0)
3938 {
3939 stream.clear(); // clear error flags that could be set by a failing tellg
3940 status = load_stream_data_noseek(stream, &buffer, &size);
3941 }
3942 else
3943 status = load_stream_data_seek(stream, &buffer, &size);
3944
3945 if (status != status_ok) return make_parse_result(status);
3946
3947 xml_encoding real_encoding = get_buffer_encoding(encoding, buffer, size);
3948
3949 return doc.load_buffer_inplace_own(buffer, zero_terminate_buffer(buffer, size, real_encoding), options, real_encoding);
3950 }
PUGI__FN xml_parse_status load_stream_data_seek(std::basic_istream< T > &stream, void **out_buffer, size_t *out_size)
Definition pugixml.cpp:3891
PUGI__FN xml_parse_status load_stream_data_noseek(std::basic_istream< T > &stream, void **out_buffer, size_t *out_size)
Definition pugixml.cpp:3837

References get_buffer_encoding(), load_stream_data_noseek(), load_stream_data_seek(), make_parse_result(), and zero_terminate_buffer().

◆ local_name()

PUGI__FN const char_t * local_name ( const xpath_node &  node)

Definition at line 7022 of file pugixml.cpp.

7023 {
7024 const char_t* name = qualified_name(node);
7025 const char_t* p = find_char(name, ':');
7026
7027 return p ? p + 1 : name;
7028 }
PUGI__FN const char_t * qualified_name(const xpath_node &node)
Definition pugixml.cpp:7017
PUGI__FN const char_t * find_char(const char_t *s, char_t c)
Definition pugixml.cpp:6545

References find_char(), and qualified_name().

Referenced by xpath_ast_node::eval_string().

◆ make_parse_result()

xml_parse_result make_parse_result ( xml_parse_status  status,
ptrdiff_t  offset = 0 
)
inline

Definition at line 2215 of file pugixml.cpp.

2216 {
2217 xml_parse_result result;
2218 result.status = status;
2219 result.offset = offset;
2220
2221 return result;
2222 }

Referenced by load_file_impl(), load_stream_impl(), and xml_parser::parse().

◆ median()

template<typename I , typename Pred >
void median ( first,
middle,
last,
const Pred &  pred 
)

Definition at line 6134 of file pugixml.cpp.

6135 {
6136 if (last - first <= 40)
6137 {
6138 // median of three for small chunks
6139 median3(first, middle, last, pred);
6140 }
6141 else
6142 {
6143 // median of nine
6144 size_t step = (last - first + 1) / 8;
6145
6146 median3(first, first + step, first + 2 * step, pred);
6147 median3(middle - step, middle, middle + step, pred);
6148 median3(last - 2 * step, last - step, last, pred);
6149 median3(first + step, middle, last - step, pred);
6150 }
6151 }
void median3(I first, I middle, I last, const Pred &pred)
Definition pugixml.cpp:6127

References median3().

Referenced by sort().

◆ median3()

template<typename I , typename Pred >
void median3 ( first,
middle,
last,
const Pred &  pred 
)

Definition at line 6127 of file pugixml.cpp.

6128 {
6129 if (pred(*middle, *first)) swap(*middle, *first);
6130 if (pred(*last, *middle)) swap(*last, *middle);
6131 if (pred(*middle, *first)) swap(*middle, *first);
6132 }
void swap(T &lhs, T &rhs)
Definition pugixml.cpp:5991

References swap().

Referenced by median().

◆ min_element()

template<typename I , typename Pred >
I min_element ( begin,
end,
const Pred &  pred 
)

Definition at line 5998 of file pugixml.cpp.

5999 {
6000 I result = begin;
6001
6002 for (I it = begin + 1; it != end; ++it)
6003 if (pred(*it, *result))
6004 result = it;
6005
6006 return result;
6007 }

Referenced by xpath_first().

◆ namespace_uri() [1/3]

PUGI__FN const char_t * namespace_uri ( const xml_attribute &  attr,
const xml_node &  parent 
)

Definition at line 7071 of file pugixml.cpp.

7072 {
7073 namespace_uri_predicate pred = attr.name();
7074
7075 // Default namespace does not apply to attributes
7076 if (!pred.prefix) return PUGIXML_TEXT("");
7077
7078 xml_node p = parent;
7079
7080 while (p)
7081 {
7082 xml_attribute a = p.find_attribute(pred);
7083
7084 if (a) return a.value();
7085
7086 p = p.parent();
7087 }
7088
7089 return PUGIXML_TEXT("");
7090 }
const char_t * prefix
Definition pugixml.cpp:7032

References namespace_uri_predicate::prefix.

◆ namespace_uri() [2/3]

PUGI__FN const char_t * namespace_uri ( const xml_node &  node)

Definition at line 7053 of file pugixml.cpp.

7054 {
7055 namespace_uri_predicate pred = node.name();
7056
7057 xml_node p = node;
7058
7059 while (p)
7060 {
7061 xml_attribute a = p.find_attribute(pred);
7062
7063 if (a) return a.value();
7064
7065 p = p.parent();
7066 }
7067
7068 return PUGIXML_TEXT("");
7069 }

Referenced by xpath_ast_node::eval_string(), and namespace_uri().

◆ namespace_uri() [3/3]

PUGI__FN const char_t * namespace_uri ( const xpath_node &  node)

Definition at line 7092 of file pugixml.cpp.

7093 {
7094 return node.attribute() ? namespace_uri(node.attribute(), node.parent()) : namespace_uri(node.node());
7095 }
PUGI__FN const char_t * namespace_uri(const xml_node &node)
Definition pugixml.cpp:7053

References namespace_uri().

◆ new_xpath_variable() [1/2]

template<typename T >
PUGI__FN T * new_xpath_variable ( const char_t *  name)

Definition at line 7207 of file pugixml.cpp.

7208 {
7209 size_t length = strlength(name);
7210 if (length == 0) return 0; // empty variable names are invalid
7211
7212 // $$ we can't use offsetof(T, name) because T is non-POD, so we just allocate additional length characters
7213 void* memory = xml_memory::allocate(sizeof(T) + length * sizeof(char_t));
7214 if (!memory) return 0;
7215
7216 T* result = new (memory) T();
7217
7218 memcpy(result->name, name, (length + 1) * sizeof(char_t));
7219
7220 return result;
7221 }
PUGI__NS_END PUGI__NS_BEGIN PUGI__FN size_t strlength(const char_t *s)
Definition pugixml.cpp:176

References xml_memory_management_function_storage< T >::allocate, and strlength().

◆ new_xpath_variable() [2/2]

PUGI__FN xpath_variable * new_xpath_variable ( xpath_value_type  type,
const char_t *  name 
)

Definition at line 7223 of file pugixml.cpp.

7224 {
7225 switch (type)
7226 {
7227 case xpath_type_node_set:
7228 return new_xpath_variable<xpath_variable_node_set>(name);
7229
7230 case xpath_type_number:
7231 return new_xpath_variable<xpath_variable_number>(name);
7232
7233 case xpath_type_string:
7234 return new_xpath_variable<xpath_variable_string>(name);
7235
7236 case xpath_type_boolean:
7237 return new_xpath_variable<xpath_variable_boolean>(name);
7238
7239 default:
7240 return 0;
7241 }
7242 }

◆ node_height()

PUGI__FN unsigned int node_height ( xml_node  n)

Definition at line 6620 of file pugixml.cpp.

6621 {
6622 unsigned int result = 0;
6623
6624 while (n)
6625 {
6626 ++result;
6627 n = n.parent();
6628 }
6629
6630 return result;
6631 }

Referenced by document_order_comparator::operator()().

◆ node_is_ancestor()

PUGI__FN bool node_is_ancestor ( xml_node  parent,
xml_node  node 
)

Definition at line 6660 of file pugixml.cpp.

6661 {
6662 while (node && node != parent) node = node.parent();
6663
6664 return parent && node == parent;
6665 }

Referenced by xpath_ast_node::step_fill().

◆ node_is_before()

PUGI__FN bool node_is_before ( xml_node  ln,
unsigned int  lh,
xml_node  rn,
unsigned int  rh 
)

Definition at line 6633 of file pugixml.cpp.

6634 {
6635 // normalize heights
6636 for (unsigned int i = rh; i < lh; i++) ln = ln.parent();
6637 for (unsigned int j = lh; j < rh; j++) rn = rn.parent();
6638
6639 // one node is the ancestor of the other
6640 if (ln == rn) return lh < rh;
6641
6642 // find common ancestor
6643 while (ln.parent() != rn.parent())
6644 {
6645 ln = ln.parent();
6646 rn = rn.parent();
6647 }
6648
6649 // there is no common ancestor (the shared parent is null), nodes are from different documents
6650 if (!ln.parent()) return ln < rn;
6651
6652 // determine sibling order
6653 for (; ln; ln = ln.next_sibling())
6654 if (ln == rn)
6655 return true;
6656
6657 return false;
6658 }

Referenced by document_order_comparator::operator()().

◆ node_output()

PUGI__FN void node_output ( xml_buffered_writer writer,
const xml_node &  node,
const char_t *  indent,
unsigned int  flags,
unsigned int  depth 
)

Definition at line 3288 of file pugixml.cpp.

3289 {
3290 const char_t* default_name = PUGIXML_TEXT(":anonymous");
3291
3292 if ((flags & format_indent) != 0 && (flags & format_raw) == 0)
3293 for (unsigned int i = 0; i < depth; ++i) writer.write(indent);
3294
3295 switch (node.type())
3296 {
3297 case node_document:
3298 {
3299 for (xml_node n = node.first_child(); n; n = n.next_sibling())
3300 node_output(writer, n, indent, flags, depth);
3301 break;
3302 }
3303
3304 case node_element:
3305 {
3306 const char_t* name = node.name()[0] ? node.name() : default_name;
3307
3308 writer.write('<');
3309 writer.write(name);
3310
3311 node_output_attributes(writer, node, flags);
3312
3313 if (flags & format_raw)
3314 {
3315 if (!node.first_child())
3316 writer.write(' ', '/', '>');
3317 else
3318 {
3319 writer.write('>');
3320
3321 for (xml_node n = node.first_child(); n; n = n.next_sibling())
3322 node_output(writer, n, indent, flags, depth + 1);
3323
3324 writer.write('<', '/');
3325 writer.write(name);
3326 writer.write('>');
3327 }
3328 }
3329 else if (!node.first_child())
3330 writer.write(' ', '/', '>', '\n');
3331 else if (node.first_child() == node.last_child() && (node.first_child().type() == node_pcdata || node.first_child().type() == node_cdata))
3332 {
3333 writer.write('>');
3334
3335 if (node.first_child().type() == node_pcdata)
3336 text_output(writer, node.first_child().value(), ctx_special_pcdata, flags);
3337 else
3338 text_output_cdata(writer, node.first_child().value());
3339
3340 writer.write('<', '/');
3341 writer.write(name);
3342 writer.write('>', '\n');
3343 }
3344 else
3345 {
3346 writer.write('>', '\n');
3347
3348 for (xml_node n = node.first_child(); n; n = n.next_sibling())
3349 node_output(writer, n, indent, flags, depth + 1);
3350
3351 if ((flags & format_indent) != 0 && (flags & format_raw) == 0)
3352 for (unsigned int i = 0; i < depth; ++i) writer.write(indent);
3353
3354 writer.write('<', '/');
3355 writer.write(name);
3356 writer.write('>', '\n');
3357 }
3358
3359 break;
3360 }
3361
3362 case node_pcdata:
3363 text_output(writer, node.value(), ctx_special_pcdata, flags);
3364 if ((flags & format_raw) == 0) writer.write('\n');
3365 break;
3366
3367 case node_cdata:
3368 text_output_cdata(writer, node.value());
3369 if ((flags & format_raw) == 0) writer.write('\n');
3370 break;
3371
3372 case node_comment:
3373 writer.write('<', '!', '-', '-');
3374 writer.write(node.value());
3375 writer.write('-', '-', '>');
3376 if ((flags & format_raw) == 0) writer.write('\n');
3377 break;
3378
3379 case node_pi:
3380 case node_declaration:
3381 writer.write('<', '?');
3382 writer.write(node.name()[0] ? node.name() : default_name);
3383
3384 if (node.type() == node_declaration)
3385 {
3386 node_output_attributes(writer, node, flags);
3387 }
3388 else if (node.value()[0])
3389 {
3390 writer.write(' ');
3391 writer.write(node.value());
3392 }
3393
3394 writer.write('?', '>');
3395 if ((flags & format_raw) == 0) writer.write('\n');
3396 break;
3397
3398 case node_doctype:
3399 writer.write('<', '!', 'D', 'O', 'C');
3400 writer.write('T', 'Y', 'P', 'E');
3401
3402 if (node.value()[0])
3403 {
3404 writer.write(' ');
3405 writer.write(node.value());
3406 }
3407
3408 writer.write('>');
3409 if ((flags & format_raw) == 0) writer.write('\n');
3410 break;
3411
3412 default:
3413 assert(!"Invalid node type");
3414 }
3415 }
void write(const char_t *data, size_t length)
Definition pugixml.cpp:3062
PUGI__FN void text_output_cdata(xml_buffered_writer &writer, const char_t *s)
Definition pugixml.cpp:3250
PUGI__FN void node_output(xml_buffered_writer &writer, const xml_node &node, const char_t *indent, unsigned int flags, unsigned int depth)
Definition pugixml.cpp:3288
PUGI__FN void node_output_attributes(xml_buffered_writer &writer, const xml_node &node, unsigned int flags)
Definition pugixml.cpp:3272
PUGI__FN void text_output(xml_buffered_writer &writer, const char_t *s, chartypex_t type, unsigned int flags)
Definition pugixml.cpp:3242

References ctx_special_pcdata, node_output(), node_output_attributes(), text_output(), text_output_cdata(), and xml_buffered_writer::write().

Referenced by node_output().

◆ node_output_attributes()

PUGI__FN void node_output_attributes ( xml_buffered_writer writer,
const xml_node &  node,
unsigned int  flags 
)

Definition at line 3272 of file pugixml.cpp.

3273 {
3274 const char_t* default_name = PUGIXML_TEXT(":anonymous");
3275
3276 for (xml_attribute a = node.first_attribute(); a; a = a.next_attribute())
3277 {
3278 writer.write(' ');
3279 writer.write(a.name()[0] ? a.name() : default_name);
3280 writer.write('=', '"');
3281
3282 text_output(writer, a.value(), ctx_special_attr, flags);
3283
3284 writer.write('"');
3285 }
3286 }

References ctx_special_attr, text_output(), and xml_buffered_writer::write().

Referenced by node_output().

◆ normalize_space()

PUGI__FN void normalize_space ( char_t *  buffer)

Definition at line 7097 of file pugixml.cpp.

7098 {
7099 char_t* write = buffer;
7100
7101 for (char_t* it = buffer; *it; )
7102 {
7103 char_t ch = *it++;
7104
7105 if (PUGI__IS_CHARTYPE(ch, ct_space))
7106 {
7107 // replace whitespace sequence with single space
7108 while (PUGI__IS_CHARTYPE(*it, ct_space)) it++;
7109
7110 // avoid leading spaces
7111 if (write != buffer) *write++ = ' ';
7112 }
7113 else *write++ = ch;
7114 }
7115
7116 // remove trailing space
7117 if (write != buffer && PUGI__IS_CHARTYPE(write[-1], ct_space)) write--;
7118
7119 // zero-terminate
7120 *write = 0;
7121 }

References ct_space, and PUGI__IS_CHARTYPE.

Referenced by xpath_ast_node::eval_string().

◆ open_file_wide()

PUGI__FN FILE * open_file_wide ( const wchar_t *  path,
const wchar_t *  mode 
)

Definition at line 3977 of file pugixml.cpp.

3978 {
3979 // there is no standard function to open wide paths, so our best bet is to try utf8 path
3980 char* path_utf8 = convert_path_heap(path);
3981 if (!path_utf8) return 0;
3982
3983 // convert mode to ASCII (we mirror _wfopen interface)
3984 char mode_ascii[4] = {0};
3985 for (size_t i = 0; mode[i]; ++i) mode_ascii[i] = static_cast<char>(mode[i]);
3986
3987 // try to open the utf8 path
3988 FILE* result = fopen(path_utf8, mode_ascii);
3989
3990 // free dummy buffer
3991 xml_memory::deallocate(path_utf8);
3992
3993 return result;
3994 }
PUGI__FN char * convert_path_heap(const wchar_t *str)
Definition pugixml.cpp:3959

References convert_path_heap(), and xml_memory_management_function_storage< T >::deallocate.

◆ partition()

template<typename I , typename Pred >
void partition ( begin,
middle,
end,
const Pred &  pred,
I *  out_eqbeg,
I *  out_eqend 
)

Definition at line 6074 of file pugixml.cpp.

6075 {
6076 I eqbeg = middle, eqend = middle + 1;
6077
6078 // expand equal range
6079 while (eqbeg != begin && *(eqbeg - 1) == *eqbeg) --eqbeg;
6080 while (eqend != end && *eqend == *eqbeg) ++eqend;
6081
6082 // process outer elements
6083 I ltend = eqbeg, gtbeg = eqend;
6084
6085 for (;;)
6086 {
6087 // find the element from the right side that belongs to the left one
6088 for (; gtbeg != end; ++gtbeg)
6089 if (!pred(*eqbeg, *gtbeg))
6090 {
6091 if (*gtbeg == *eqbeg) swap(*gtbeg, *eqend++);
6092 else break;
6093 }
6094
6095 // find the element from the left side that belongs to the right one
6096 for (; ltend != begin; --ltend)
6097 if (!pred(*(ltend - 1), *eqbeg))
6098 {
6099 if (*eqbeg == *(ltend - 1)) swap(*(ltend - 1), *--eqbeg);
6100 else break;
6101 }
6102
6103 // scanned all elements
6104 if (gtbeg == end && ltend == begin)
6105 {
6106 *out_eqbeg = eqbeg;
6107 *out_eqend = eqend;
6108 return;
6109 }
6110
6111 // make room for elements by moving equal area
6112 if (gtbeg == end)
6113 {
6114 if (--ltend != --eqbeg) swap(*ltend, *eqbeg);
6115 swap(*eqbeg, *--eqend);
6116 }
6117 else if (ltend == begin)
6118 {
6119 if (eqend != gtbeg) swap(*eqbeg, *eqend);
6120 ++eqend;
6121 swap(*gtbeg++, *eqbeg++);
6122 }
6123 else swap(*gtbeg++, *--ltend);
6124 }
6125 }

References swap().

Referenced by sort().

◆ prepend_node()

void prepend_node ( xml_node_struct *  child,
xml_node_struct *  node 
)
inline

Definition at line 635 of file pugixml.cpp.

636 {
637 child->parent = node;
638
639 xml_node_struct* head = node->first_child;
640
641 if (head)
642 {
643 child->prev_sibling_c = head->prev_sibling_c;
644 head->prev_sibling_c = child;
645 }
646 else
647 child->prev_sibling_c = child;
648
649 child->next_sibling = head;
650 node->first_child = child;
651 }

◆ qualified_name()

PUGI__FN const char_t * qualified_name ( const xpath_node &  node)

Definition at line 7017 of file pugixml.cpp.

7018 {
7019 return node.attribute() ? node.attribute().name() : node.node().name();
7020 }

Referenced by xpath_ast_node::eval_string(), and local_name().

◆ recursive_copy_skip()

PUGI__FN void recursive_copy_skip ( xml_node &  dest,
const xml_node &  source,
const xml_node &  skip 
)

Definition at line 3463 of file pugixml.cpp.

3464 {
3465 assert(dest.type() == source.type());
3466
3467 switch (source.type())
3468 {
3469 case node_element:
3470 {
3471 dest.set_name(source.name());
3472
3473 for (xml_attribute a = source.first_attribute(); a; a = a.next_attribute())
3474 dest.append_attribute(a.name()).set_value(a.value());
3475
3476 for (xml_node c = source.first_child(); c; c = c.next_sibling())
3477 {
3478 if (c == skip) continue;
3479
3480 xml_node cc = dest.append_child(c.type());
3481 assert(cc);
3482
3483 recursive_copy_skip(cc, c, skip);
3484 }
3485
3486 break;
3487 }
3488
3489 case node_pcdata:
3490 case node_cdata:
3491 case node_comment:
3492 case node_doctype:
3493 dest.set_value(source.value());
3494 break;
3495
3496 case node_pi:
3497 dest.set_name(source.name());
3498 dest.set_value(source.value());
3499 break;
3500
3501 case node_declaration:
3502 {
3503 dest.set_name(source.name());
3504
3505 for (xml_attribute a = source.first_attribute(); a; a = a.next_attribute())
3506 dest.append_attribute(a.name()).set_value(a.value());
3507
3508 break;
3509 }
3510
3511 default:
3512 assert(!"Invalid node type");
3513 }
3514 }
PUGI__FN void recursive_copy_skip(xml_node &dest, const xml_node &source, const xml_node &skip)
Definition pugixml.cpp:3463

References recursive_copy_skip().

Referenced by recursive_copy_skip().

◆ remove_node()

void remove_node ( xml_node_struct *  node)
inline

Definition at line 687 of file pugixml.cpp.

688 {
689 xml_node_struct* parent = node->parent;
690
691 if (node->next_sibling)
692 node->next_sibling->prev_sibling_c = node->prev_sibling_c;
693 else if (parent->first_child)
694 parent->first_child->prev_sibling_c = node->prev_sibling_c;
695
696 if (node->prev_sibling_c->next_sibling)
697 node->prev_sibling_c->next_sibling = node->next_sibling;
698 else
699 parent->first_child = node->next_sibling;
700 }

◆ reverse()

template<typename I >
void reverse ( begin,
end 
)

Definition at line 6009 of file pugixml.cpp.

6010 {
6011 while (end - begin > 1) swap(*begin++, *--end);
6012 }

References swap().

Referenced by FIX::Session::lookupSession(), and xpath_sort().

◆ round_nearest()

PUGI__FN double round_nearest ( double  value)

Definition at line 7005 of file pugixml.cpp.

7006 {
7007 return floor(value + 0.5);
7008 }

Referenced by xpath_ast_node::eval_string().

◆ round_nearest_nzero()

PUGI__FN double round_nearest_nzero ( double  value)

Definition at line 7010 of file pugixml.cpp.

7011 {
7012 // same as round_nearest, but returns -0 for [-0.5, -0]
7013 // ceil is used to differentiate between +0 and -0 (we return -0 for [-0.5, -0] and +0 for +0)
7014 return (value >= -0.5 && value <= 0) ? ceil(value) : floor(value + 0.5);
7015 }

Referenced by xpath_ast_node::eval_number().

◆ save_file_impl()

PUGI__FN bool save_file_impl ( const xml_document &  doc,
FILE *  file,
const char_t *  indent,
unsigned int  flags,
xml_encoding  encoding 
)

Definition at line 3997 of file pugixml.cpp.

3998 {
3999 if (!file) return false;
4000
4001 xml_writer_file writer(file);
4002 doc.save(writer, indent, flags, encoding);
4003
4004 int result = ferror(file);
4005
4006 fclose(file);
4007
4008 return result == 0;
4009 }

◆ set_value_buffer()

PUGI__FN bool set_value_buffer ( char_t *&  dest,
uintptr_t header,
uintptr_t  header_mask,
char(&)  buf[128] 
)

Definition at line 3641 of file pugixml.cpp.

3642 {
3643 #ifdef PUGIXML_WCHAR_MODE
3644 char_t wbuf[128];
3645 impl::widen_ascii(wbuf, buf);
3646
3647 return strcpy_insitu(dest, header, header_mask, wbuf);
3648 #else
3649 return strcpy_insitu(dest, header, header_mask, buf);
3650 #endif
3651 }
PUGI__FN bool strcpy_insitu(char_t *&dest, uintptr_t &header, uintptr_t header_mask, const char_t *source)
Definition pugixml.cpp:1668

References strcpy_insitu().

Referenced by set_value_convert(), set_value_convert(), and set_value_convert().

◆ set_value_convert() [1/4]

PUGI__FN bool set_value_convert ( char_t *&  dest,
uintptr_t header,
uintptr_t  header_mask,
bool  value 
)

Definition at line 3677 of file pugixml.cpp.

3678 {
3679 return strcpy_insitu(dest, header, header_mask, value ? PUGIXML_TEXT("true") : PUGIXML_TEXT("false"));
3680 }

References strcpy_insitu().

◆ set_value_convert() [2/4]

PUGI__FN bool set_value_convert ( char_t *&  dest,
uintptr_t header,
uintptr_t  header_mask,
double  value 
)

Definition at line 3669 of file pugixml.cpp.

3670 {
3671 char buf[128];
3672 sprintf(buf, "%g", value);
3673
3674 return set_value_buffer(dest, header, header_mask, buf);
3675 }
PUGI__FN bool set_value_buffer(char_t *&dest, uintptr_t &header, uintptr_t header_mask, char(&buf)[128])
Definition pugixml.cpp:3641

References set_value_buffer().

◆ set_value_convert() [3/4]

PUGI__FN bool set_value_convert ( char_t *&  dest,
uintptr_t header,
uintptr_t  header_mask,
int  value 
)

Definition at line 3653 of file pugixml.cpp.

3654 {
3655 char buf[128];
3656 sprintf(buf, "%d", value);
3657
3658 return set_value_buffer(dest, header, header_mask, buf);
3659 }

References set_value_buffer().

◆ set_value_convert() [4/4]

PUGI__FN bool set_value_convert ( char_t *&  dest,
uintptr_t header,
uintptr_t  header_mask,
unsigned int  value 
)

Definition at line 3661 of file pugixml.cpp.

3662 {
3663 char buf[128];
3664 sprintf(buf, "%u", value);
3665
3666 return set_value_buffer(dest, header, header_mask, buf);
3667 }

References set_value_buffer().

◆ sort()

template<typename I , typename Pred >
void sort ( begin,
end,
const Pred &  pred 
)

Definition at line 6153 of file pugixml.cpp.

6154 {
6155 // sort large chunks
6156 while (end - begin > 32)
6157 {
6158 // find median element
6159 I middle = begin + (end - begin) / 2;
6160 median(begin, middle, end - 1, pred);
6161
6162 // partition in three chunks (< = >)
6163 I eqbeg, eqend;
6164 partition(begin, middle, end, pred, &eqbeg, &eqend);
6165
6166 // loop on larger half
6167 if (eqbeg - begin > end - eqend)
6168 {
6169 sort(eqend, end, pred);
6170 end = eqbeg;
6171 }
6172 else
6173 {
6174 sort(begin, eqbeg, pred);
6175 begin = eqend;
6176 }
6177 }
6178
6179 // insertion sort small chunk
6180 if (begin != end) insertion_sort(begin, end, pred, &*begin);
6181 }
void sort(I begin, I end, const Pred &pred)
Definition pugixml.cpp:6153
void median(I first, I middle, I last, const Pred &pred)
Definition pugixml.cpp:6134
void insertion_sort(I begin, I end, const Pred &pred, T *)
Definition pugixml.cpp:6042
void partition(I begin, I middle, I end, const Pred &pred, I *out_eqbeg, I *out_eqend)
Definition pugixml.cpp:6074

References insertion_sort(), median(), partition(), and sort().

Referenced by xpath_node_set_raw::remove_duplicates(), sort(), and xpath_sort().

◆ starts_with()

PUGI__NS_END PUGI__NS_BEGIN PUGI__FN bool starts_with ( const char_t *  string,
const char_t *  pattern 
)

Definition at line 6534 of file pugixml.cpp.

6535 {
6536 while (*pattern && *string == *pattern)
6537 {
6538 string++;
6539 pattern++;
6540 }
6541
6542 return *pattern == 0;
6543 }

Referenced by xpath_ast_node::eval_boolean(), namespace_uri_predicate::operator()(), xpath_ast_node::step_push(), and xpath_ast_node::step_push().

◆ strconv_cdata()

PUGI__FN char_t * strconv_cdata ( char_t *  s,
char_t  endch 
)

Definition at line 1939 of file pugixml.cpp.

1940 {
1941 gap g;
1942
1943 while (true)
1944 {
1946
1947 if (*s == '\r') // Either a single 0x0d or 0x0d 0x0a pair
1948 {
1949 *s++ = '\n'; // replace first one with 0x0a
1950
1951 if (*s == '\n') g.push(s, 1);
1952 }
1953 else if (s[0] == ']' && s[1] == ']' && PUGI__ENDSWITH(s[2], '>')) // CDATA ends here
1954 {
1955 *g.flush(s) = 0;
1956
1957 return s + 1;
1958 }
1959 else if (*s == 0)
1960 {
1961 return 0;
1962 }
1963 else ++s;
1964 }
1965 }
#define PUGI__SCANWHILE_UNROLL(X)
Definition pugixml.cpp:1906
#define PUGI__ENDSWITH(c, e)
Definition pugixml.cpp:1899
char_t * flush(char_t *s)
Definition pugixml.cpp:1744
void push(char_t *&s, size_t count)
Definition pugixml.cpp:1727

References ct_parse_cdata, gap::flush(), PUGI__ENDSWITH, PUGI__IS_CHARTYPE, PUGI__SCANWHILE_UNROLL, and gap::push().

Referenced by xml_parser::parse_exclamation().

◆ strconv_comment()

PUGI__FN char_t * strconv_comment ( char_t *  s,
char_t  endch 
)

Definition at line 1911 of file pugixml.cpp.

1912 {
1913 gap g;
1914
1915 while (true)
1916 {
1918
1919 if (*s == '\r') // Either a single 0x0d or 0x0d 0x0a pair
1920 {
1921 *s++ = '\n'; // replace first one with 0x0a
1922
1923 if (*s == '\n') g.push(s, 1);
1924 }
1925 else if (s[0] == '-' && s[1] == '-' && PUGI__ENDSWITH(s[2], '>')) // comment ends here
1926 {
1927 *g.flush(s) = 0;
1928
1929 return s + (s[2] == '>' ? 3 : 2);
1930 }
1931 else if (*s == 0)
1932 {
1933 return 0;
1934 }
1935 else ++s;
1936 }
1937 }

References ct_parse_comment, gap::flush(), PUGI__ENDSWITH, PUGI__IS_CHARTYPE, PUGI__SCANWHILE_UNROLL, and gap::push().

Referenced by xml_parser::parse_exclamation().

◆ strconv_escape()

PUGI__FN char_t * strconv_escape ( char_t *  s,
gap g 
)

Definition at line 1758 of file pugixml.cpp.

1759 {
1760 char_t* stre = s + 1;
1761
1762 switch (*stre)
1763 {
1764 case '#': // &#...
1765 {
1766 unsigned int ucsc = 0;
1767
1768 if (stre[1] == 'x') // &#x... (hex code)
1769 {
1770 stre += 2;
1771
1772 char_t ch = *stre;
1773
1774 if (ch == ';') return stre;
1775
1776 for (;;)
1777 {
1778 if (static_cast<unsigned int>(ch - '0') <= 9)
1779 ucsc = 16 * ucsc + (ch - '0');
1780 else if (static_cast<unsigned int>((ch | ' ') - 'a') <= 5)
1781 ucsc = 16 * ucsc + ((ch | ' ') - 'a' + 10);
1782 else if (ch == ';')
1783 break;
1784 else // cancel
1785 return stre;
1786
1787 ch = *++stre;
1788 }
1789
1790 ++stre;
1791 }
1792 else // &#... (dec code)
1793 {
1794 char_t ch = *++stre;
1795
1796 if (ch == ';') return stre;
1797
1798 for (;;)
1799 {
1800 if (static_cast<unsigned int>(static_cast<unsigned int>(ch) - '0') <= 9)
1801 ucsc = 10 * ucsc + (ch - '0');
1802 else if (ch == ';')
1803 break;
1804 else // cancel
1805 return stre;
1806
1807 ch = *++stre;
1808 }
1809
1810 ++stre;
1811 }
1812
1813 #ifdef PUGIXML_WCHAR_MODE
1814 s = reinterpret_cast<char_t*>(wchar_writer::any(reinterpret_cast<wchar_writer::value_type>(s), ucsc));
1815 #else
1816 s = reinterpret_cast<char_t*>(utf8_writer::any(reinterpret_cast<uint8_t*>(s), ucsc));
1817 #endif
1818
1819 g.push(s, stre - s);
1820 return stre;
1821 }
1822
1823 case 'a': // &a
1824 {
1825 ++stre;
1826
1827 if (*stre == 'm') // &am
1828 {
1829 if (*++stre == 'p' && *++stre == ';') // &amp;
1830 {
1831 *s++ = '&';
1832 ++stre;
1833
1834 g.push(s, stre - s);
1835 return stre;
1836 }
1837 }
1838 else if (*stre == 'p') // &ap
1839 {
1840 if (*++stre == 'o' && *++stre == 's' && *++stre == ';') // &apos;
1841 {
1842 *s++ = '\'';
1843 ++stre;
1844
1845 g.push(s, stre - s);
1846 return stre;
1847 }
1848 }
1849 break;
1850 }
1851
1852 case 'g': // &g
1853 {
1854 if (*++stre == 't' && *++stre == ';') // &gt;
1855 {
1856 *s++ = '>';
1857 ++stre;
1858
1859 g.push(s, stre - s);
1860 return stre;
1861 }
1862 break;
1863 }
1864
1865 case 'l': // &l
1866 {
1867 if (*++stre == 't' && *++stre == ';') // &lt;
1868 {
1869 *s++ = '<';
1870 ++stre;
1871
1872 g.push(s, stre - s);
1873 return stre;
1874 }
1875 break;
1876 }
1877
1878 case 'q': // &q
1879 {
1880 if (*++stre == 'u' && *++stre == 'o' && *++stre == 't' && *++stre == ';') // &quot;
1881 {
1882 *s++ = '"';
1883 ++stre;
1884
1885 g.push(s, stre - s);
1886 return stre;
1887 }
1888 break;
1889 }
1890
1891 default:
1892 break;
1893 }
1894
1895 return stre;
1896 }
static value_type any(value_type result, uint32_t ch)
Definition pugixml.cpp:822

References utf8_writer::any(), and gap::push().

Referenced by strconv_pcdata_impl< opt_trim, opt_eol, opt_escape >::parse(), strconv_attribute_impl< opt_escape >::parse_eol(), strconv_attribute_impl< opt_escape >::parse_simple(), strconv_attribute_impl< opt_escape >::parse_wconv(), and strconv_attribute_impl< opt_escape >::parse_wnorm().

◆ strcpy_insitu()

PUGI__FN bool strcpy_insitu ( char_t *&  dest,
uintptr_t header,
uintptr_t  header_mask,
const char_t *  source 
)

Definition at line 1668 of file pugixml.cpp.

1669 {
1670 assert(header);
1671
1672 size_t source_length = strlength(source);
1673
1674 if (source_length == 0)
1675 {
1676 // empty string and null pointer are equivalent, so just deallocate old memory
1677 xml_allocator* alloc = reinterpret_cast<xml_memory_page*>(header & xml_memory_page_pointer_mask)->allocator;
1678
1679 if (header & header_mask) alloc->deallocate_string(dest);
1680
1681 // mark the string as not allocated
1682 dest = 0;
1683 header &= ~header_mask;
1684
1685 return true;
1686 }
1687 else if (dest && strcpy_insitu_allow(source_length, header & header_mask, dest))
1688 {
1689 // we can reuse old buffer, so just copy the new data (including zero terminator)
1690 memcpy(dest, source, (source_length + 1) * sizeof(char_t));
1691
1692 return true;
1693 }
1694 else
1695 {
1696 xml_allocator* alloc = reinterpret_cast<xml_memory_page*>(header & xml_memory_page_pointer_mask)->allocator;
1697
1698 // allocate new buffer
1699 char_t* buf = alloc->allocate_string(source_length + 1);
1700 if (!buf) return false;
1701
1702 // copy the string (including zero terminator)
1703 memcpy(buf, source, (source_length + 1) * sizeof(char_t));
1704
1705 // deallocate old buffer (*after* the above to protect against overlapping memory and/or allocation failures)
1706 if (header & header_mask) alloc->deallocate_string(dest);
1707
1708 // the string is now allocated, so set the flag
1709 dest = buf;
1710 header |= header_mask;
1711
1712 return true;
1713 }
1714 }
bool strcpy_insitu_allow(size_t length, uintptr_t allocated, char_t *target)
Definition pugixml.cpp:1654
char_t * allocate_string(size_t length)
Definition pugixml.cpp:396

References xml_allocator::allocate_string(), xml_allocator::deallocate_string(), strcpy_insitu_allow(), strlength(), and xml_memory_page_pointer_mask.

Referenced by set_value_buffer(), and set_value_convert().

◆ strcpy_insitu_allow()

bool strcpy_insitu_allow ( size_t  length,
uintptr_t  allocated,
char_t *  target 
)
inline

Definition at line 1654 of file pugixml.cpp.

1655 {
1656 assert(target);
1657 size_t target_length = strlength(target);
1658
1659 // always reuse document buffer memory if possible
1660 if (!allocated) return target_length >= length;
1661
1662 // reuse heap memory if waste is not too great
1663 const size_t reuse_threshold = 32;
1664
1665 return target_length >= length && (target_length < reuse_threshold || target_length - length < target_length / 2);
1666 }

References strlength().

Referenced by strcpy_insitu().

◆ strequal()

PUGI__FN bool strequal ( const char_t *  src,
const char_t *  dst 
)

Definition at line 188 of file pugixml.cpp.

189 {
190 assert(src && dst);
191
192 #ifdef PUGIXML_WCHAR_MODE
193 return wcscmp(src, dst) == 0;
194 #else
195 return strcmp(src, dst) == 0;
196 #endif
197 }

Referenced by xpath_string::operator!=(), xpath_string::operator==(), xpath_ast_node::step_push(), and xpath_ast_node::step_push().

◆ strequalrange()

PUGI__FN bool strequalrange ( const char_t *  lhs,
const char_t *  rhs,
size_t  count 
)

Definition at line 200 of file pugixml.cpp.

201 {
202 for (size_t i = 0; i < count; ++i)
203 if (lhs[i] != rhs[i])
204 return false;
205
206 return lhs[count] == 0;
207 }

Referenced by namespace_uri_predicate::operator()(), and xpath_lexer_string::operator==().

◆ string_value()

PUGI__FN xpath_string string_value ( const xpath_node &  na,
xpath_allocator alloc 
)

Definition at line 6570 of file pugixml.cpp.

6571 {
6572 if (na.attribute())
6573 return xpath_string_const(na.attribute().value());
6574 else
6575 {
6576 const xml_node& n = na.node();
6577
6578 switch (n.type())
6579 {
6580 case node_pcdata:
6581 case node_cdata:
6582 case node_comment:
6583 case node_pi:
6584 return xpath_string_const(n.value());
6585
6586 case node_document:
6587 case node_element:
6588 {
6589 xpath_string result;
6590
6591 xml_node cur = n.first_child();
6592
6593 while (cur && cur != n)
6594 {
6595 if (cur.type() == node_pcdata || cur.type() == node_cdata)
6596 result.append(xpath_string_const(cur.value()), alloc);
6597
6598 if (cur.first_child())
6599 cur = cur.first_child();
6600 else if (cur.next_sibling())
6601 cur = cur.next_sibling();
6602 else
6603 {
6604 while (!cur.next_sibling() && cur != n)
6605 cur = cur.parent();
6606
6607 if (cur != n) cur = cur.next_sibling();
6608 }
6609 }
6610
6611 return result;
6612 }
6613
6614 default:
6615 return xpath_string();
6616 }
6617 }
6618 }
void append(const xpath_string &o, xpath_allocator *alloc)
Definition pugixml.cpp:6450

References xpath_string::append(), and xpath_string_const().

Referenced by xpath_ast_node::compare_eq(), xpath_ast_node::compare_rel(), xpath_ast_node::eval_number(), and xpath_ast_node::eval_string().

◆ strlength()

PUGI__NS_END PUGI__NS_BEGIN PUGI__FN size_t strlength ( const char_t *  s)

Definition at line 176 of file pugixml.cpp.

177 {
178 assert(s);
179
180 #ifdef PUGIXML_WCHAR_MODE
181 return wcslen(s);
182 #else
183 return strlen(s);
184 #endif
185 }

Referenced by xpath_string::append(), xpath_string::duplicate_string(), xpath_string::length(), new_xpath_variable(), strcpy_insitu(), strcpy_insitu_allow(), translate(), and xml_buffered_writer::write().

◆ strlength_wide()

PUGI__FN size_t strlength_wide ( const wchar_t *  s)

Definition at line 210 of file pugixml.cpp.

211 {
212 assert(s);
213
214 #ifdef PUGIXML_WCHAR_MODE
215 return wcslen(s);
216 #else
217 const wchar_t* end = s;
218 while (*end) end++;
219 return static_cast<size_t>(end - s);
220 #endif
221 }

Referenced by convert_path_heap().

◆ swap()

template<typename T >
void swap ( T &  lhs,
T &  rhs 
)

Definition at line 5991 of file pugixml.cpp.

5992 {
5993 T temp = lhs;
5994 lhs = rhs;
5995 rhs = temp;
5996 }

Referenced by xpath_ast_node::compare_eq(), median3(), partition(), and reverse().

◆ text_output()

PUGI__FN void text_output ( xml_buffered_writer writer,
const char_t *  s,
chartypex_t  type,
unsigned int  flags 
)

Definition at line 3242 of file pugixml.cpp.

3243 {
3244 if (flags & format_no_escapes)
3245 writer.write(s);
3246 else
3247 text_output_escaped(writer, s, type);
3248 }
PUGI__FN void text_output_escaped(xml_buffered_writer &writer, const char_t *s, chartypex_t type)
Definition pugixml.cpp:3201

References text_output_escaped(), and xml_buffered_writer::write().

Referenced by node_output(), and node_output_attributes().

◆ text_output_cdata()

PUGI__FN void text_output_cdata ( xml_buffered_writer writer,
const char_t *  s 
)

Definition at line 3250 of file pugixml.cpp.

3251 {
3252 do
3253 {
3254 writer.write('<', '!', '[', 'C', 'D');
3255 writer.write('A', 'T', 'A', '[');
3256
3257 const char_t* prev = s;
3258
3259 // look for ]]> sequence - we can't output it as is since it terminates CDATA
3260 while (*s && !(s[0] == ']' && s[1] == ']' && s[2] == '>')) ++s;
3261
3262 // skip ]] if we stopped at ]]>, > will go to the next CDATA section
3263 if (*s) s += 2;
3264
3265 writer.write(prev, static_cast<size_t>(s - prev));
3266
3267 writer.write(']', ']', '>');
3268 }
3269 while (*s);
3270 }

References xml_buffered_writer::write().

Referenced by node_output().

◆ text_output_escaped()

PUGI__FN void text_output_escaped ( xml_buffered_writer writer,
const char_t *  s,
chartypex_t  type 
)

Definition at line 3201 of file pugixml.cpp.

3202 {
3203 while (*s)
3204 {
3205 const char_t* prev = s;
3206
3207 // While *s is a usual symbol
3208 while (!PUGI__IS_CHARTYPEX(*s, type)) ++s;
3209
3210 writer.write(prev, static_cast<size_t>(s - prev));
3211
3212 switch (*s)
3213 {
3214 case 0: break;
3215 case '&':
3216 writer.write('&', 'a', 'm', 'p', ';');
3217 ++s;
3218 break;
3219 case '<':
3220 writer.write('&', 'l', 't', ';');
3221 ++s;
3222 break;
3223 case '>':
3224 writer.write('&', 'g', 't', ';');
3225 ++s;
3226 break;
3227 case '"':
3228 writer.write('&', 'q', 'u', 'o', 't', ';');
3229 ++s;
3230 break;
3231 default: // s is not a usual symbol
3232 {
3233 unsigned int ch = static_cast<unsigned int>(*s++);
3234 assert(ch < 32);
3235
3236 writer.write('&', '#', static_cast<char_t>((ch / 10) + '0'), static_cast<char_t>((ch % 10) + '0'), ';');
3237 }
3238 }
3239 }
3240 }

References PUGI__IS_CHARTYPEX, and xml_buffered_writer::write().

Referenced by text_output().

◆ tolower_ascii()

PUGI__FN char_t tolower_ascii ( char_t  ch)

Definition at line 6565 of file pugixml.cpp.

6566 {
6567 return static_cast<unsigned int>(ch - 'A') < 26 ? static_cast<char_t>(ch | ' ') : ch;
6568 }

Referenced by xpath_ast_node::eval_boolean().

◆ translate()

PUGI__FN void translate ( char_t *  buffer,
const char_t *  from,
const char_t *  to 
)

Definition at line 7123 of file pugixml.cpp.

7124 {
7125 size_t to_length = strlength(to);
7126
7127 char_t* write = buffer;
7128
7129 while (*buffer)
7130 {
7131 PUGI__DMC_VOLATILE char_t ch = *buffer++;
7132
7133 const char_t* pos = find_char(from, ch);
7134
7135 if (!pos)
7136 *write++ = ch; // do not process
7137 else if (static_cast<size_t>(pos - from) < to_length)
7138 *write++ = to[pos - from]; // replace
7139 }
7140
7141 // zero-terminate
7142 *write = 0;
7143 }

References find_char(), PUGI__DMC_VOLATILE, and strlength().

Referenced by xpath_ast_node::eval_string().

◆ truncate_zeros()

PUGI__FN void truncate_zeros ( char *  begin,
char *  end 
)

Definition at line 6817 of file pugixml.cpp.

6818 {
6819 while (begin != end && end[-1] == '0') end--;
6820
6821 *end = 0;
6822 }

Referenced by convert_number_to_mantissa_exponent().

◆ unique()

template<typename I >
I unique ( begin,
end 
)

Definition at line 6014 of file pugixml.cpp.

6015 {
6016 // fast skip head
6017 while (end - begin > 1 && *begin != *(begin + 1)) begin++;
6018
6019 if (begin == end) return begin;
6020
6021 // last written element
6022 I write = begin++;
6023
6024 // merge unique elements
6025 while (begin != end)
6026 {
6027 if (*begin != *write)
6028 *++write = *begin++;
6029 else
6030 begin++;
6031 }
6032
6033 // past-the-end (write points to live element)
6034 return write + 1;
6035 }

Referenced by xpath_node_set_raw::remove_duplicates().

◆ xpath_first()

PUGI__FN xpath_node xpath_first ( const xpath_node *  begin,
const xpath_node *  end,
xpath_node_set::type_t  type 
)

Definition at line 7318 of file pugixml.cpp.

7319 {
7320 if (begin == end) return xpath_node();
7321
7322 switch (type)
7323 {
7324 case xpath_node_set::type_sorted:
7325 return *begin;
7326
7327 case xpath_node_set::type_sorted_reverse:
7328 return *(end - 1);
7329
7330 case xpath_node_set::type_unsorted:
7331 return *min_element(begin, end, document_order_comparator());
7332
7333 default:
7334 assert(!"Invalid node set type");
7335 return xpath_node();
7336 }
7337 }
I min_element(I begin, I end, const Pred &pred)
Definition pugixml.cpp:5998

References min_element().

Referenced by xpath_node_set_raw::first().

◆ xpath_sort()

PUGI__NS_END PUGI__NS_BEGIN PUGI__FN xpath_node_set::type_t xpath_sort ( xpath_node *  begin,
xpath_node *  end,
xpath_node_set::type_t  type,
bool  rev 
)

Definition at line 7302 of file pugixml.cpp.

7303 {
7304 xpath_node_set::type_t order = rev ? xpath_node_set::type_sorted_reverse : xpath_node_set::type_sorted;
7305
7306 if (type == xpath_node_set::type_unsorted)
7307 {
7308 sort(begin, end, document_order_comparator());
7309
7310 type = xpath_node_set::type_sorted;
7311 }
7312
7313 if (type != order) reverse(begin, end);
7314
7315 return order;
7316 }
void reverse(I begin, I end)
Definition pugixml.cpp:6009

References reverse(), and sort().

Referenced by xpath_node_set_raw::sort_do().

◆ xpath_string_const()

PUGI__FN xpath_string xpath_string_const ( const char_t *  str)

Definition at line 6527 of file pugixml.cpp.

6528 {
6529 return xpath_string(str, false);
6530 }

Referenced by convert_number_to_string(), xpath_ast_node::eval_string(), and string_value().

◆ zero_terminate_buffer()

PUGI__FN size_t zero_terminate_buffer ( void *  buffer,
size_t  size,
xml_encoding  encoding 
)

Definition at line 3740 of file pugixml.cpp.

3741 {
3742 // We only need to zero-terminate if encoding conversion does not do it for us
3743 #ifdef PUGIXML_WCHAR_MODE
3744 xml_encoding wchar_encoding = get_wchar_encoding();
3745
3746 if (encoding == wchar_encoding || need_endian_swap_utf(encoding, wchar_encoding))
3747 {
3748 size_t length = size / sizeof(char_t);
3749
3750 static_cast<char_t*>(buffer)[length] = 0;
3751 return (length + 1) * sizeof(char_t);
3752 }
3753 #else
3754 if (encoding == encoding_utf8)
3755 {
3756 static_cast<char*>(buffer)[size] = 0;
3757 return size + 1;
3758 }
3759 #endif
3760
3761 return size;
3762 }

References get_wchar_encoding().

Referenced by load_file_impl(), and load_stream_impl().

Variable Documentation

◆ chartype_table

const unsigned char chartype_table[256]
static
Initial value:
=
{
55, 0, 0, 0, 0, 0, 0, 0, 0, 12, 12, 0, 0, 63, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
8, 0, 6, 0, 0, 0, 7, 6, 0, 0, 0, 0, 0, 96, 64, 0,
64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 192, 0, 1, 0, 48, 0,
0, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 0, 0, 16, 0, 192,
0, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 0, 0, 0, 0, 0,
192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192
}

Definition at line 1137 of file pugixml.cpp.

1138 {
1139 55, 0, 0, 0, 0, 0, 0, 0, 0, 12, 12, 0, 0, 63, 0, 0, // 0-15
1140 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 16-31
1141 8, 0, 6, 0, 0, 0, 7, 6, 0, 0, 0, 0, 0, 96, 64, 0, // 32-47
1142 64, 64, 64, 64, 64, 64, 64, 64, 64, 64, 192, 0, 1, 0, 48, 0, // 48-63
1143 0, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, // 64-79
1144 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 0, 0, 16, 0, 192, // 80-95
1145 0, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, // 96-111
1146 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 0, 0, 0, 0, 0, // 112-127
1147
1148 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, // 128+
1149 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
1150 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
1151 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
1152 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
1153 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
1154 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192,
1155 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192, 192
1156 };

◆ chartypex_table

const unsigned char chartypex_table[256]
static
Initial value:
=
{
3, 3, 3, 3, 3, 3, 3, 3, 3, 0, 2, 3, 3, 2, 3, 3,
3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
0, 0, 2, 0, 0, 0, 3, 0, 0, 0, 0, 0, 0, 16, 16, 0,
24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 0, 0, 3, 0, 3, 0,
0, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 0, 0, 0, 0, 20,
0, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 0, 0, 0, 0, 0,
20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20
}

Definition at line 1167 of file pugixml.cpp.

1168 {
1169 3, 3, 3, 3, 3, 3, 3, 3, 3, 0, 2, 3, 3, 2, 3, 3, // 0-15
1170 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, // 16-31
1171 0, 0, 2, 0, 0, 0, 3, 0, 0, 0, 0, 0, 0, 16, 16, 0, // 32-47
1172 24, 24, 24, 24, 24, 24, 24, 24, 24, 24, 0, 0, 3, 0, 3, 0, // 48-63
1173
1174 0, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, // 64-79
1175 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 0, 0, 0, 0, 20, // 80-95
1176 0, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, // 96-111
1177 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 0, 0, 0, 0, 0, // 112-127
1178
1179 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, // 128+
1180 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
1181 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
1182 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
1183 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
1184 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
1185 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20,
1186 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20
1187 };

◆ dummy_node_set

const xpath_node_set dummy_node_set
static

Definition at line 7186 of file pugixml.cpp.

◆ xml_memory_page_alignment

const uintptr_t xml_memory_page_alignment = 32
static

Definition at line 269 of file pugixml.cpp.

Referenced by xml_allocator::allocate_page().

◆ xml_memory_page_name_allocated_mask

const uintptr_t xml_memory_page_name_allocated_mask = 16
static

Definition at line 271 of file pugixml.cpp.

Referenced by document_order().

◆ xml_memory_page_pointer_mask

const uintptr_t xml_memory_page_pointer_mask = ~(xml_memory_page_alignment - 1)
static

Definition at line 270 of file pugixml.cpp.

Referenced by destroy_attribute(), destroy_node(), get_allocator(), and strcpy_insitu().

◆ xml_memory_page_size

PUGI__NS_END static PUGI__NS_BEGIN const size_t xml_memory_page_size
static
Initial value:
=
32768

Definition at line 261 of file pugixml.cpp.

Referenced by xml_allocator::allocate_memory(), and xml_allocator::allocate_memory_oob().

◆ xml_memory_page_type_mask

const uintptr_t xml_memory_page_type_mask = 7
static

Definition at line 273 of file pugixml.cpp.

Referenced by xml_parser::parse_tree().

◆ xml_memory_page_value_allocated_mask

const uintptr_t xml_memory_page_value_allocated_mask = 8
static

Definition at line 272 of file pugixml.cpp.

Referenced by document_order().


Generated on Sun Mar 31 2024 07:07:24 for QuickFIX by doxygen 1.9.8 written by Dimitri van Heesch, © 1997-2001