/* Serializable.c generated by valac 0.44.3, the Vala compiler
 * generated from Serializable.vala, do not modify */

/* -*- Mode: vala; indent-tabs-mode: nil; c-basic-offset: 2; tab-width: 2 -*- */
/* Serializable.vala
 *
 * Copyright (C) 2013-2015  Daniel Espinosa <esodan@gmail.com>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.

 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, see <http://www.gnu.org/licenses/>.
 *
 * Authors:
 *      Daniel Espinosa <esodan@gmail.com>
 */

#include <glib-object.h>
#include <glib.h>
#include <stdlib.h>
#include <string.h>
#include <gee.h>
#include <gio/gio.h>
#include <float.h>
#include <math.h>
#include <glib/gi18n-lib.h>

#define GXML_TYPE_SERIALIZABLE (gxml_serializable_get_type ())
#define GXML_SERIALIZABLE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GXML_TYPE_SERIALIZABLE, GXmlSerializable))
#define GXML_IS_SERIALIZABLE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GXML_TYPE_SERIALIZABLE))
#define GXML_SERIALIZABLE_GET_INTERFACE(obj) (G_TYPE_INSTANCE_GET_INTERFACE ((obj), GXML_TYPE_SERIALIZABLE, GXmlSerializableIface))

typedef struct _GXmlSerializable GXmlSerializable;
typedef struct _GXmlSerializableIface GXmlSerializableIface;

#define GXML_TYPE_NODE (gxml_node_get_type ())
#define GXML_NODE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GXML_TYPE_NODE, GXmlNode))
#define GXML_IS_NODE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GXML_TYPE_NODE))
#define GXML_NODE_GET_INTERFACE(obj) (G_TYPE_INSTANCE_GET_INTERFACE ((obj), GXML_TYPE_NODE, GXmlNodeIface))

typedef struct _GXmlNode GXmlNode;
typedef struct _GXmlNodeIface GXmlNodeIface;

#define GXML_TYPE_ELEMENT_LIST (gxml_element_list_get_type ())
#define GXML_ELEMENT_LIST(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GXML_TYPE_ELEMENT_LIST, GXmlElementList))
#define GXML_ELEMENT_LIST_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GXML_TYPE_ELEMENT_LIST, GXmlElementListClass))
#define GXML_IS_ELEMENT_LIST(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GXML_TYPE_ELEMENT_LIST))
#define GXML_IS_ELEMENT_LIST_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GXML_TYPE_ELEMENT_LIST))
#define GXML_ELEMENT_LIST_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GXML_TYPE_ELEMENT_LIST, GXmlElementListClass))

typedef struct _GXmlElementList GXmlElementList;
typedef struct _GXmlElementListClass GXmlElementListClass;

#define GXML_TYPE_NAMESPACE (gxml_namespace_get_type ())
#define GXML_NAMESPACE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GXML_TYPE_NAMESPACE, GXmlNamespace))
#define GXML_IS_NAMESPACE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GXML_TYPE_NAMESPACE))
#define GXML_NAMESPACE_GET_INTERFACE(obj) (G_TYPE_INSTANCE_GET_INTERFACE ((obj), GXML_TYPE_NAMESPACE, GXmlNamespaceIface))

typedef struct _GXmlNamespace GXmlNamespace;
typedef struct _GXmlNamespaceIface GXmlNamespaceIface;
typedef enum  {
	GXML_NODE_TYPE_INVALID = 0,
	GXML_NODE_TYPE_ELEMENT = 1,
	GXML_NODE_TYPE_ATTRIBUTE,
	GXML_NODE_TYPE_TEXT,
	GXML_NODE_TYPE_CDATA_SECTION,
	GXML_NODE_TYPE_ENTITY_REFERENCE,
	GXML_NODE_TYPE_ENTITY,
	GXML_NODE_TYPE_PROCESSING_INSTRUCTION,
	GXML_NODE_TYPE_COMMENT,
	GXML_NODE_TYPE_DOCUMENT,
	GXML_NODE_TYPE_DOCUMENT_TYPE,
	GXML_NODE_TYPE_DOCUMENT_FRAGMENT,
	GXML_NODE_TYPE_NOTATION
} GXmlNodeType;

#define GXML_TYPE_NODE_TYPE (gxml_node_type_get_type ())

#define GXML_TYPE_DOCUMENT (gxml_document_get_type ())
#define GXML_DOCUMENT(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GXML_TYPE_DOCUMENT, GXmlDocument))
#define GXML_IS_DOCUMENT(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GXML_TYPE_DOCUMENT))
#define GXML_DOCUMENT_GET_INTERFACE(obj) (G_TYPE_INSTANCE_GET_INTERFACE ((obj), GXML_TYPE_DOCUMENT, GXmlDocumentIface))

typedef struct _GXmlDocument GXmlDocument;
typedef struct _GXmlDocumentIface GXmlDocumentIface;

#define GXML_TYPE_ATTRIBUTE (gxml_attribute_get_type ())
#define GXML_ATTRIBUTE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GXML_TYPE_ATTRIBUTE, GXmlAttribute))
#define GXML_IS_ATTRIBUTE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GXML_TYPE_ATTRIBUTE))
#define GXML_ATTRIBUTE_GET_INTERFACE(obj) (G_TYPE_INSTANCE_GET_INTERFACE ((obj), GXML_TYPE_ATTRIBUTE, GXmlAttributeIface))

typedef struct _GXmlAttribute GXmlAttribute;
typedef struct _GXmlAttributeIface GXmlAttributeIface;
#define _g_free0(var) (var = (g_free (var), NULL))
#define _g_param_spec_unref0(var) ((var == NULL) ? NULL : (var = (g_param_spec_unref (var), NULL)))
#define _g_hash_table_unref0(var) ((var == NULL) ? NULL : (var = (g_hash_table_unref (var), NULL)))
enum  {
	GXML_SERIALIZABLE_SERIALIZE_UNKNOWN_PROPERTY_SIGNAL,
	GXML_SERIALIZABLE_SERIALIZE_UNKNOWN_PROPERTY_TYPE_SIGNAL,
	GXML_SERIALIZABLE_DESERIALIZE_UNKNOWN_PROPERTY_SIGNAL,
	GXML_SERIALIZABLE_DESERIALIZE_UNKNOWN_PROPERTY_TYPE_SIGNAL,
	GXML_SERIALIZABLE_NUM_SIGNALS
};
static guint gxml_serializable_signals[GXML_SERIALIZABLE_NUM_SIGNALS] = {0};

struct _GXmlNamespaceIface {
	GTypeInterface parent_iface;
	gchar* (*get_uri) (GXmlNamespace* self);
	gchar* (*get_prefix) (GXmlNamespace* self);
};

struct _GXmlDocumentIface {
	GTypeInterface parent_iface;
	GXmlNode* (*create_element) (GXmlDocument* self, const gchar* name, GError** error);
	GXmlNode* (*create_text) (GXmlDocument* self, const gchar* text);
	GXmlNode* (*create_comment) (GXmlDocument* self, const gchar* text);
	GXmlNode* (*create_cdata) (GXmlDocument* self, const gchar* text);
	GXmlNode* (*create_pi) (GXmlDocument* self, const gchar* target, const gchar* data);
	gboolean (*save) (GXmlDocument* self, GCancellable* cancellable, GError** error);
	gboolean (*save_as) (GXmlDocument* self, GFile* f, GCancellable* cancellable, GError** error);
	gboolean (*get_indent) (GXmlDocument* self);
	void (*set_indent) (GXmlDocument* self, gboolean value);
	gboolean (*get_ns_top) (GXmlDocument* self);
	void (*set_ns_top) (GXmlDocument* self, gboolean value);
	gboolean (*get_prefix_default_ns) (GXmlDocument* self);
	void (*set_prefix_default_ns) (GXmlDocument* self, gboolean value);
	gboolean (*get_backup) (GXmlDocument* self);
	void (*set_backup) (GXmlDocument* self, gboolean value);
	GXmlNode* (*get_root) (GXmlDocument* self);
	GFile* (*get_file) (GXmlDocument* self);
	void (*set_file) (GXmlDocument* self, GFile* value);
};

