aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBoris Kolpackov <boris@codesynthesis.com>2010-03-28 16:53:35 +0200
committerBoris Kolpackov <boris@codesynthesis.com>2010-03-28 16:53:35 +0200
commit4332a60585a14ff51bc54d29a4a81d37b3b1df81 (patch)
treefd3b807e3f5b3841371d509505a50498d21a2f99
parentc2d201480002a24c05f1f4bc934036555b79cad6 (diff)
Validate enumerations in the xsd:string parser/serializer
-rw-r--r--libxsde/xsde/cxx/parser/validating/string-common.cxx61
-rw-r--r--libxsde/xsde/cxx/parser/validating/string-common.hxx32
-rw-r--r--libxsde/xsde/cxx/parser/validating/string-stl.cxx24
-rw-r--r--libxsde/xsde/cxx/parser/validating/string.cxx24
-rw-r--r--libxsde/xsde/cxx/parser/validating/xml-schema-pskel.hxx67
-rw-r--r--libxsde/xsde/cxx/parser/validating/xml-schema-pskel.ixx52
-rw-r--r--libxsde/xsde/cxx/schema-error.cxx1
-rw-r--r--libxsde/xsde/cxx/schema-error.hxx1
-rw-r--r--libxsde/xsde/cxx/serializer/validating/string-common.cxx69
-rw-r--r--libxsde/xsde/cxx/serializer/validating/string-common.hxx35
-rw-r--r--libxsde/xsde/cxx/serializer/validating/string-stl.cxx24
-rw-r--r--libxsde/xsde/cxx/serializer/validating/string.cxx28
-rw-r--r--libxsde/xsde/cxx/serializer/validating/xml-schema-sskel.hxx67
-rw-r--r--libxsde/xsde/cxx/serializer/validating/xml-schema-sskel.ixx50
-rw-r--r--libxsde/xsde/makefile2
-rw-r--r--xsde/cxx/parser/elements.hxx102
-rw-r--r--xsde/cxx/parser/parser-header.cxx38
-rw-r--r--xsde/cxx/parser/parser-inline.cxx56
-rw-r--r--xsde/cxx/parser/parser-source.cxx31
-rw-r--r--xsde/cxx/serializer/elements.hxx104
-rw-r--r--xsde/cxx/serializer/serializer-header.cxx41
-rw-r--r--xsde/cxx/serializer/serializer-inline.cxx56
-rw-r--r--xsde/cxx/serializer/serializer-source.cxx29
23 files changed, 779 insertions, 215 deletions
diff --git a/libxsde/xsde/cxx/parser/validating/string-common.cxx b/libxsde/xsde/cxx/parser/validating/string-common.cxx
new file mode 100644
index 0000000..15956f6
--- /dev/null
+++ b/libxsde/xsde/cxx/parser/validating/string-common.cxx
@@ -0,0 +1,61 @@
+// file : xsde/cxx/parser/validating/string-common.cxx
+// author : Boris Kolpackov <boris@codesynthesis.com>
+// copyright : Copyright (c) 2005-2010 Code Synthesis Tools CC
+// license : GNU GPL v2 + exceptions; see accompanying LICENSE file
+
+#include <string.h> // strcmp
+#include <xsde/cxx/parser/validating/string-common.hxx>
+
+namespace xsde
+{
+ namespace cxx
+ {
+ namespace parser
+ {
+ namespace validating
+ {
+ void string_common::
+ validate_facets (const char* s,
+ size_t n,
+ const string_facets::facets& f,
+ context& ctx)
+ {
+ if (f.length_set_ && n != f.length_)
+ {
+ ctx.schema_error (schema_error::length_not_equal_prescribed);
+ return;
+ }
+
+ if (f.min_length_set_ && n < f.min_length_)
+ {
+ ctx.schema_error (schema_error::length_less_than_min);
+ return;
+ }
+
+ if (f.max_length_set_ && n > f.max_length_)
+ {
+ ctx.schema_error (schema_error::length_greater_than_max);
+ return;
+ }
+
+ if (f.enum_count_ != 0)
+ {
+ size_t i = 0;
+
+ for (; i < f.enum_count_; ++i)
+ {
+ if (strcmp (s, f.enum_[i]) == 0)
+ break;
+ }
+
+ if (i == f.enum_count_)
+ {
+ ctx.schema_error (schema_error::value_not_in_enumeration);
+ return;
+ }
+ }
+ }
+ }
+ }
+ }
+}
diff --git a/libxsde/xsde/cxx/parser/validating/string-common.hxx b/libxsde/xsde/cxx/parser/validating/string-common.hxx
new file mode 100644
index 0000000..52ea0c5
--- /dev/null
+++ b/libxsde/xsde/cxx/parser/validating/string-common.hxx
@@ -0,0 +1,32 @@
+// file : xsde/cxx/parser/validating/string-common.hxx
+// author : Boris Kolpackov <boris@codesynthesis.com>
+// copyright : Copyright (c) 2005-2010 Code Synthesis Tools CC
+// license : GNU GPL v2 + exceptions; see accompanying LICENSE file
+
+#ifndef XSDE_CXX_PARSER_VALIDATING_STRING_COMMON_HXX
+#define XSDE_CXX_PARSER_VALIDATING_STRING_COMMON_HXX
+
+#include <xsde/cxx/parser/validating/xml-schema-pskel.hxx>
+
+namespace xsde
+{
+ namespace cxx
+ {
+ namespace parser
+ {
+ namespace validating
+ {
+ struct string_common
+ {
+ static void
+ validate_facets (const char* s,
+ size_t n,
+ const string_facets::facets&,
+ context&);
+ };
+ }
+ }
+ }
+}
+
+#endif // XSDE_CXX_PARSER_VALIDATING_STRING_COMMON_HXX
diff --git a/libxsde/xsde/cxx/parser/validating/string-stl.cxx b/libxsde/xsde/cxx/parser/validating/string-stl.cxx
index d0d0e14..9e1ad13 100644
--- a/libxsde/xsde/cxx/parser/validating/string-stl.cxx
+++ b/libxsde/xsde/cxx/parser/validating/string-stl.cxx
@@ -4,6 +4,7 @@
// license : GNU GPL v2 + exceptions; see accompanying LICENSE file
#include <xsde/cxx/parser/validating/string-stl.hxx>
+#include <xsde/cxx/parser/validating/string-common.hxx>
namespace xsde
{
@@ -28,27 +29,8 @@ namespace xsde
void string_pimpl::
_post ()
{
- // Check facets.
- //
- const facets& f = _facets ();
-
- if (f.length_set_ && str_.size () != f.length_)
- {
- _schema_error (schema_error::length_not_equal_prescribed);
- return;
- }
-
- if (f.min_length_set_ && str_.size () < f.min_length_)
- {
- _schema_error (schema_error::length_less_than_min);
- return;
- }
-
- if (f.max_length_set_ && str_.size () > f.max_length_)
- {
- _schema_error (schema_error::length_greater_than_max);
- return;
- }
+ string_common::validate_facets (
+ str_.c_str (), str_.size (), _facets (), _context ());
}
std::string string_pimpl::
diff --git a/libxsde/xsde/cxx/parser/validating/string.cxx b/libxsde/xsde/cxx/parser/validating/string.cxx
index c40a7c9..3e29a93 100644
--- a/libxsde/xsde/cxx/parser/validating/string.cxx
+++ b/libxsde/xsde/cxx/parser/validating/string.cxx
@@ -6,6 +6,7 @@
#include <xsde/cxx/config.hxx>
#include <xsde/cxx/parser/validating/string.hxx>
+#include <xsde/cxx/parser/validating/string-common.hxx>
namespace xsde
{
@@ -40,27 +41,8 @@ namespace xsde
void string_pimpl::
_post ()
{
- // Check facets.
- //
- const facets& f = _facets ();
-
- if (f.length_set_ && str_.size () != f.length_)
- {
- _schema_error (schema_error::length_not_equal_prescribed);
- return;
- }
-
- if (f.min_length_set_ && str_.size () < f.min_length_)
- {
- _schema_error (schema_error::length_less_than_min);
- return;
- }
-
- if (f.max_length_set_ && str_.size () > f.max_length_)
- {
- _schema_error (schema_error::length_greater_than_max);
- return;
- }
+ string_common::validate_facets (
+ str_.data (), str_.size (), _facets (), _context ());
}
char* string_pimpl::
diff --git a/libxsde/xsde/cxx/parser/validating/xml-schema-pskel.hxx b/libxsde/xsde/cxx/parser/validating/xml-schema-pskel.hxx
index 1e05778..ed0ff4f 100644
--- a/libxsde/xsde/cxx/parser/validating/xml-schema-pskel.hxx
+++ b/libxsde/xsde/cxx/parser/validating/xml-schema-pskel.hxx
@@ -653,10 +653,47 @@ namespace xsde
};
+ //
// String-based types. If STL is disabled you are getting a C
// string that you have to delete with delete[].
//
- struct string_pskel: simple_content
+
+ struct string_facets
+ {
+ string_facets ();
+
+ void
+ _length_facet (size_t);
+
+ void
+ _max_length_facet (size_t);
+
+ void
+ _min_length_facet (size_t);
+
+ void
+ _enumeration_facet (const char* const*, size_t count);
+
+ public:
+ struct facets
+ {
+ size_t length_;
+ size_t min_length_;
+ size_t max_length_;
+
+ const char* const* enum_;
+ size_t enum_count_;
+
+ unsigned int length_set_ : 1;
+ unsigned int min_length_set_ : 1;
+ unsigned int max_length_set_ : 1;
+ };
+
+ protected:
+ facets facets_;
+ };
+
+ struct string_pskel: simple_content, string_facets
{
#ifdef XSDE_STL
virtual std::string
@@ -673,9 +710,8 @@ namespace xsde
_dynamic_type () const;
#endif
- string_pskel ();
-
#ifdef XSDE_REUSE_STYLE_TIEIN
+ string_pskel ();
string_pskel (string_pskel* impl, void*);
protected:
@@ -683,33 +719,8 @@ namespace xsde
#endif
// Facets.
//
- public:
- void
- _length_facet (size_t);
-
- void
- _max_length_facet (size_t);
-
- void
- _min_length_facet (size_t);
-
- protected:
- struct facets
- {
- size_t length_;
- size_t min_length_;
- size_t max_length_;
-
- unsigned int length_set_ : 1;
- unsigned int min_length_set_ : 1;
- unsigned int max_length_set_ : 1;
- };
-
const facets&
_facets () const;
-
- private:
- facets facets_;
};
struct normalized_string_pskel: simple_content
diff --git a/libxsde/xsde/cxx/parser/validating/xml-schema-pskel.ixx b/libxsde/xsde/cxx/parser/validating/xml-schema-pskel.ixx
index 3d69e15..c08fb09 100644
--- a/libxsde/xsde/cxx/parser/validating/xml-schema-pskel.ixx
+++ b/libxsde/xsde/cxx/parser/validating/xml-schema-pskel.ixx
@@ -446,51 +446,63 @@ namespace xsde
}
#endif
- // string_pskel
+ // string_facets
//
- inline string_pskel::
- string_pskel ()
+ inline string_facets::
+ string_facets ()
{
-#ifdef XSDE_REUSE_STYLE_TIEIN
- string_impl_ = 0;
-#endif
facets_.length_set_ = 0;
facets_.min_length_set_ = 0;
facets_.max_length_set_ = 0;
- }
-#ifdef XSDE_REUSE_STYLE_TIEIN
- inline string_pskel::
- string_pskel (string_pskel* impl, void*)
- : simple_content (impl, 0), string_impl_ (impl)
- {
- facets_.length_set_ = 0;
- facets_.min_length_set_ = 0;
- facets_.max_length_set_ = 0;
+ facets_.enum_ = 0;
+ facets_.enum_count_ = 0;
}
-#endif
- inline void string_pskel::
+ inline void string_facets::
_length_facet (size_t v)
{
facets_.length_ = v;
facets_.length_set_ = 1;
}
- inline void string_pskel::
+ inline void string_facets::
_max_length_facet (size_t v)
{
facets_.max_length_ = v;
facets_.max_length_set_ = 1;
}
- inline void string_pskel::
+ inline void string_facets::
_min_length_facet (size_t v)
{
facets_.min_length_ = v;
facets_.min_length_set_ = 1;
}
+ inline void string_facets::
+ _enumeration_facet (const char* const* e, size_t count)
+ {
+ facets_.enum_ = e;
+ facets_.enum_count_ = count;
+ }
+
+ // string_pskel
+ //
+#ifdef XSDE_REUSE_STYLE_TIEIN
+ inline string_pskel::
+ string_pskel ()
+ : string_impl_ (0)
+ {
+ }
+
+ inline string_pskel::
+ string_pskel (string_pskel* impl, void*)
+ : simple_content (impl, 0), string_impl_ (impl)
+ {
+ }
+#endif
+
inline const string_pskel::facets& string_pskel::
_facets () const
{
@@ -499,7 +511,7 @@ namespace xsde
return static_cast<const string_pskel&> (*parent_).facets_;
else
#endif
- return facets_;
+ return facets_;
}
// normalized_string_pskel
diff --git a/libxsde/xsde/cxx/schema-error.cxx b/libxsde/xsde/cxx/schema-error.cxx
index c347fa1..a37ea28 100644
--- a/libxsde/xsde/cxx/schema-error.cxx
+++ b/libxsde/xsde/cxx/schema-error.cxx
@@ -58,6 +58,7 @@ namespace xsde
"invalid duration value",
"value is greater than maximum allowed",
"value is less than minimum allowed",
+ "value is not in enumeration",
"length is greater than maximum allowed",
"length is less than minimum allowed",
"length is not equal to prescribed length",
diff --git a/libxsde/xsde/cxx/schema-error.hxx b/libxsde/xsde/cxx/schema-error.hxx
index 8569e49..f442bf6 100644
--- a/libxsde/xsde/cxx/schema-error.hxx
+++ b/libxsde/xsde/cxx/schema-error.hxx
@@ -61,6 +61,7 @@ namespace xsde
invalid_duration_value,
value_greater_than_max,
value_less_than_min,
+ value_not_in_enumeration,
length_greater_than_max,
length_less_than_min,
length_not_equal_prescribed,
diff --git a/libxsde/xsde/cxx/serializer/validating/string-common.cxx b/libxsde/xsde/cxx/serializer/validating/string-common.cxx
new file mode 100644
index 0000000..20a1b34
--- /dev/null
+++ b/libxsde/xsde/cxx/serializer/validating/string-common.cxx
@@ -0,0 +1,69 @@
+// file : xsde/cxx/serializer/validating/string-common.cxx
+// author : Boris Kolpackov <boris@codesynthesis.com>
+// copyright : Copyright (c) 2005-2010 Code Synthesis Tools CC
+// license : GNU GPL v2 + exceptions; see accompanying LICENSE file
+
+#include <string.h> // strlen, strcmp
+#include <xsde/cxx/serializer/validating/string-common.hxx>
+
+namespace xsde
+{
+ namespace cxx
+ {
+ namespace serializer
+ {
+ namespace validating
+ {
+ void string_common::
+ validate_facets (const char* s,
+#ifdef XSDE_STL
+ size_t n,
+#endif
+ const string_facets::facets& f,
+ context& ctx)
+ {
+#ifndef XSDE_STL
+ size_t n;
+ if (f.length_set_ || f.min_length_set_ || f.max_length_set_)
+ n = strlen (s);
+#endif
+
+ if (f.length_set_ && n != f.length_)
+ {
+ ctx.schema_error (schema_error::length_not_equal_prescribed);
+ return;
+ }
+
+ if (f.min_length_set_ && n < f.min_length_)
+ {
+ ctx.schema_error (schema_error::length_less_than_min);
+ return;
+ }
+
+ if (f.max_length_set_ && n > f.max_length_)
+ {
+ ctx.schema_error (schema_error::length_greater_than_max);
+ return;
+ }
+
+ if (f.enum_count_ != 0)
+ {
+ size_t i = 0;
+
+ for (; i < f.enum_count_; ++i)
+ {
+ if (strcmp (s, f.enum_[i]) == 0)
+ break;
+ }
+
+ if (i == f.enum_count_)
+ {
+ ctx.schema_error (schema_error::value_not_in_enumeration);
+ return;
+ }
+ }
+ }
+ }
+ }
+ }
+}
diff --git a/libxsde/xsde/cxx/serializer/validating/string-common.hxx b/libxsde/xsde/cxx/serializer/validating/string-common.hxx
new file mode 100644
index 0000000..d7f221d
--- /dev/null
+++ b/libxsde/xsde/cxx/serializer/validating/string-common.hxx
@@ -0,0 +1,35 @@
+// file : xsde/cxx/serializer/validating/string-common.hxx
+// author : Boris Kolpackov <boris@codesynthesis.com>
+// copyright : Copyright (c) 2005-2010 Code Synthesis Tools CC
+// license : GNU GPL v2 + exceptions; see accompanying LICENSE file
+
+#ifndef XSDE_CXX_SERIALIZER_VALIDATING_STRING_COMMON_HXX
+#define XSDE_CXX_SERIALIZER_VALIDATING_STRING_COMMON_HXX
+
+#include <xsde/cxx/config.hxx>
+#include <xsde/cxx/serializer/validating/xml-schema-sskel.hxx>
+
+namespace xsde
+{
+ namespace cxx
+ {
+ namespace serializer
+ {
+ namespace validating
+ {
+ struct string_common
+ {
+ static void
+ validate_facets (const char* s,
+#ifdef XSDE_STL
+ size_t n,
+#endif
+ const string_facets::facets&,
+ context&);
+ };
+ }
+ }
+ }
+}
+
+#endif // XSDE_CXX_SERIALIZER_VALIDATING_STRING_COMMON_HXX
diff --git a/libxsde/xsde/cxx/serializer/validating/string-stl.cxx b/libxsde/xsde/cxx/serializer/validating/string-stl.cxx
index 1e9a37b..ef13746 100644
--- a/libxsde/xsde/cxx/serializer/validating/string-stl.cxx
+++ b/libxsde/xsde/cxx/serializer/validating/string-stl.cxx
@@ -4,6 +4,7 @@
// license : GNU GPL v2 + exceptions; see accompanying LICENSE file
#include <xsde/cxx/serializer/validating/string-stl.hxx>
+#include <xsde/cxx/serializer/validating/string-common.hxx>
namespace xsde
{
@@ -22,27 +23,8 @@ namespace xsde
void string_simpl::
_serialize_content ()
{
- // Check facets.
- //
- const facets& f = _facets ();
-
- if (f.length_set_ && value_.size () != f.length_)
- {
- _schema_error (schema_error::length_not_equal_prescribed);
- return;
- }
-
- if (f.min_length_set_ && value_.size () < f.min_length_)
- {
- _schema_error (schema_error::length_less_than_min);
- return;
- }
-
- if (f.max_length_set_ && value_.size () > f.max_length_)
- {
- _schema_error (schema_error::length_greater_than_max);
- return;
- }
+ string_common::validate_facets (
+ value_.c_str (), value_.size (), _facets (), _context ());
// Make sure we don't hold any references to the string.
//
diff --git a/libxsde/xsde/cxx/serializer/validating/string.cxx b/libxsde/xsde/cxx/serializer/validating/string.cxx
index 0def094..befe450 100644
--- a/libxsde/xsde/cxx/serializer/validating/string.cxx
+++ b/libxsde/xsde/cxx/serializer/validating/string.cxx
@@ -3,8 +3,8 @@
// copyright : Copyright (c) 2005-2010 Code Synthesis Tools CC
// license : GNU GPL v2 + exceptions; see accompanying LICENSE file
-#include <string.h> // strlen
#include <xsde/cxx/serializer/validating/string.hxx>
+#include <xsde/cxx/serializer/validating/string-common.hxx>
namespace xsde
{
@@ -30,31 +30,7 @@ namespace xsde
void string_simpl::
_serialize_content ()
{
- // Check facets.
- //
- if (length_set_ || min_length_set_ || max_length_set_)
- {
- size_t n = strlen (value_);
- const facets& f = _facets ();
-
- if (f.length_set_ && n != f.length_)
- {
- _schema_error (schema_error::length_not_equal_prescribed);
- return;
- }
-
- if (f.min_length_set_ && n < f.min_length_)
- {
- _schema_error (schema_error::length_less_than_min);
- return;
- }
-
- if (f.max_length_set_ && n > f.max_length_)
- {
- _schema_error (schema_error::length_greater_than_max);
- return;
- }
- }
+ string_common::validate_facets (value_, _facets (), _context ());
_characters (value_);
diff --git a/libxsde/xsde/cxx/serializer/validating/xml-schema-sskel.hxx b/libxsde/xsde/cxx/serializer/validating/xml-schema-sskel.hxx
index 940f256..c206e78 100644
--- a/libxsde/xsde/cxx/serializer/validating/xml-schema-sskel.hxx
+++ b/libxsde/xsde/cxx/serializer/validating/xml-schema-sskel.hxx
@@ -636,9 +636,46 @@ namespace xsde
#endif
};
+ //
// String-based types.
//
- struct string_sskel: simple_content
+
+ struct string_facets
+ {
+ string_facets ();
+
+ void
+ _length_facet (size_t);
+
+ void
+ _max_length_facet (size_t);
+
+ void
+ _min_length_facet (size_t);
+
+ void
+ _enumeration_facet (const char* const*, size_t count);
+
+ public:
+ struct facets
+ {
+ size_t length_;
+ size_t min_length_;
+ size_t max_length_;
+
+ const char* const* enum_;
+ size_t enum_count_;
+
+ unsigned int length_set_ : 1;
+ unsigned int min_length_set_ : 1;
+ unsigned int max_length_set_ : 1;
+ };
+
+ protected:
+ facets facets_;
+ };
+
+ struct string_sskel: simple_content, string_facets
{
virtual void
#ifdef XSDE_STL
@@ -655,9 +692,8 @@ namespace xsde
_dynamic_type () const;
#endif
- string_sskel ();
-
#ifdef XSDE_REUSE_STYLE_TIEIN
+ string_sskel ();
string_sskel (string_sskel* impl, void*);
protected:
@@ -665,33 +701,8 @@ namespace xsde
#endif
// Facets.
//
- public:
- void
- _length_facet (size_t);
-
- void
- _max_length_facet (size_t);
-
- void
- _min_length_facet (size_t);
-
- protected:
- struct facets
- {
- size_t length_;
- size_t min_length_;
- size_t max_length_;
-
- unsigned int length_set_ : 1;
- unsigned int min_length_set_ : 1;
- unsigned int max_length_set_ : 1;
- };
-
const facets&
_facets () const;
-
- private:
- facets facets_;
};
#ifdef XSDE_REUSE_STYLE_MIXIN
diff --git a/libxsde/xsde/cxx/serializer/validating/xml-schema-sskel.ixx b/libxsde/xsde/cxx/serializer/validating/xml-schema-sskel.ixx
index fd84bf0..b2eb40f 100644
--- a/libxsde/xsde/cxx/serializer/validating/xml-schema-sskel.ixx
+++ b/libxsde/xsde/cxx/serializer/validating/xml-schema-sskel.ixx
@@ -447,51 +447,63 @@ namespace xsde
}
#endif
- // string_sskel
+ // string_facets
//
- inline string_sskel::
- string_sskel ()
+ inline string_facets::
+ string_facets ()
{
-#ifdef XSDE_REUSE_STYLE_TIEIN
- string_impl_ = 0;
-#endif
facets_.length_set_ = 0;
facets_.min_length_set_ = 0;
facets_.max_length_set_ = 0;
- }
-#ifdef XSDE_REUSE_STYLE_TIEIN
- inline string_sskel::
- string_sskel (string_sskel* impl, void*)
- : simple_content (impl, 0), string_impl_ (impl)
- {
- facets_.length_set_ = 0;
- facets_.min_length_set_ = 0;
- facets_.max_length_set_ = 0;
+ facets_.enum_ = 0;
+ facets_.enum_count_ = 0;
}
-#endif
- inline void string_sskel::
+ inline void string_facets::
_length_facet (size_t v)
{
facets_.length_ = v;
facets_.length_set_ = 1;
}
- inline void string_sskel::
+ inline void string_facets::
_max_length_facet (size_t v)
{
facets_.max_length_ = v;
facets_.max_length_set_ = 1;
}
- inline void string_sskel::
+ inline void string_facets::
_min_length_facet (size_t v)
{
facets_.min_length_ = v;
facets_.min_length_set_ = 1;
}
+ inline void string_facets::
+ _enumeration_facet (const char* const* e, size_t count)
+ {
+ facets_.enum_ = e;
+ facets_.enum_count_ = count;
+ }
+
+ // string_sskel
+ //
+#ifdef XSDE_REUSE_STYLE_TIEIN
+ inline string_sskel::
+ string_sskel ()
+ : string_impl_ (0)
+ {
+ }
+
+ inline string_sskel::
+ string_sskel (string_sskel* impl, void*)
+ : simple_content (impl, 0), string_impl_ (impl)
+ {
+ }
+#endif
+
inline const string_sskel::facets& string_sskel::
_facets () const
{
diff --git a/libxsde/xsde/makefile b/libxsde/xsde/makefile
index 3a0465c..fc1355d 100644
--- a/libxsde/xsde/makefile
+++ b/libxsde/xsde/makefile
@@ -103,6 +103,7 @@ ifeq ($(xsde_parser_validation),y)
cxx_tun += \
cxx/parser/validating/parser.cxx \
cxx/parser/validating/time-zone.cxx \
+cxx/parser/validating/string-common.cxx \
cxx/parser/validating/xml-schema-pskel.cxx
ifeq ($(xsde_polymorphic),y)
@@ -296,6 +297,7 @@ ifeq ($(xsde_serializer_validation),y)
cxx_tun += \
cxx/serializer/validating/serializer.cxx \
cxx/serializer/validating/time-zone.cxx \
+cxx/serializer/validating/string-common.cxx \
cxx/serializer/validating/xml-schema-sskel.cxx
ifeq ($(xsde_polymorphic),y)
diff --git a/xsde/cxx/parser/elements.hxx b/xsde/cxx/parser/elements.hxx
index 954b13b..f603400 100644
--- a/xsde/cxx/parser/elements.hxx
+++ b/xsde/cxx/parser/elements.hxx
@@ -191,6 +191,108 @@ namespace CXX
String parser_map_;
};
+ // Check whether this is a string-based type (including ID, IDFER,
+ // anyURI, and ENTITY).
+ //
+ struct StringBasedType: Traversal::Complex,
+ Traversal::Fundamental::String,
+ Traversal::Fundamental::NormalizedString,
+ Traversal::Fundamental::Token,
+ Traversal::Fundamental::Name,
+ Traversal::Fundamental::NameToken,
+ Traversal::Fundamental::NCName,
+ Traversal::Fundamental::Language,
+ Traversal::Fundamental::Id,
+ Traversal::Fundamental::IdRef,
+ Traversal::Fundamental::AnyURI,
+ Traversal::Fundamental::Entity
+
+ {
+ StringBasedType (Boolean& r)
+ : r_ (r)
+ {
+ *this >> inherits_ >> *this;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Complex& c)
+ {
+ inherits (c, inherits_);
+ }
+
+ // Strings.
+ //
+ virtual Void
+ traverse (SemanticGraph::Fundamental::String&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::NormalizedString&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::Token&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::NameToken&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::Name&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::NCName&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::Language&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::Id&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::IdRef&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::AnyURI&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::Entity&)
+ {
+ r_ = true;
+ }
+
+ private:
+ Boolean& r_;
+ Traversal::Inherits inherits_;
+ };
+
//
//
struct RequiredAttributeTest: Traversal::Attribute
diff --git a/xsde/cxx/parser/parser-header.cxx b/xsde/cxx/parser/parser-header.cxx
index 34f2119..5bc9cb7 100644
--- a/xsde/cxx/parser/parser-header.cxx
+++ b/xsde/cxx/parser/parser-header.cxx
@@ -28,6 +28,13 @@ namespace CXX
SemanticGraph::Type& base (e.inherits ().base ());
String fq_base (fq_name (base));
+ Boolean facets (false); // Whether we need to set facets.
+ if (validation)
+ {
+ StringBasedType t (facets);
+ t.dispatch (e);
+ }
+
os << "class " << name << ": public " <<
(mixin ? "virtual " : "") << fq_base
<< "{"
@@ -60,15 +67,22 @@ namespace CXX
<< "_dynamic_type () const;";
}
- if (tiein)
+ if (facets || tiein)
{
os << endl
<< "// Constructor." << endl
- << "//" << endl
- << name << " (" << fq_base << "* tiein);"
- << endl;
+ << "//" << endl;
- os << "// Implementation details." << endl
+ if (tiein)
+ os << name << " (" << fq_base << "* tiein);";
+ else
+ os << name << " ();";
+ }
+
+ if (tiein)
+ {
+ os << endl
+ << "// Implementation details." << endl
<< "//" << endl;
// If our base has pure virtual post, override it here.
@@ -87,6 +101,20 @@ namespace CXX
<< name << " (" << name << "*, void*);";
}
+ if (facets)
+ {
+ UnsignedLong enum_count (0);
+
+ for (Type::NamesIterator i (e.names_begin ()), end (e.names_end ());
+ i != end; ++i)
+ ++enum_count;
+
+ os << endl
+ << "protected:" << endl
+ << "static const char* const _xsde_" << name << "_enums_[" <<
+ enum_count << "UL];";
+ }
+
os << "};";
}
};
diff --git a/xsde/cxx/parser/parser-inline.cxx b/xsde/cxx/parser/parser-inline.cxx
index def8434..528ff86 100644
--- a/xsde/cxx/parser/parser-inline.cxx
+++ b/xsde/cxx/parser/parser-inline.cxx
@@ -24,9 +24,41 @@ namespace CXX
virtual Void
traverse (Type& e)
{
+ String const& name (ename (e));
+
+ Boolean facets (false); // Whether we need to set facets.
+ if (validation)
+ {
+ StringBasedType t (facets);
+ t.dispatch (e);
+ }
+
+ UnsignedLong enum_count (0);
+ if (facets)
+ {
+ for (Type::NamesIterator i (e.names_begin ()), end (e.names_end ());
+ i != end; ++i)
+ ++enum_count;
+ }
+
+ if (facets || tiein)
+ os << "// " << name << endl
+ << "//" << endl
+ << endl;
+
+ if (facets && !tiein)
+ {
+ os << inl
+ << name << "::" << endl
+ << name << " ()" << endl
+ << "{"
+ << "this->_enumeration_facet (_xsde_" << name << "_enums_, " <<
+ enum_count << "UL);"
+ << "}";
+ }
+
if (tiein)
{
- String const& name (ename (e));
String const& impl (etiein (e));
// We have to use "real" (non-typedef) base name in base
@@ -36,25 +68,31 @@ namespace CXX
String fq_base (fq_name (base));
String real_fq_base (real_fq_name (base));
- os << "// " << name << endl
- << "//" << endl
- << endl;
-
os << inl
<< name << "::" << endl
<< name << " (" << fq_base << "* tiein)" << endl
<< ": " << real_fq_base << " (tiein, 0)," << endl
<< " " << impl << " (0)"
- << "{"
- << "}";
+ << "{";
+
+ if (facets)
+ os << "this->_enumeration_facet (_xsde_" << name <<
+ "_enums_, " << enum_count << "UL);";
+
+ os << "}";
os << inl
<< name << "::" << endl
<< name << " (" << name << "* impl, void*)" << endl
<< ": " << real_fq_base << " (impl, 0)," << endl
<< " " << impl << " (impl)"
- << "{"
- << "}";
+ << "{";
+
+ if (facets)
+ os << "this->_enumeration_facet (_xsde_" << name <<
+ "_enums_, " << enum_count << "UL);";
+
+ os << "}";
}
}
};
diff --git a/xsde/cxx/parser/parser-source.cxx b/xsde/cxx/parser/parser-source.cxx
index 83b79f8..f4da879 100644
--- a/xsde/cxx/parser/parser-source.cxx
+++ b/xsde/cxx/parser/parser-source.cxx
@@ -5,6 +5,8 @@
#include <cxx/parser/parser-source.hxx>
+#include <cult/containers/set.hxx>
+
#include <xsd-frontend/semantic-graph.hxx>
#include <xsd-frontend/traversal.hxx>
@@ -34,7 +36,14 @@ namespace CXX
base.inherits_p () &&
base_ret == ret_type (base.inherits ().base ()));
- if (same || ret == L"void" || poly_code ||
+ Boolean facets (false); // Whether we need to set facets.
+ if (validation)
+ {
+ StringBasedType t (facets);
+ t.dispatch (e);
+ }
+
+ if (facets || same || ret == L"void" || poly_code ||
(tiein && !(base_same || base_ret == L"void")))
{
os << "// " << name << endl
@@ -145,6 +154,26 @@ namespace CXX
<< "return this->" << impl << "->" << base_post << " ();"
<< "}";
}
+
+ if (facets)
+ {
+ typedef Cult::Containers::Set<String> Enums;
+ Enums enums;
+
+ for (Type::NamesIterator i (e.names_begin ()),
+ end (e.names_end ()); i != end; ++i)
+ enums.insert (i->name ());
+
+ os << "const char* const " << name << "::" << "_xsde_" << name <<
+ "_enums_[" << enums.size () << "UL] = "
+ << "{";
+
+ for (Enums::Iterator b (enums.begin ()), i (b), end (enums.end ());
+ i != end; ++i)
+ os << (i != b ? ",\n" : "") << strlit (*i);
+
+ os << "};";
+ }
}
};
diff --git a/xsde/cxx/serializer/elements.hxx b/xsde/cxx/serializer/elements.hxx
index 50a54eb..470d6c4 100644
--- a/xsde/cxx/serializer/elements.hxx
+++ b/xsde/cxx/serializer/elements.hxx
@@ -203,6 +203,110 @@ namespace CXX
String serializer_map_;
};
+
+ // Check whether this is a string-based type (including ID, IDFER,
+ // anyURI, and ENTITY).
+ //
+ struct StringBasedType: Traversal::Complex,
+ Traversal::Fundamental::String,
+ Traversal::Fundamental::NormalizedString,
+ Traversal::Fundamental::Token,
+ Traversal::Fundamental::Name,
+ Traversal::Fundamental::NameToken,
+ Traversal::Fundamental::NCName,
+ Traversal::Fundamental::Language,
+ Traversal::Fundamental::Id,
+ Traversal::Fundamental::IdRef,
+ Traversal::Fundamental::AnyURI,
+ Traversal::Fundamental::Entity
+
+ {
+ StringBasedType (Boolean& r)
+ : r_ (r)
+ {
+ *this >> inherits_ >> *this;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Complex& c)
+ {
+ inherits (c, inherits_);
+ }
+
+ // Strings.
+ //
+ virtual Void
+ traverse (SemanticGraph::Fundamental::String&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::NormalizedString&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::Token&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::NameToken&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::Name&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::NCName&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::Language&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::Id&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::IdRef&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::AnyURI&)
+ {
+ r_ = true;
+ }
+
+ virtual Void
+ traverse (SemanticGraph::Fundamental::Entity&)
+ {
+ r_ = true;
+ }
+
+ private:
+ Boolean& r_;
+ Traversal::Inherits inherits_;
+ };
+
+
//
//
struct RequiredAttributeTest: Traversal::Attribute
diff --git a/xsde/cxx/serializer/serializer-header.cxx b/xsde/cxx/serializer/serializer-header.cxx
index 5459b51..b432f15 100644
--- a/xsde/cxx/serializer/serializer-header.cxx
+++ b/xsde/cxx/serializer/serializer-header.cxx
@@ -275,6 +275,13 @@ namespace CXX
SemanticGraph::Type& base (e.inherits ().base ());
String fq_base (fq_name (base));
+ Boolean facets (false); // Whether we need to set facets.
+ if (validation)
+ {
+ StringBasedType t (facets);
+ t.dispatch (e);
+ }
+
os << "class " << name << ": public " <<
(mixin ? "virtual " : "") << fq_base
<< "{"
@@ -328,15 +335,22 @@ namespace CXX
<< "_dynamic_type () const;";
}
- if (tiein)
+ if (facets || tiein)
{
os << endl
<< "// Constructor." << endl
- << "//" << endl
- << name << " (" << fq_base << "* tiein);"
- << endl;
+ << "//" << endl;
- os << "// Implementation details." << endl
+ if (tiein)
+ os << name << " (" << fq_base << "* tiein);";
+ else
+ os << name << " ();";
+ }
+
+ if (tiein)
+ {
+ os << endl
+ << "// Implementation details." << endl
<< "//" << endl;
// If our base has pure virtual functions, override them here.
@@ -345,8 +359,21 @@ namespace CXX
os << "protected:" << endl
<< name << "* " << etiein (e) << ";"
- << name << " (" << name << "*, void*);"
- << endl;
+ << name << " (" << name << "*, void*);";
+ }
+
+ if (facets)
+ {
+ UnsignedLong enum_count (0);
+
+ for (Type::NamesIterator i (e.names_begin ()), end (e.names_end ());
+ i != end; ++i)
+ ++enum_count;
+
+ os << endl
+ << "protected:" << endl
+ << "static const char* const _xsde_" << name << "_enums_[" <<
+ enum_count << "UL];";
}
os << "};";
diff --git a/xsde/cxx/serializer/serializer-inline.cxx b/xsde/cxx/serializer/serializer-inline.cxx
index 3ff9bab..e14680e 100644
--- a/xsde/cxx/serializer/serializer-inline.cxx
+++ b/xsde/cxx/serializer/serializer-inline.cxx
@@ -24,9 +24,41 @@ namespace CXX
virtual Void
traverse (Type& e)
{
+ String const& name (ename (e));
+
+ Boolean facets (false); // Whether we need to set facets.
+ if (validation)
+ {
+ StringBasedType t (facets);
+ t.dispatch (e);
+ }
+
+ UnsignedLong enum_count (0);
+ if (facets)
+ {
+ for (Type::NamesIterator i (e.names_begin ()), end (e.names_end ());
+ i != end; ++i)
+ ++enum_count;
+ }
+
+ if (facets || tiein)
+ os << "// " << name << endl
+ << "//" << endl
+ << endl;
+
+ if (facets && !tiein)
+ {
+ os << inl
+ << name << "::" << endl
+ << name << " ()" << endl
+ << "{"
+ << "this->_enumeration_facet (_xsde_" << name << "_enums_, " <<
+ enum_count << "UL);"
+ << "}";
+ }
+
if (tiein)
{
- String const& name (ename (e));
String const& impl (etiein (e));
// We have to use "real" (non-typedef) base name in base
@@ -36,25 +68,31 @@ namespace CXX
String fq_base (fq_name (base));
String real_fq_base (real_fq_name (base));
- os << "// " << name << endl
- << "//" << endl
- << endl;
-
os << inl
<< name << "::" << endl
<< name << " (" << fq_base << "* tiein)" << endl
<< ": " << real_fq_base << " (tiein, 0)," << endl
<< " " << impl << " (0)"
- << "{"
- << "}";
+ << "{";
+
+ if (facets)
+ os << "this->_enumeration_facet (_xsde_" << name <<
+ "_enums_, " << enum_count << "UL);";
+
+ os << "}";
os << inl
<< name << "::" << endl
<< name << " (" << name << "* impl, void*)" << endl
<< ": " << real_fq_base << " (impl, 0)," << endl
<< " " << impl << " (impl)"
- << "{"
- << "}";
+ << "{";
+
+ if (facets)
+ os << "this->_enumeration_facet (_xsde_" << name <<
+ "_enums_, " << enum_count << "UL);";
+
+ os << "}";
}
}
};
diff --git a/xsde/cxx/serializer/serializer-source.cxx b/xsde/cxx/serializer/serializer-source.cxx
index 509acf4..e4fd239 100644
--- a/xsde/cxx/serializer/serializer-source.cxx
+++ b/xsde/cxx/serializer/serializer-source.cxx
@@ -5,6 +5,8 @@
#include <cxx/serializer/serializer-source.hxx>
+#include <cult/containers/set.hxx>
+
#include <xsd-frontend/semantic-graph.hxx>
#include <xsd-frontend/traversal.hxx>
@@ -382,6 +384,13 @@ namespace CXX
String const& arg (arg_type (e));
SemanticGraph::Type& base (e.inherits ().base ());
+ Boolean facets (false); // Whether we need to set facets.
+ if (validation)
+ {
+ StringBasedType t (facets);
+ t.dispatch (e);
+ }
+
os << "// " << name << endl
<< "//" << endl
<< endl;
@@ -470,6 +479,26 @@ namespace CXX
BaseOverride t (*this, name);
t.dispatch (base);
}
+
+ if (facets)
+ {
+ typedef Cult::Containers::Set<String> Enums;
+ Enums enums;
+
+ for (Type::NamesIterator i (e.names_begin ()),
+ end (e.names_end ()); i != end; ++i)
+ enums.insert (i->name ());
+
+ os << "const char* const " << name << "::" << "_xsde_" << name <<
+ "_enums_[" << enums.size () << "UL] = "
+ << "{";
+
+ for (Enums::Iterator b (enums.begin ()), i (b), end (enums.end ());
+ i != end; ++i)
+ os << (i != b ? ",\n" : "") << strlit (*i);
+
+ os << "};";
+ }
}
};