aboutsummaryrefslogtreecommitdiff
path: root/libxsde/xsde/cxx/parser/expat/document.hxx
diff options
context:
space:
mode:
Diffstat (limited to 'libxsde/xsde/cxx/parser/expat/document.hxx')
-rw-r--r--libxsde/xsde/cxx/parser/expat/document.hxx337
1 files changed, 337 insertions, 0 deletions
diff --git a/libxsde/xsde/cxx/parser/expat/document.hxx b/libxsde/xsde/cxx/parser/expat/document.hxx
new file mode 100644
index 0000000..2f87686
--- /dev/null
+++ b/libxsde/xsde/cxx/parser/expat/document.hxx
@@ -0,0 +1,337 @@
+// file : xsde/cxx/parser/expat/document.hxx
+// author : Boris Kolpackov <boris@codesynthesis.com>
+// copyright : Copyright (c) 2005-2009 Code Synthesis Tools CC
+// license : GNU GPL v2 + exceptions; see accompanying LICENSE file
+
+#ifndef XSDE_CXX_PARSER_EXPAT_DOCUMENT_HXX
+#define XSDE_CXX_PARSER_EXPAT_DOCUMENT_HXX
+
+#include <xsde/cxx/config.hxx>
+
+#include <stddef.h> // size_t
+
+#ifdef XSDE_STL
+# include <string>
+#endif
+
+#ifdef XSDE_IOSTREAM
+# include <iosfwd>
+#endif
+
+#include <xsde/c/expat/expat.h>
+
+// We only support UTF-8 expat for now.
+//
+#ifdef XML_UNICODE
+#error UTF-16 expat (XML_UNICODE defined) is not supported
+#endif
+
+#include <xsde/cxx/string.hxx>
+
+#ifdef XSDE_STL
+# include <xsde/cxx/string-sequence-stl.hxx>
+#else
+# include <xsde/cxx/string-sequence.hxx>
+#endif
+
+#include <xsde/cxx/parser/context.hxx>
+#include <xsde/cxx/parser/elements.hxx>
+
+#ifndef XSDE_EXCEPTIONS
+# include <xsde/cxx/parser/error.hxx>
+#endif
+
+namespace xsde
+{
+ namespace cxx
+ {
+ namespace parser
+ {
+ namespace expat
+ {
+ // Simple auto pointer for Expat's XML_Parser object.
+ //
+ struct parser_auto_ptr
+ {
+ ~parser_auto_ptr ();
+
+ explicit
+ parser_auto_ptr (XML_Parser = 0);
+
+ parser_auto_ptr&
+ operator= (XML_Parser);
+
+ public:
+ operator XML_Parser ()
+ {
+ return parser_;
+ }
+
+ private:
+ parser_auto_ptr (const parser_auto_ptr&);
+
+ parser_auto_ptr&
+ operator= (const parser_auto_ptr&);
+
+ private:
+ XML_Parser parser_;
+ };
+
+ //
+ //
+ class document_pimpl
+ {
+ public:
+ virtual
+ ~document_pimpl ();
+
+#ifdef XSDE_POLYMORPHIC
+ document_pimpl (parser_base&,
+ const char* root_element_name,
+ bool polymorphic = false);
+
+ document_pimpl (parser_base&,
+ const char* root_element_namespace,
+ const char* root_element_name,
+ bool polymorphic = false);
+
+#ifdef XSDE_STL
+ document_pimpl (parser_base&,
+ const std::string& root_element_name,
+ bool polymorphic = false);
+
+ document_pimpl (parser_base&,
+ const std::string& root_element_namespace,
+ const std::string& root_element_name,
+ bool polymorphic = false);
+
+#endif // XSDE_STL
+ protected:
+ document_pimpl (); // Non-polymorphic parsing.
+
+ document_pimpl (const char* root_element_name);
+
+ document_pimpl (const char* root_element_namespace,
+ const char* root_element_name);
+
+#ifdef XSDE_STL
+ document_pimpl (const std::string& root_element_name);
+
+ document_pimpl (const std::string& root_element_namespace,
+ const std::string& root_element_name);
+#endif
+
+
+#else // XSDE_POLYMORPHIC
+
+ document_pimpl (parser_base&,
+ const char* root_element_name);
+
+ document_pimpl (parser_base&,
+ const char* root_element_namespace,
+ const char* root_element_name);
+
+#ifdef XSDE_STL
+ document_pimpl (parser_base&,
+ const std::string& root_element_name);
+
+ document_pimpl (parser_base&,
+ const std::string& root_element_namespace,
+ const std::string& root_element_name);
+#endif
+ protected:
+ document_pimpl ();
+
+#endif // XSDE_POLYMORPHIC
+
+ // This function is called to obtain the root element type parser.
+ // If the returned pointed is 0 then the whole document content
+ // is ignored.
+ //
+ // The type argument contains the type name and namespace if
+ // xsi:type attribute or an element that substitutes the root
+ // was specified and 0 otherwise. The type argument is in the
+ // form "<name> <namespace>" with the space and namespace part
+ // absent if the type does not have a namespace.
+ //
+ //
+#ifdef XSDE_POLYMORPHIC
+ virtual parser_base*
+ start_root_element (const ro_string& ns,
+ const ro_string& name,
+ const char* type);
+#else
+ virtual parser_base*
+ start_root_element (const ro_string& ns, const ro_string& name);
+#endif
+
+
+ // This function is called to indicate the completion of document
+ // parsing. The parser argument contains the pointer returned by
+ // start_root_element.
+ //
+ virtual void
+ end_root_element (const ro_string& ns,
+ const ro_string& name,
+ parser_base* parser);
+
+ public:
+ // If you override start_root_element() then you will most
+ // likely also want to override reset() in order to reset
+ // root element parser(s).
+ //
+ virtual void
+ reset ();
+
+#ifdef XSDE_IOSTREAM
+ public:
+ // Parse a local file. The file is accessed with std::ifstream
+ // in binary mode. The std::ios_base::failure exception is used
+ // to report io errors (badbit and failbit) if XSDE_EXCEPTIONS
+ // is defined. Otherwise error codes are used.
+ //
+ void
+ parse (const char* file);
+
+#ifdef XSDE_STL
+ void
+ parse (const std::string& file);
+#endif
+
+ // Parse std::istream. std::ios_base::failure exception is used
+ // to report io errors (badbit and failbit) if XSDE_EXCEPTIONS
+ // is defined. Otherwise error codes are used.
+ //
+ void
+ parse (std::istream&);
+#endif
+
+ public:
+ // Parse a chunk of input. You can call this function multiple
+ // times with the last call having the last argument true.
+ //
+ void
+ parse (const void* data, size_t size, bool last);
+
+ public:
+ // Low-level Expat-specific parsing API. A typical use case
+ // would look like this (pseudo-code):
+ //
+ // XML_Parser xml_parser (XML_ParserCreateNS (0, ' '));
+ //
+ // xxx_pimpl root;
+ // document_pimpl doc (root, "root");
+ //
+ // root.pre ();
+ // doc.parse_begin (xml_parser);
+ //
+ // while (more_stuff_to_parse)
+ // {
+ // // Call XML_Parse or XML_ParseBuffer:
+ // //
+ // if (XML_Parse (...) != XML_STATUS_ERROR)
+ // break;
+ // }
+ //
+ // doc.parse_end ();
+ // result_type result (root.post_xxx ());
+ //
+ // Notes:
+ //
+ // 1. If your XML instances use XML namespaces, XML_ParserCreateNS
+ // functions should be used to create the XML parser. Space
+ // (XML_Char (' ')) should be used as a separator (the second
+ // argument to XML_ParserCreateNS).
+ //
+ // 2. If XML_Parse or XML_ParseBuffer fail, call parse_end to
+ // determine the error which is indicated either via exception
+ // or set as an error code.
+ //
+ void
+ parse_begin (XML_Parser);
+
+ void
+ parse_end ();
+
+#ifndef XSDE_EXCEPTIONS
+ public:
+ const error&
+ _error () const;
+#endif
+
+ protected:
+ void
+ set ();
+
+ void
+ clear ();
+
+ protected:
+ static void XMLCALL
+ start_element (void*, const XML_Char*, const XML_Char**);
+
+ static void XMLCALL
+ end_element (void*, const XML_Char*);
+
+ static void XMLCALL
+ characters (void*, const XML_Char*, int);
+
+#ifdef XSDE_POLYMORPHIC
+ static void XMLCALL
+ start_namespace_decl (void*, const XML_Char*, const XML_Char*);
+
+ static void XMLCALL
+ end_namespace_decl (void*, const XML_Char*);
+#endif
+
+ protected:
+ void
+ start_element_ (const XML_Char* ns_name, const XML_Char** atts);
+
+ void
+ end_element_ (const XML_Char* ns_name);
+
+ void
+ characters_ (const XML_Char* s, size_t n);
+
+#ifdef XSDE_POLYMORPHIC
+ void
+ start_namespace_decl_ (const XML_Char* prefix, const XML_Char* ns);
+
+ void
+ end_namespace_decl_ (const XML_Char* prefix);
+#endif
+
+ protected:
+ bool first_;
+ XML_Parser xml_parser_;
+ parser_auto_ptr auto_xml_parser_;
+
+ context context_;
+
+ parser_base* parser_;
+ string root_name_;
+ string root_ns_;
+
+#ifdef XSDE_POLYMORPHIC
+ bool polymorphic_;
+ string_sequence prefixes_;
+ string_sequence prefix_namespaces_;
+#endif
+
+#ifndef XSDE_EXCEPTIONS
+ error error_;
+#endif
+
+ private:
+ void
+ init_root_name (const char* ns, const char* name);
+ };
+ }
+ }
+ }
+}
+
+#include <xsde/cxx/parser/expat/document.ixx>
+
+#endif // XSDE_CXX_PARSER_EXPAT_DOCUMENT_HXX