struct _GXmlNodeIface {
	GTypeInterface parent_iface;
	GXmlNode* (*get) (GXmlNode* self, const gchar* key);
	GXmlElementList* (*get_elements_by_property_value) (GXmlNode* self, const gchar* property, const gchar* value);
	GXmlElementList* (*get_elements_by_name) (GXmlNode* self, const gchar* name);
	GXmlElementList* (*get_elements_by_name_ns) (GXmlNode* self, const gchar* name, const gchar* ns);
	gchar* (*to_string) (GXmlNode* self);
	gboolean (*set_namespace) (GXmlNode* self, const gchar* uri, const gchar* prefix);
	gchar* (*ns_prefix) (GXmlNode* self);
	gchar* (*ns_uri) (GXmlNode* self);
	GeeList* (*get_namespaces) (GXmlNode* self);
	GeeBidirList* (*get_children_nodes) (GXmlNode* self);
	GeeMap* (*get_attrs) (GXmlNode* self);
	gchar* (*get_name) (GXmlNode* self);
	gchar* (*get_value) (GXmlNode* self);
	void (*set_value) (GXmlNode* self, const gchar* value);
	GXmlNodeType (*get_type_node) (GXmlNode* self);
	GXmlDocument* (*get_document) (GXmlNode* self);
	GXmlNode* (*get_parent) (GXmlNode* self);
};

struct _GXmlAttributeIface {
	GTypeInterface parent_iface;
	GXmlNamespace* (*get_namespace) (GXmlAttribute* self);
	void (*set_namespace) (GXmlAttribute* self, GXmlNamespace* value);
	gchar* (*get_prefix) (GXmlAttribute* self);
};

struct _GXmlSerializableIface {
	GTypeInterface parent_iface;
	gboolean (*get_enable_unknown_serializable_property) (GXmlSerializable* self);
	gboolean (*set_default_namespace) (GXmlSerializable* self, GXmlNode* node);
	gboolean (*serialize_use_xml_node_value) (GXmlSerializable* self);
	gchar* (*node_name) (GXmlSerializable* self);
	gboolean (*property_use_nick) (GXmlSerializable* self);
	GXmlNode* (*serialize) (GXmlSerializable* self, GXmlNode* node, GError** error);
	GXmlNode* (*serialize_property) (GXmlSerializable* self, GXmlNode* element, GParamSpec* prop, GError** error);
	gboolean (*deserialize) (GXmlSerializable* self, GXmlNode* node, GError** error);
	gboolean (*deserialize_property) (GXmlSerializable* self, GXmlNode* property_node, GError** error);
	GParamSpec* (*find_property_spec) (GXmlSerializable* self, const gchar* property_name);
	GParamSpec* (*default_find_property_spec) (GXmlSerializable* self, const gchar* property_name);
	GParamSpec** (*list_serializable_properties) (GXmlSerializable* self, gint* result_length1);
	GParamSpec** (*default_list_serializable_properties) (GXmlSerializable* self, gint* result_length1);
	GeeMap* (*get_unknown_serializable_properties) (GXmlSerializable* self);
	GeeCollection* (*get_unknown_serializable_nodes) (GXmlSerializable* self);
	gchar* (*get_serialized_xml_node_value) (GXmlSerializable* self);
	void (*set_serialized_xml_node_value) (GXmlSerializable* self, const gchar* value);
};

typedef enum  {
	GXML_SERIALIZABLE_ERROR_UNSUPPORTED_TYPE_ERROR,
	GXML_SERIALIZABLE_ERROR_STR_TO_VALUE_ERROR
} GXmlSerializableError;
#define GXML_SERIALIZABLE_ERROR gxml_serializable_error_quark ()
/**
   * Errors from {@link Serializable}.
   */

GType gxml_element_list_get_type (void) G_GNUC_CONST;
GType gxml_namespace_get_type (void) G_GNUC_CONST;
GType gxml_node_type_get_type (void) G_GNUC_CONST;
GType gxml_document_get_type (void) G_GNUC_CONST;
GType gxml_node_get_type (void) G_GNUC_CONST;
GType gxml_attribute_get_type (void) G_GNUC_CONST;
GType gxml_serializable_get_type (void) G_GNUC_CONST;
gboolean gxml_serializable_get_enable_unknown_serializable_property (GXmlSerializable* self);
gboolean gxml_serializable_set_default_namespace (GXmlSerializable* self,
                                                  GXmlNode* node);
gboolean gxml_serializable_serialize_use_xml_node_value (GXmlSerializable* self);
gchar* gxml_serializable_node_name (GXmlSerializable* self);
gboolean gxml_serializable_property_use_nick (GXmlSerializable* self);
GXmlNode* gxml_serializable_serialize (GXmlSerializable* self,
                                       GXmlNode* node,
                                       GError** error);
GXmlNode* gxml_serializable_serialize_property (GXmlSerializable* self,
                                                GXmlNode* element,
                                                GParamSpec* prop,
                                                GError** error);
gboolean gxml_serializable_deserialize (GXmlSerializable* self,
                                        GXmlNode* node,
                                        GError** error);
gboolean gxml_serializable_deserialize_property (GXmlSerializable* self,
                                                 GXmlNode* property_node,
                                                 GError** error);
GParamSpec* gxml_serializable_find_property_spec (GXmlSerializable* self,
                                                  const gchar* property_name);
GParamSpec* gxml_serializable_default_find_property_spec (GXmlSerializable* self,
                                                          const gchar* property_name);
static GParamSpec* gxml_serializable_real_default_find_property_spec (GXmlSerializable* self,
                                                               const gchar* property_name);
GParamSpec** gxml_serializable_list_serializable_properties (GXmlSerializable* self,
                                                             gint* result_length1);
GParamSpec** gxml_serializable_default_list_serializable_properties (GXmlSerializable* self,
                                                                     gint* result_length1);
static GParamSpec** gxml_serializable_real_default_list_serializable_properties (GXmlSerializable* self,
                                                                          gint* result_length1);
static void _g_free0_ (gpointer var);
static void _g_param_spec_unref0_ (gpointer var);
static void _vala_array_add1 (GParamSpec** * array,
                       int* length,
                       int* size,
                       GParamSpec* value);
GQuark gxml_serializable_error_quark (void);
gboolean gxml_serializable_string_to_gvalue (const gchar* str,
                                             GValue* dest,
                                             GError** error);
gchar* gxml_serializable_gvalue_to_string (GValue* val,
                                           GError** error);
GeeMap* gxml_serializable_get_unknown_serializable_properties (GXmlSerializable* self);
GeeCollection* gxml_serializable_get_unknown_serializable_nodes (GXmlSerializable* self);
gchar* gxml_serializable_get_serialized_xml_node_value (GXmlSerializable* self);
void gxml_serializable_set_serialized_xml_node_value (GXmlSerializable* self,
                                                      const gchar* value);
static void g_cclosure_user_marshal_VOID__OBJECT_G_PARAM_SPEC_POINTER (GClosure * closure,
                                                                GValue * return_value,
                                                                guint n_param_values,
                                                                const GValue * param_values,
                                                                gpointer invocation_hint,
                                                                gpointer marshal_data);
static void g_cclosure_user_marshal_VOID__OBJECT_G_PARAM_SPEC (GClosure * closure,
                                                        GValue * return_value,
                                                        guint n_param_values,
                                                        const GValue * param_values,
                                                        gpointer invocation_hint,
                                                        gpointer marshal_data);
static void _vala_array_destroy (gpointer array,
                          gint array_length,
                          GDestroyNotify destroy_func);
static void _vala_array_free (gpointer array,
                       gint array_length,
                       GDestroyNotify destroy_func);
static gint _vala_array_length (gpointer array);

/**
    * Return false if you want to ignore unknown properties and {@link GXml.Node}'s
    * not in your class definition.
    *
    * Take care, disabling this feature you can lost data on serialization, because any unknown
    * property or element will be discarted.
    */
gboolean
gxml_serializable_get_enable_unknown_serializable_property (GXmlSerializable* self)
{
	g_return_val_if_fail (self != NULL, FALSE);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->get_enable_unknown_serializable_property (self);
}

/**
     * Used to set specific namespace for an {@link GXml.Element}.
     *
     * By default no namspace prefix is added to {@link GXml.Element} on serialized. Implementors
     * must consider override this methodk if this node should have a namespace.
     */
gboolean
gxml_serializable_set_default_namespace (GXmlSerializable* self,
                                         GXmlNode* node)
{
	g_return_val_if_fail (self != NULL, FALSE);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->set_default_namespace (self, node);
}

/**
      * Used to check {@link GXml.Element}'s contents must be deseralized.
      *
      * By default GXml's implementations doesn't deseriaze/serialize XML node contents.
      * In order to enable it, you must override {@link serialize_use_xml_node_value}
      * method to return true and store XML node's content to {@link serialized_xml_node_value}
      * property.
      *
      * Implementors could set up methods to provide a clean easy to use API to set
      * nodes contents. In most cases, users would like to set a value through a getter
      * or setter or through a property in the class.
      *
     */
gboolean
gxml_serializable_serialize_use_xml_node_value (GXmlSerializable* self)
{
	g_return_val_if_fail (self != NULL, FALSE);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->serialize_use_xml_node_value (self);
}

/**
      * Defines the way to set Node name.
      */
gchar*
gxml_serializable_node_name (GXmlSerializable* self)
{
	g_return_val_if_fail (self != NULL, NULL);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->node_name (self);
}

/**
      * Defines the way to set Node's property name, by using
      * it's nick instead of default name.
      *
      * When serialize a class property, by default it uses its name given  on class
      * declaration, but is less common to see XML node properties with names like
      * "your_property", but more common is to use "YourProperty". In order
      * to use this kind of names, your implementation should use properties' nick
      * name and override {@link property_use_nick} method to return true. This should
      * instruct your code to use this method to use property's nick name. This is
      * the default in GXml default implementations.
      */
gboolean
gxml_serializable_property_use_nick (GXmlSerializable* self)
{
	g_return_val_if_fail (self != NULL, FALSE);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->property_use_nick (self);
}

/**
     * Serialize this object.
     *
     * This method must call serialize_property() recursivally on all properties
     * to serialize.
     *
     * @param node an {@link GXml.Node} object to serialize to.
     */
GXmlNode*
gxml_serializable_serialize (GXmlSerializable* self,
                             GXmlNode* node,
                             GError** error)
{
	g_return_val_if_fail (self != NULL, NULL);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->serialize (self, node, error);
}

/**
     * Serialize a property @prop on a {@link GXml.Element}.
     *
     * This method is called recursivally by {@link serialize} method over all properties
     * to be serialized.
     */
GXmlNode*
gxml_serializable_serialize_property (GXmlSerializable* self,
                                      GXmlNode* element,
                                      GParamSpec* prop,
                                      GError** error)
{
	g_return_val_if_fail (self != NULL, NULL);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->serialize_property (self, element, prop, error);
}

/**
     * Deserialize this object.
     *
     * @param node {@link GXml.Node} used to deserialize from.
     */
gboolean
gxml_serializable_deserialize (GXmlSerializable* self,
                               GXmlNode* node,
                               GError** error)
{
	g_return_val_if_fail (self != NULL, FALSE);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->deserialize (self, node, error);
}

/**
     * Handles deserializing individual properties.
     *
     * Interface method to handle deserialization of an
     * individual property.  The implementing class
     * receives a description of the property and the
     * {@link GXml.Node} that contains the content.  The
     * implementing {@link GXml.Serializable} object can extract
     * the data from the {@link GXml.Node} and store it in its
     * property itself. Note that the {@link GXml.Node} may be
     * as simple as a {@link GXml.Text} that stores the data as a
     * string.
     *
     * Implementors:
     * Use Serializable.get_property_value in order to allow derived classes to
     * override the properties to serialize.
     *
     * @param property_node the {@link GXml.Node} encapsulating data to deserialize
     * @return `true` if the property was handled.
     */
gboolean
gxml_serializable_deserialize_property (GXmlSerializable* self,
                                        GXmlNode* property_node,
                                        GError** error)
{
	g_return_val_if_fail (self != NULL, FALSE);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->deserialize_property (self, property_node, error);
}

/**
     * Handles finding the {@link GLib.ParamSpec} for a given property, it should
     * a serializable property, see {@link list_serializable_properties}.
     *
     * @param property_name the name of a property to obtain a {@link GLib.ParamSpec} for
     * @return a {@link GLib.ParamSpec} describing the named property
     */
GParamSpec*
gxml_serializable_find_property_spec (GXmlSerializable* self,
                                      const gchar* property_name)
{
	g_return_val_if_fail (self != NULL, NULL);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->find_property_spec (self, property_name);
}

/**
     * Default implementation for {@link Serializable.find_property_spec}
     *
     */
static gpointer
_g_param_spec_ref0 (gpointer self)
{
	return self ? g_param_spec_ref (self) : NULL;
}

static gboolean
string_contains (const gchar* self,
                 const gchar* needle)
{
	gboolean result = FALSE;
	gchar* _tmp0_;
	g_return_val_if_fail (self != NULL, FALSE);
	g_return_val_if_fail (needle != NULL, FALSE);
	_tmp0_ = strstr ((gchar*) self, (gchar*) needle);
	result = _tmp0_ != NULL;
	return result;
}

static gchar
string_get (const gchar* self,
            glong index)
{
	gchar result = '\0';
	gchar _tmp0_;
	g_return_val_if_fail (self != NULL, '\0');
	_tmp0_ = ((gchar*) self)[index];
	result = _tmp0_;
	return result;
}

static gchar*
string_slice (const gchar* self,
              glong start,
              glong end)
{
	gchar* result = NULL;
	glong string_length = 0L;
	gint _tmp0_;
	gint _tmp1_;
	gboolean _tmp2_ = FALSE;
	gboolean _tmp3_ = FALSE;
	gchar* _tmp4_;
	g_return_val_if_fail (self != NULL, NULL);
	_tmp0_ = strlen (self);
	_tmp1_ = _tmp0_;
	string_length = (glong) _tmp1_;
	if (start < ((glong) 0)) {
		start = string_length + start;
	}
	if (end < ((glong) 0)) {
		end = string_length + end;
	}
	if (start >= ((glong) 0)) {
		_tmp2_ = start <= string_length;
	} else {
		_tmp2_ = FALSE;
	}
	g_return_val_if_fail (_tmp2_, NULL);
	if (end >= ((glong) 0)) {
		_tmp3_ = end <= string_length;
	} else {
		_tmp3_ = FALSE;
	}
	g_return_val_if_fail (_tmp3_, NULL);
	g_return_val_if_fail (start <= end, NULL);
	_tmp4_ = g_strndup (((gchar*) self) + start, (gsize) (end - start));
	result = _tmp4_;
	return result;
}

static const gchar*
string_to_string (const gchar* self)
{
	const gchar* result = NULL;
	g_return_val_if_fail (self != NULL, NULL);
	result = self;
	return result;
}

static GParamSpec*
gxml_serializable_real_default_find_property_spec (GXmlSerializable* self,
                                                   const gchar* property_name)
{
	GParamSpec* result = NULL;
	GParamSpec** props = NULL;
	gint _tmp0_ = 0;
	GParamSpec** _tmp1_;
	gint props_length1;
	gint _props_size_;
	GParamSpec** _tmp2_;
	gint _tmp2__length1;
	g_return_val_if_fail (property_name != NULL, NULL);
	_tmp1_ = gxml_serializable_list_serializable_properties (self, &_tmp0_);
	props = _tmp1_;
	props_length1 = _tmp0_;
	_props_size_ = props_length1;
	_tmp2_ = props;
	_tmp2__length1 = props_length1;
	{
		GParamSpec** spec_collection = NULL;
		gint spec_collection_length1 = 0;
		gint _spec_collection_size_ = 0;
		gint spec_it = 0;
		spec_collection = _tmp2_;
		spec_collection_length1 = _tmp2__length1;
		for (spec_it = 0; spec_it < _tmp2__length1; spec_it = spec_it + 1) {
			GParamSpec* _tmp3_;
			GParamSpec* spec = NULL;
			_tmp3_ = _g_param_spec_ref0 (spec_collection[spec_it]);
			spec = _tmp3_;
			{
				GParamSpec* _tmp4_;
				const gchar* _tmp5_;
				gchar* _tmp6_;
				gchar* _tmp7_;
				gchar* _tmp8_;
				gchar* _tmp9_;
				gboolean _tmp10_;
				GParamSpec* _tmp18_;
				const gchar* _tmp19_;
				_tmp4_ = spec;
				_tmp5_ = _tmp4_->name;
				_tmp6_ = g_utf8_strdown (_tmp5_, (gssize) -1);
				_tmp7_ = _tmp6_;
				_tmp8_ = g_utf8_strdown (property_name, (gssize) -1);
				_tmp9_ = _tmp8_;
				_tmp10_ = g_strcmp0 (_tmp7_, _tmp9_) == 0;
				_g_free0 (_tmp9_);
				_g_free0 (_tmp7_);
				if (_tmp10_) {
					result = spec;
					props = (_vala_array_free (props, props_length1, (GDestroyNotify) g_param_spec_unref), NULL);
					return result;
				}
				if (gxml_serializable_property_use_nick (self)) {
					GParamSpec* _tmp11_;
					const gchar* _tmp12_;
					gchar* _tmp13_;
					gchar* _tmp14_;
					gchar* _tmp15_;
					gchar* _tmp16_;
					gboolean _tmp17_;
					_tmp11_ = spec;
					_tmp12_ = g_param_spec_get_nick (_tmp11_);
					_tmp13_ = g_utf8_strdown (_tmp12_, (gssize) -1);
					_tmp14_ = _tmp13_;
					_tmp15_ = g_utf8_strdown (property_name, (gssize) -1);
					_tmp16_ = _tmp15_;
					_tmp17_ = g_strcmp0 (_tmp14_, _tmp16_) == 0;
					_g_free0 (_tmp16_);
					_g_free0 (_tmp14_);
					if (_tmp17_) {
						result = spec;
						props = (_vala_array_free (props, props_length1, (GDestroyNotify) g_param_spec_unref), NULL);
						return result;
					}
				}
				_tmp18_ = spec;
				_tmp19_ = _tmp18_->name;
				if (string_contains (_tmp19_, "-")) {
					gchar** sp = NULL;
					GParamSpec* _tmp20_;
					const gchar* _tmp21_;
					gchar** _tmp22_;
					gchar** _tmp23_;
					gint sp_length1;
					gint _sp_size_;
					gchar* n = NULL;
					gchar* _tmp24_;
					gchar** _tmp25_;
					gint _tmp25__length1;
					const gchar* _tmp43_;
					gchar* _tmp44_;
					gchar* _tmp45_;
					gchar* _tmp46_;
					gchar* _tmp47_;
					gboolean _tmp48_;
					_tmp20_ = spec;
					_tmp21_ = _tmp20_->name;
					_tmp23_ = _tmp22_ = g_strsplit (_tmp21_, "-", 0);
					sp = _tmp23_;
					sp_length1 = _vala_array_length (_tmp22_);
					_sp_size_ = sp_length1;
					_tmp24_ = g_strdup ("");
					n = _tmp24_;
					_tmp25_ = sp;
					_tmp25__length1 = sp_length1;
					{
						gchar** s_collection = NULL;
						gint s_collection_length1 = 0;
						gint _s_collection_size_ = 0;
						gint s_it = 0;
						s_collection = _tmp25_;
						s_collection_length1 = _tmp25__length1;
						for (s_it = 0; s_it < _tmp25__length1; s_it = s_it + 1) {
							gchar* _tmp26_;
							gchar* s = NULL;
							_tmp26_ = g_strdup (s_collection[s_it]);
							s = _tmp26_;
							{
								const gchar* _tmp27_;
								const gchar* _tmp28_;
								gchar* _tmp29_;
								gchar* _tmp30_;
								gchar* _tmp31_;
								gchar* _tmp32_;
								const gchar* _tmp33_;
								const gchar* _tmp34_;
								gint _tmp35_;
								gint _tmp36_;
								gchar* _tmp37_;
								gchar* _tmp38_;
								const gchar* _tmp39_;
								gchar* _tmp40_;
								gchar* _tmp41_;
								gchar* _tmp42_;
								_tmp27_ = n;
								_tmp28_ = s;
								_tmp29_ = g_strdup_printf ("%c", string_get (_tmp28_, (glong) 0));
								_tmp30_ = _tmp29_;
								_tmp31_ = g_utf8_strup (_tmp30_, (gssize) -1);
								_tmp32_ = _tmp31_;
								_tmp33_ = s;
								_tmp34_ = s;
								_tmp35_ = strlen (_tmp34_);
								_tmp36_ = _tmp35_;
								_tmp37_ = string_slice (_tmp33_, (glong) 1, (glong) _tmp36_);
								_tmp38_ = _tmp37_;
								_tmp39_ = string_to_string (_tmp38_);
								_tmp40_ = g_strconcat (_tmp32_, _tmp39_, NULL);
								_tmp41_ = _tmp40_;
								_tmp42_ = g_strconcat (_tmp27_, _tmp41_, NULL);
								_g_free0 (n);
								n = _tmp42_;
								_g_free0 (_tmp41_);
								_g_free0 (_tmp38_);
								_g_free0 (_tmp32_);
								_g_free0 (_tmp30_);
								_g_free0 (s);
							}
						}
					}
					_tmp43_ = n;
					_tmp44_ = g_utf8_strdown (_tmp43_, (gssize) -1);
					_tmp45_ = _tmp44_;
					_tmp46_ = g_utf8_strdown (property_name, (gssize) -1);
					_tmp47_ = _tmp46_;
					_tmp48_ = g_strcmp0 (_tmp45_, _tmp47_) == 0;
					_g_free0 (_tmp47_);
					_g_free0 (_tmp45_);
					if (_tmp48_) {
						result = spec;
						_g_free0 (n);
						sp = (_vala_array_free (sp, sp_length1, (GDestroyNotify) g_free), NULL);
						props = (_vala_array_free (props, props_length1, (GDestroyNotify) g_param_spec_unref), NULL);
						return result;
					}
					_g_free0 (n);
					sp = (_vala_array_free (sp, sp_length1, (GDestroyNotify) g_free), NULL);
				}
				_g_param_spec_unref0 (spec);
			}
		}
	}
	result = NULL;
	props = (_vala_array_free (props, props_length1, (GDestroyNotify) g_param_spec_unref), NULL);
	return result;
}

GParamSpec*
gxml_serializable_default_find_property_spec (GXmlSerializable* self,
                                              const gchar* property_name)
{
	g_return_val_if_fail (self != NULL, NULL);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->default_find_property_spec (self, property_name);
}

/**
     * List the known properties for an object's class to be de/seriablizable.
     *
     * @return an array of {@link GLib.ParamSpec} of "properties" for the object.
     */
GParamSpec**
gxml_serializable_list_serializable_properties (GXmlSerializable* self,
                                                gint* result_length1)
{
	g_return_val_if_fail (self != NULL, NULL);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->list_serializable_properties (self, result_length1);
}

/**
     * Default implementation for {@link Serializable.list_serializable_properties}
     *
     */
static void
_g_free0_ (gpointer var)
{
	var = (g_free (var), NULL);
}

static void
_g_param_spec_unref0_ (gpointer var)
{
	(var == NULL) ? NULL : (var = (g_param_spec_unref (var), NULL));
}

static void
_vala_array_add1 (GParamSpec** * array,
                  int* length,
                  int* size,
                  GParamSpec* value)
{
	if ((*length) == (*size)) {
		*size = (*size) ? (2 * (*size)) : 4;
		*array = g_renew (GParamSpec*, *array, (*size) + 1);
	}
	(*array)[(*length)++] = value;
	(*array)[*length] = NULL;
}

static GParamSpec**
gxml_serializable_real_default_list_serializable_properties (GXmlSerializable* self,
                                                             gint* result_length1)
{
	GParamSpec** result = NULL;
	GParamSpec** props = NULL;
	GParamSpec** _tmp0_;
	gint props_length1;
	gint _props_size_;
	GHashTable* l = NULL;
	GHashFunc _tmp1_;
	GEqualFunc _tmp2_;
	GHashTable* _tmp3_;
	GHashTable* _tmp4_;
	gchar* _tmp5_;
	GObjectClass* _tmp6_;
	GParamSpec* _tmp7_;
	GParamSpec* _tmp8_;
	GHashTable* _tmp9_;
	gchar* _tmp10_;
	GObjectClass* _tmp11_;
	GParamSpec* _tmp12_;
	GParamSpec* _tmp13_;
	GHashTable* _tmp14_;
	gchar* _tmp15_;
	GObjectClass* _tmp16_;
	GParamSpec* _tmp17_;
	GParamSpec* _tmp18_;
	GHashTable* _tmp19_;
	gchar* _tmp20_;
	GObjectClass* _tmp21_;
	GParamSpec* _tmp22_;
	GParamSpec* _tmp23_;
	GObjectClass* _tmp24_;
	guint _tmp25_ = 0;
	GParamSpec** _tmp26_;
	GParamSpec** _tmp34_;
	gint _tmp34__length1;
	_tmp0_ = g_new0 (GParamSpec*, 0 + 1);
	props = _tmp0_;
	props_length1 = 0;
	_props_size_ = props_length1;
	_tmp1_ = g_str_hash;
	_tmp2_ = g_str_equal;
	_tmp3_ = g_hash_table_new_full (_tmp1_, _tmp2_, _g_free0_, _g_param_spec_unref0_);
	l = _tmp3_;
	_tmp4_ = l;
	_tmp5_ = g_strdup ("ignored-serializable-properties");
	_tmp6_ = G_OBJECT_GET_CLASS ((GObject*) self);
	_tmp7_ = g_object_class_find_property (_tmp6_, "ignored-serializable-properties");
	_tmp8_ = _g_param_spec_ref0 (_tmp7_);
	g_hash_table_insert (_tmp4_, _tmp5_, _tmp8_);
	_tmp9_ = l;
	_tmp10_ = g_strdup ("unknown-serializable-properties");
	_tmp11_ = G_OBJECT_GET_CLASS ((GObject*) self);
	_tmp12_ = g_object_class_find_property (_tmp11_, "unknown-serializable-properties");
	_tmp13_ = _g_param_spec_ref0 (_tmp12_);
	g_hash_table_insert (_tmp9_, _tmp10_, _tmp13_);
	_tmp14_ = l;
	_tmp15_ = g_strdup ("unknown-serializable-nodes");
	_tmp16_ = G_OBJECT_GET_CLASS ((GObject*) self);
	_tmp17_ = g_object_class_find_property (_tmp16_, "unknown-serializable-nodes");
	_tmp18_ = _g_param_spec_ref0 (_tmp17_);
	g_hash_table_insert (_tmp14_, _tmp15_, _tmp18_);
	_tmp19_ = l;
	_tmp20_ = g_strdup ("serialized-xml-node-value");
	_tmp21_ = G_OBJECT_GET_CLASS ((GObject*) self);
	_tmp22_ = g_object_class_find_property (_tmp21_, "serialized-xml-node-value");
	_tmp23_ = _g_param_spec_ref0 (_tmp22_);
	g_hash_table_insert (_tmp19_, _tmp20_, _tmp23_);
	_tmp24_ = G_OBJECT_GET_CLASS ((GObject*) self);
	_tmp26_ = g_object_class_list_properties (_tmp24_, &_tmp25_);
	{
		GParamSpec** spec_collection = NULL;
		gint spec_collection_length1 = 0;
		gint _spec_collection_size_ = 0;
		gint spec_it = 0;
		spec_collection = _tmp26_;
		spec_collection_length1 = _tmp25_;
		for (spec_it = 0; spec_it < _tmp25_; spec_it = spec_it + 1) {
			GParamSpec* _tmp27_;
			GParamSpec* spec = NULL;
			_tmp27_ = _g_param_spec_ref0 (spec_collection[spec_it]);
			spec = _tmp27_;
			{
				GHashTable* _tmp28_;
				GParamSpec* _tmp29_;
				const gchar* _tmp30_;
				_tmp28_ = l;
				_tmp29_ = spec;
				_tmp30_ = _tmp29_->name;
				if (!g_hash_table_contains (_tmp28_, _tmp30_)) {
					GParamSpec** _tmp31_;
					gint _tmp31__length1;
					GParamSpec* _tmp32_;
					GParamSpec* _tmp33_;
					_tmp31_ = props;
					_tmp31__length1 = props_length1;
					_tmp32_ = spec;
					_tmp33_ = _g_param_spec_ref0 (_tmp32_);
					_vala_array_add1 (&props, &props_length1, &_props_size_, _tmp33_);
				}
				_g_param_spec_unref0 (spec);
			}
		}
		spec_collection = (g_free (spec_collection), NULL);
	}
	_tmp34_ = props;
	_tmp34__length1 = props_length1;
	if (result_length1) {
		*result_length1 = _tmp34__length1;
	}
	result = _tmp34_;
	_g_hash_table_unref0 (l);
	return result;
}

GParamSpec**
gxml_serializable_default_list_serializable_properties (GXmlSerializable* self,
                                                        gint* result_length1)
{
	g_return_val_if_fail (self != NULL, NULL);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->default_list_serializable_properties (self, result_length1);
}

/**
      * Transforms a string into another type hosted by {@link GLib.Value}.
      *
      * A utility function that handles converting a string
      * representation of a value into the type specified by the
      * supplied #GValue dest.  A #GXmlSerializableError will be
      * set if the string cannot be parsed into the desired type.
      *
      * {@link Serializable} interface support a number of data types to convert
      * from its string representation. These are supported types:
      *
      * a. integers: int8, int64, uint, long, ulong, char, uchar
      * a. boolean
      * a. floats: float, double
      * a. enumerations
      *
      * @param str the string to transform into the given #GValue object
      * @param dest the #GValue out parameter that will contain the parsed value from the string
      * @return `true` if parsing succeeded, otherwise `false`
      */
static gdouble
double_parse (const gchar* str)
{
	gdouble result = 0.0;
	g_return_val_if_fail (str != NULL, 0.0);
	result = g_ascii_strtod (str, NULL);
	return result;
}

static gboolean
bool_try_parse (const gchar* str,
                gboolean* _result_)
{
	gboolean _vala__result_ = FALSE;
	gboolean result = FALSE;
	g_return_val_if_fail (str != NULL, FALSE);
	if (g_strcmp0 (str, "true") == 0) {
		_vala__result_ = TRUE;
		result = TRUE;
		if (_result_) {
			*_result_ = _vala__result_;
		}
		return result;
	} else {
		if (g_strcmp0 (str, "false") == 0) {
			_vala__result_ = FALSE;
			result = TRUE;
			if (_result_) {
				*_result_ = _vala__result_;
			}
			return result;
		} else {
			_vala__result_ = FALSE;
			result = FALSE;
			if (_result_) {
				*_result_ = _vala__result_;
			}
			return result;
		}
	}
	if (_result_) {
		*_result_ = _vala__result_;
	}
}

gboolean
gxml_serializable_string_to_gvalue (const gchar* str,
                                    GValue* dest,
                                    GError** error)
{
	gboolean result = FALSE;
	GType t = 0UL;
	GValue dest2 = {0};
	GValue _tmp0_ = {0};
	gboolean ret = FALSE;
	gboolean _tmp1_ = FALSE;
	GError* _inner_error0_ = NULL;
	g_return_val_if_fail (str != NULL, FALSE);
	g_return_val_if_fail (dest != NULL, FALSE);
	t = G_VALUE_TYPE (dest);
	g_value_init (&_tmp0_, t);
	dest2 = _tmp0_;
	ret = FALSE;
	if (t == G_TYPE_INT64) {
		_tmp1_ = TRUE;
	} else {
		_tmp1_ = t == G_TYPE_UINT64;
	}
	if (_tmp1_) {
		gint64 val = 0LL;
		val = (gint64) double_parse (str);
		g_value_set_int64 (&dest2, val);
		ret = TRUE;
	} else {
		if (t == G_TYPE_INT) {
			gint val = 0;
			val = (gint) double_parse (str);
			g_value_set_int (&dest2, val);
			ret = TRUE;
		} else {
			if (t == G_TYPE_LONG) {
				glong val = 0L;
				val = (glong) double_parse (str);
				g_value_set_long (&dest2, val);
				ret = TRUE;
			} else {
				if (t == G_TYPE_UINT) {
					guint val = 0U;
					val = (guint) double_parse (str);
					g_value_set_uint (&dest2, val);
					ret = TRUE;
				} else {
					if (t == G_TYPE_ULONG) {
						gulong val = 0UL;
						val = (gulong) double_parse (str);
						g_value_set_ulong (&dest2, val);
						ret = TRUE;
					} else {
						if (t == G_TYPE_BOOLEAN) {
							gboolean val = FALSE;
							gchar* _tmp2_;
							gchar* _tmp3_;
							gboolean _tmp4_ = FALSE;
							gboolean _tmp5_;
							gboolean _tmp6_;
							_tmp2_ = g_utf8_strdown (str, (gssize) -1);
							_tmp3_ = _tmp2_;
							_tmp5_ = bool_try_parse (_tmp3_, &_tmp4_);
							val = _tmp4_;
							ret = _tmp5_;
							_tmp6_ = ret;
							_g_free0 (_tmp3_);
							if (_tmp6_) {
								g_value_set_boolean (&dest2, val);
							}
						} else {
							if (t == G_TYPE_FLOAT) {
								gfloat val = 0.0F;
								val = (gfloat) double_parse (str);
								g_value_set_float (&dest2, val);
								ret = TRUE;
							} else {
								if (t == G_TYPE_DOUBLE) {
									gdouble val = 0.0;
									val = (gdouble) double_parse (str);
									g_value_set_double (&dest2, val);
									ret = TRUE;
								} else {
									if (t == G_TYPE_STRING) {
										g_value_set_string (&dest2, str);
										ret = TRUE;
									} else {
										if (t == G_TYPE_UCHAR) {
											guchar val = '\0';
											val = (guchar) double_parse (str);
											g_value_set_uchar (&dest2, val);
											ret = TRUE;
										} else {
											if (t == G_TYPE_BOXED) {
											} else {
												if (G_TYPE_IS_ENUM (t)) {
													gint val = 0;
													val = (gint) double_parse (str);
													g_value_set_enum (&dest2, val);
													ret = TRUE;
												} else {
													if (G_TYPE_IS_FLAGS (t)) {
													} else {
														if (G_TYPE_IS_OBJECT (t)) {
														} else {
														}
													}
												}
											}
										}
									}
								}
							}
						}
					}
				}
			}
		}
	}
	if (ret == TRUE) {
		GValue _tmp7_;
		GValue _tmp8_ = {0};
		_tmp7_ = dest2;
		if (G_IS_VALUE (&_tmp7_)) {
			g_value_init (&_tmp8_, G_VALUE_TYPE (&_tmp7_));
			g_value_copy (&_tmp7_, &_tmp8_);
		} else {
			_tmp8_ = _tmp7_;
		}
		G_IS_VALUE (dest) ? (g_value_unset (dest), NULL) : NULL;
		*dest = _tmp8_;
		result = TRUE;
		G_IS_VALUE (&dest2) ? (g_value_unset (&dest2), NULL) : NULL;
		return result;
	} else {
		const gchar* _tmp9_;
		GError* _tmp10_;
		_tmp9_ = g_type_name (t);
		_tmp10_ = g_error_new (GXML_SERIALIZABLE_ERROR, GXML_SERIALIZABLE_ERROR_UNSUPPORTED_TYPE_ERROR, _ ("Transformation Error on \'%s\' or Unsupported type: \'%s\'"), str, _tmp9_);
		_inner_error0_ = _tmp10_;
		if (_inner_error0_->domain == GXML_SERIALIZABLE_ERROR) {
			gboolean _tmp11_ = FALSE;
			g_propagate_error (error, _inner_error0_);
			G_IS_VALUE (&dest2) ? (g_value_unset (&dest2), NULL) : NULL;
			return _tmp11_;
		} else {
			gboolean _tmp12_ = FALSE;
			G_IS_VALUE (&dest2) ? (g_value_unset (&dest2), NULL) : NULL;
			g_critical ("file %s: line %d: uncaught error: %s (%s, %d)", __FILE__, __LINE__, _inner_error0_->message, g_quark_to_string (_inner_error0_->domain), _inner_error0_->code);
			g_clear_error (&_inner_error0_);
			return _tmp12_;
		}
	}
	G_IS_VALUE (&dest2) ? (g_value_unset (&dest2), NULL) : NULL;
}

/**
     * Transforms a {@link GLib.Value} to its string representation.
     *
     * By default use {@link GLib.Value} standard transformations.
     *
     */
gchar*
gxml_serializable_gvalue_to_string (GValue* val,
                                    GError** error)
{
	gchar* result = NULL;
	GValue ret = {0};
	GValue _tmp0_ = {0};
	GError* _inner_error0_ = NULL;
	g_return_val_if_fail (val != NULL, NULL);
	g_value_init (&_tmp0_, G_TYPE_STRING);
	g_value_set_string (&_tmp0_, "");
	ret = _tmp0_;
	if (g_value_type_transformable (G_VALUE_TYPE (val), G_TYPE_STRING)) {
		gchar* _tmp1_;
		g_value_transform (val, &ret);
		_tmp1_ = g_value_dup_string (&ret);
		result = _tmp1_;
		G_IS_VALUE (&ret) ? (g_value_unset (&ret), NULL) : NULL;
		return result;
	} else {
		const gchar* _tmp2_;
		GError* _tmp3_;
		_tmp2_ = g_type_name (G_VALUE_TYPE (val));
		_tmp3_ = g_error_new (GXML_SERIALIZABLE_ERROR, GXML_SERIALIZABLE_ERROR_UNSUPPORTED_TYPE_ERROR, _ ("Can't transform \'%s\' to string"), _tmp2_);
		_inner_error0_ = _tmp3_;
		if (_inner_error0_->domain == GXML_SERIALIZABLE_ERROR) {
			g_propagate_error (error, _inner_error0_);
			G_IS_VALUE (&ret) ? (g_value_unset (&ret), NULL) : NULL;
			return NULL;
		} else {
			G_IS_VALUE (&ret) ? (g_value_unset (&ret), NULL) : NULL;
			g_critical ("file %s: line %d: uncaught error: %s (%s, %d)", __FILE__, __LINE__, _inner_error0_->message, g_quark_to_string (_inner_error0_->domain), _inner_error0_->code);
			g_clear_error (&_inner_error0_);
			return NULL;
		}
	}
	G_IS_VALUE (&ret) ? (g_value_unset (&ret), NULL) : NULL;
}

GeeMap*
gxml_serializable_get_unknown_serializable_properties (GXmlSerializable* self)
{
	g_return_val_if_fail (self != NULL, NULL);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->get_unknown_serializable_properties (self);
}

GeeCollection*
gxml_serializable_get_unknown_serializable_nodes (GXmlSerializable* self)
{
	g_return_val_if_fail (self != NULL, NULL);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->get_unknown_serializable_nodes (self);
}

gchar*
gxml_serializable_get_serialized_xml_node_value (GXmlSerializable* self)
{
	g_return_val_if_fail (self != NULL, NULL);
	return GXML_SERIALIZABLE_GET_INTERFACE (self)->get_serialized_xml_node_value (self);
}

void
gxml_serializable_set_serialized_xml_node_value (GXmlSerializable* self,
                                                 const gchar* value)
{
	g_return_if_fail (self != NULL);
	GXML_SERIALIZABLE_GET_INTERFACE (self)->set_serialized_xml_node_value (self, value);
}

static void
g_cclosure_user_marshal_VOID__OBJECT_G_PARAM_SPEC_POINTER (GClosure * closure,
                                                           GValue * return_value,
                                                           guint n_param_values,
                                                           const GValue * param_values,
                                                           gpointer invocation_hint,
                                                           gpointer marshal_data)
{
	typedef void (*GMarshalFunc_VOID__OBJECT_G_PARAM_SPEC_POINTER) (gpointer data1, gpointer arg_1, gpointer arg_2, gpointer arg_3, gpointer data2);
	register GMarshalFunc_VOID__OBJECT_G_PARAM_SPEC_POINTER callback;
	register GCClosure * cc;
	register gpointer data1;
	register gpointer data2;
	cc = (GCClosure *) closure;
	g_return_if_fail (n_param_values == 4);
	if (G_CCLOSURE_SWAP_DATA (closure)) {
		data1 = closure->data;
		data2 = param_values->data[0].v_pointer;
	} else {
		data1 = param_values->data[0].v_pointer;
		data2 = closure->data;
	}
	callback = (GMarshalFunc_VOID__OBJECT_G_PARAM_SPEC_POINTER) (marshal_data ? marshal_data : cc->callback);
	callback (data1, g_value_get_object (param_values + 1), g_value_get_param (param_values + 2), g_value_get_pointer (param_values + 3), data2);
}

static void
g_cclosure_user_marshal_VOID__OBJECT_G_PARAM_SPEC (GClosure * closure,
                                                   GValue * return_value,
                                                   guint n_param_values,
                                                   const GValue * param_values,
                                                   gpointer invocation_hint,
                                                   gpointer marshal_data)
{
	typedef void (*GMarshalFunc_VOID__OBJECT_G_PARAM_SPEC) (gpointer data1, gpointer arg_1, gpointer arg_2, gpointer data2);
	register GMarshalFunc_VOID__OBJECT_G_PARAM_SPEC callback;
	register GCClosure * cc;
	register gpointer data1;
	register gpointer data2;
	cc = (GCClosure *) closure;
	g_return_if_fail (n_param_values == 3);
	if (G_CCLOSURE_SWAP_DATA (closure)) {
		data1 = closure->data;
		data2 = param_values->data[0].v_pointer;
	} else {
		data1 = param_values->data[0].v_pointer;
		data2 = closure->data;
	}
	callback = (GMarshalFunc_VOID__OBJECT_G_PARAM_SPEC) (marshal_data ? marshal_data : cc->callback);
	callback (data1, g_value_get_object (param_values + 1), g_value_get_param (param_values + 2), data2);
}

static void
gxml_serializable_default_init (GXmlSerializableIface * iface,
                                gpointer iface_data)
{
	/**
	     * On deserialization stores any {@link GXml.Attribute} not used on this
	     * object, but exists in current XML file.
	     *
	     * Node's name is used as key to find stored {@link GXml.Attribute}, key is
	     * case sensitive.
	     *
	     * XML allows great flexibility, providing different ways to represent the same
	     * information. This is a problem when you try to deserialize them.
	     *
	     * In order to deserialize correctly, you must create your XML, both by
	     * serializing a {@link Serializable} object or by hand writing. By using the
	     * former, you can add extra information, like attributes, but most of
	     * them could be ignored or lost on deserialization/serialization process. To
	     * avoid data lost, you can override {@link get_enable_unknown_serializable_property}
	     * method in order to return true, your implementation or the ones in GXml, will
	     * store all unknown attributes on deserialization and must serialize
	     * again back to the XML file. Even you are allowed to get this unknown objects
	     * by iterating on {@link unknown_serializable_properties} collection, if you know
	     * attribute's name, use it to retrieve it.
	     *
	     * This property is ignored on serialisation.
	     */
	g_object_interface_install_property (iface, g_param_spec_object ("unknown-serializable-properties", "unknown-serializable-properties", "unknown-serializable-properties", GEE_TYPE_MAP, G_PARAM_STATIC_STRINGS | G_PARAM_READABLE));
	/**
	     * On deserialization stores any {@link GXml.Node} not used on this
	     * object, but exists in current XML file.
	     *
	     * XML allows great flexibility, providing different ways to represent the same
	     * information. This is a problem when you try to deserialize them.
	     *
	     * In order to deserialize correctly, you must create your XML, both by
	     * serializing a {@link Serializable} object or by hand writing. By using the
	     * former, you can add extra information, like nodes or contents in known nodes,
	     * but most of them could be ignored or lost on deserialization/serialization process.
	     * To avoid data lost, you can override {@link get_enable_unknown_serializable_property}
	     * method in order to return true, your implementation or the ones in GXml, will
	     * store all unknown properties and nodes on deserialization and must serialize
	     * again back to the XML file. Even you are allowed to get this unknown objects
	     * by iterating on {@link Serializable.unknown_serializable_nodes} hash table.
	     *
	     * This property is ignored on serialisation.
	     */
	g_object_interface_install_property (iface, g_param_spec_object ("unknown-serializable-nodes", "unknown-serializable-nodes", "unknown-serializable-nodes", GEE_TYPE_COLLECTION, G_PARAM_STATIC_STRINGS | G_PARAM_READABLE));
	/**
	     * Used to add content in an {@link GXml.Element}.
	     *
	     * By default no contents is serialized/deseralized. Implementors must implement
	     * {@link Serializable.serialize_use_xml_node_value} function returning
	     * true in order to use this property.
	     *
	     * This property is ignored by default. Implementors must implement
	     * {@link serialize_use_xml_node_value} to return true and add a
	     * set and get function to get/set this value, in order to use your own API.
	     *
	     * This property is ignored on serialisation.
	     */
	g_object_interface_install_property (iface, g_param_spec_string ("serialized-xml-node-value", "serialized-xml-node-value", "serialized-xml-node-value", NULL, G_PARAM_STATIC_STRINGS | G_PARAM_READABLE | G_PARAM_WRITABLE));
	/**
	     * Signal to serialize unknown properties. Any new node must be added to
	     * @param element before return the new @param node added.
	     *
	     * @param element a {@link GXml.Node} to add attribute or child nodes to
	     * @param prop a {@link GLib.ParamSpec} describing attribute to serialize
	     * @param node set to the {@link GXml.Node} representing this attribute
	     */
	gxml_serializable_signals[GXML_SERIALIZABLE_SERIALIZE_UNKNOWN_PROPERTY_SIGNAL] = g_signal_new ("serialize-unknown-property", GXML_TYPE_SERIALIZABLE, G_SIGNAL_RUN_LAST, 0, NULL, NULL, g_cclosure_user_marshal_VOID__OBJECT_G_PARAM_SPEC_POINTER, G_TYPE_NONE, 3, GXML_TYPE_NODE, G_TYPE_PARAM, G_TYPE_POINTER);
	/**
	     * Signal to serialize unknown properties. Any new node must be added to
	     * @param element before return the new @node added.
	     * 
	     * @param element a {@link GXml.Node} to add attribute or child nodes to
	     * @param prop a {@link GLib.ParamSpec} describing attribute to serialize
	     * @param node set to the {@link GXml.Node} representing this attribute
	     */
	gxml_serializable_signals[GXML_SERIALIZABLE_SERIALIZE_UNKNOWN_PROPERTY_TYPE_SIGNAL] = g_signal_new ("serialize-unknown-property-type", GXML_TYPE_SERIALIZABLE, G_SIGNAL_RUN_LAST, 0, NULL, NULL, g_cclosure_user_marshal_VOID__OBJECT_G_PARAM_SPEC_POINTER, G_TYPE_NONE, 3, GXML_TYPE_NODE, G_TYPE_PARAM, G_TYPE_POINTER);
	/**
	     * Signal to deserialize unknown properties.
	     *
	     * @param node a {@link GXml.Node} to get attribute from
	     * @param prop a {@link GLib.ParamSpec} describing attribute to deserialize
	     */
	gxml_serializable_signals[GXML_SERIALIZABLE_DESERIALIZE_UNKNOWN_PROPERTY_SIGNAL] = g_signal_new ("deserialize-unknown-property", GXML_TYPE_SERIALIZABLE, G_SIGNAL_RUN_LAST, 0, NULL, NULL, g_cclosure_user_marshal_VOID__OBJECT_G_PARAM_SPEC, G_TYPE_NONE, 2, GXML_TYPE_NODE, G_TYPE_PARAM);
	/**
	     * Signal to deserialize unknown properties' type.
	     *
	     * @param node a {@link GXml.Node} to get attribute from
	     * @param prop a {@link GLib.ParamSpec} describing attribute to deserialize
	     */
	gxml_serializable_signals[GXML_SERIALIZABLE_DESERIALIZE_UNKNOWN_PROPERTY_TYPE_SIGNAL] = g_signal_new ("deserialize-unknown-property-type", GXML_TYPE_SERIALIZABLE, G_SIGNAL_RUN_LAST, 0, NULL, NULL, g_cclosure_user_marshal_VOID__OBJECT_G_PARAM_SPEC, G_TYPE_NONE, 2, GXML_TYPE_NODE, G_TYPE_PARAM);
	iface->default_find_property_spec = gxml_serializable_real_default_find_property_spec;
	iface->default_list_serializable_properties = gxml_serializable_real_default_list_serializable_properties;
}

/**
   * A {@link GXml.Node} Serialization framework. Base interface.
   *
   * Implementors of this interface, could define or override the way you want to 
   * represent your class in a XML file.
   */
GType
gxml_serializable_get_type (void)
{
	static volatile gsize gxml_serializable_type_id__volatile = 0;
	if (g_once_init_enter (&gxml_serializable_type_id__volatile)) {
		static const GTypeInfo g_define_type_info = { sizeof (GXmlSerializableIface), (GBaseInitFunc) NULL, (GBaseFinalizeFunc) NULL, (GClassInitFunc) gxml_serializable_default_init, (GClassFinalizeFunc) NULL, NULL, 0, 0, (GInstanceInitFunc) NULL, NULL };
		GType gxml_serializable_type_id;
		gxml_serializable_type_id = g_type_register_static (G_TYPE_INTERFACE, "GXmlSerializable", &g_define_type_info, 0);
		g_type_interface_add_prerequisite (gxml_serializable_type_id, G_TYPE_OBJECT);
		g_once_init_leave (&gxml_serializable_type_id__volatile, gxml_serializable_type_id);
	}
	return gxml_serializable_type_id__volatile;
}

GQuark
gxml_serializable_error_quark (void)
{
	return g_quark_from_static_string ("gxml-serializable-error-quark");
}

static void
_vala_array_destroy (gpointer array,
                     gint array_length,
                     GDestroyNotify destroy_func)
{
	if ((array != NULL) && (destroy_func != NULL)) {
		int i;
		for (i = 0; i < array_length; i = i + 1) {
			if (((gpointer*) array)[i] != NULL) {
				destroy_func (((gpointer*) array)[i]);
			}
		}
	}
}

static void
_vala_array_free (gpointer array,
                  gint array_length,
                  GDestroyNotify destroy_func)
{
	_vala_array_destroy (array, array_length, destroy_func);
	g_free (array);
}

static gint
_vala_array_length (gpointer array)
{
	int length;
	length = 0;
	if (array) {
		while (((gpointer*) array)[length]) {
			length++;
		}
	}
	return length;
}

