/* libxml-Implementation.c generated by valac 0.28.1, the Vala compiler
 * generated from libxml-Implementation.vala, do not modify */

/* -*- Mode: vala; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */
/* Implementation.vala
 *
 * Copyright (C) 2011-2013  Richard Schwarting <aquarichy@gmail.com>
 * Copyright (C) 2011,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:
 *      Richard Schwarting <aquarichy@gmail.com>
 *      Daniel Espinosa <esodan@gmail.com>
 */

#include <glib.h>
#include <glib-object.h>
#include <stdlib.h>
#include <string.h>


#define GXML_TYPE_IMPLEMENTATION (gxml_implementation_get_type ())
#define GXML_IMPLEMENTATION(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GXML_TYPE_IMPLEMENTATION, GXmlImplementation))
#define GXML_IMPLEMENTATION_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GXML_TYPE_IMPLEMENTATION, GXmlImplementationClass))
#define GXML_IS_IMPLEMENTATION(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GXML_TYPE_IMPLEMENTATION))
#define GXML_IS_IMPLEMENTATION_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GXML_TYPE_IMPLEMENTATION))
#define GXML_IMPLEMENTATION_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GXML_TYPE_IMPLEMENTATION, GXmlImplementationClass))

typedef struct _GXmlImplementation GXmlImplementation;
typedef struct _GXmlImplementationClass GXmlImplementationClass;
typedef struct _GXmlImplementationPrivate GXmlImplementationPrivate;

#define GXML_TYPE_DOM_EXCEPTION (gxml_dom_exception_get_type ())
#define _g_free0(var) (var = (g_free (var), NULL))

#define GXML_TYPE_XNODE (gxml_xnode_get_type ())
#define GXML_XNODE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GXML_TYPE_XNODE, GXmlxNode))
#define GXML_XNODE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GXML_TYPE_XNODE, GXmlxNodeClass))
#define GXML_IS_XNODE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GXML_TYPE_XNODE))
#define GXML_IS_XNODE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GXML_TYPE_XNODE))
#define GXML_XNODE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GXML_TYPE_XNODE, GXmlxNodeClass))

typedef struct _GXmlxNode GXmlxNode;
typedef struct _GXmlxNodeClass GXmlxNodeClass;

#define GXML_TYPE_XDOCUMENT_TYPE (gxml_xdocument_type_get_type ())
#define GXML_XDOCUMENT_TYPE(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GXML_TYPE_XDOCUMENT_TYPE, GXmlxDocumentType))
#define GXML_XDOCUMENT_TYPE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GXML_TYPE_XDOCUMENT_TYPE, GXmlxDocumentTypeClass))
#define GXML_IS_XDOCUMENT_TYPE(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GXML_TYPE_XDOCUMENT_TYPE))
#define GXML_IS_XDOCUMENT_TYPE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GXML_TYPE_XDOCUMENT_TYPE))
#define GXML_XDOCUMENT_TYPE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GXML_TYPE_XDOCUMENT_TYPE, GXmlxDocumentTypeClass))

typedef struct _GXmlxDocumentType GXmlxDocumentType;
typedef struct _GXmlxDocumentTypeClass GXmlxDocumentTypeClass;

#define GXML_TYPE_XDOCUMENT (gxml_xdocument_get_type ())
#define GXML_XDOCUMENT(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GXML_TYPE_XDOCUMENT, GXmlxDocument))
#define GXML_XDOCUMENT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GXML_TYPE_XDOCUMENT, GXmlxDocumentClass))
#define GXML_IS_XDOCUMENT(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GXML_TYPE_XDOCUMENT))
#define GXML_IS_XDOCUMENT_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GXML_TYPE_XDOCUMENT))
#define GXML_XDOCUMENT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GXML_TYPE_XDOCUMENT, GXmlxDocumentClass))

typedef struct _GXmlxDocument GXmlxDocument;
typedef struct _GXmlxDocumentClass GXmlxDocumentClass;
#define _g_object_unref0(var) ((var == NULL) ? NULL : (var = (g_object_unref (var), NULL)))

struct _GXmlImplementation {
	GObject parent_instance;
	GXmlImplementationPrivate * priv;
};

struct _GXmlImplementationClass {
	GObjectClass parent_class;
};

typedef enum  {
	GXML_DOM_EXCEPTION_NONE,
	GXML_DOM_EXCEPTION_INDEX_SIZE,
	GXML_DOM_EXCEPTION_DOMSTRING_SIZE,
	GXML_DOM_EXCEPTION_HIERARCHY_REQUEST,
	GXML_DOM_EXCEPTION_WRONG_DOCUMENT,
	GXML_DOM_EXCEPTION_INVALID_CHARACTER,
	GXML_DOM_EXCEPTION_NO_DATA_ALLOWED,
	GXML_DOM_EXCEPTION_NO_MODIFICATION_ALLOWED,
	GXML_DOM_EXCEPTION_NOT_FOUND,
	GXML_DOM_EXCEPTION_NOT_SUPPORTED,
	GXML_DOM_EXCEPTION_INUSE_ATTRIBUTE,
	GXML_DOM_EXCEPTION_DOM,
	GXML_DOM_EXCEPTION_INVALID_DOC,
	GXML_DOM_EXCEPTION_INVALID_ROOT,
	GXML_DOM_EXCEPTION_NAMESPACE,
	GXML_DOM_EXCEPTION_X_OTHER
} GXmlDomException;


static gpointer gxml_implementation_parent_class = NULL;

GType gxml_implementation_get_type (void) G_GNUC_CONST;
enum  {
	GXML_IMPLEMENTATION_DUMMY_PROPERTY
};
GXmlImplementation* gxml_implementation_new (void);
GXmlImplementation* gxml_implementation_construct (GType object_type);
static void gxml_implementation_check_namespace (GXmlImplementation* self, const gchar* namespace_uri, const gchar* qualified_name);
GType gxml_dom_exception_get_type (void) G_GNUC_CONST;
void gxml_warning (GXmlDomException ex, const gchar* message) G_GNUC_DEPRECATED;
gboolean gxml_xdocument_check_invalid_characters (const gchar* name, const gchar* subject);
gboolean gxml_implementation_has_feature (GXmlImplementation* self, const gchar* feature, const gchar* version);
GType gxml_xnode_get_type (void) G_GNUC_CONST;
GType gxml_xdocument_type_get_type (void) G_GNUC_CONST;
void gxml_implementation_check_wrong_document (GXmlImplementation* self, GXmlxDocumentType* doctype);
GType gxml_xdocument_get_type (void) G_GNUC_CONST;
GXmlxDocument* gxml_xnode_get_owner_document (GXmlxNode* self);
GXmlxDocument* gxml_implementation_create_document (GXmlImplementation* self, const gchar* namespace_uri, const gchar* qualified_name, GXmlxDocumentType* doctype);
GXmlxDocument* gxml_xdocument_new_with_implementation (GXmlImplementation* impl, const gchar* namespace_uri, const gchar* qualified_name, GXmlxDocumentType* doctype);
GXmlxDocument* gxml_xdocument_construct_with_implementation (GType object_type, GXmlImplementation* impl, const gchar* namespace_uri, const gchar* qualified_name, GXmlxDocumentType* doctype);
static GObject * gxml_implementation_constructor (GType type, guint n_construct_properties, GObjectConstructParam * construct_properties);
void gxml_init_init (void);
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);


GXmlImplementation* gxml_implementation_construct (GType object_type) {
	GXmlImplementation * self = NULL;
	self = (GXmlImplementation*) g_object_new (object_type, NULL);
	return self;
}


GXmlImplementation* gxml_implementation_new (void) {
	return gxml_implementation_construct (GXML_TYPE_IMPLEMENTATION);
}


static void gxml_implementation_check_namespace (GXmlImplementation* self, const gchar* namespace_uri, const gchar* qualified_name) {
	gboolean _tmp0_ = FALSE;
	const gchar* _tmp1_ = NULL;
	const gchar* _tmp6_ = NULL;
	gboolean _tmp27_ = FALSE;
	const gchar* _tmp28_ = NULL;
	g_return_if_fail (self != NULL);
	_tmp1_ = qualified_name;
	if (_tmp1_ == NULL) {
		const gchar* _tmp2_ = NULL;
		_tmp2_ = namespace_uri;
		_tmp0_ = _tmp2_ != NULL;
	} else {
		_tmp0_ = FALSE;
	}
	if (_tmp0_) {
		const gchar* _tmp3_ = NULL;
		gchar* _tmp4_ = NULL;
		gchar* _tmp5_ = NULL;
		_tmp3_ = namespace_uri;
		_tmp4_ = g_strdup_printf ("qualified_name is null but namespace_uri [%s] is not.  Both should eit" \
"her be null or not null.", _tmp3_);
		_tmp5_ = _tmp4_;
		gxml_warning (GXML_DOM_EXCEPTION_NAMESPACE, _tmp5_);
		_g_free0 (_tmp5_);
	}
	_tmp6_ = qualified_name;
	if (_tmp6_ != NULL) {
		const gchar* _tmp7_ = NULL;
		gchar** parts = NULL;
		const gchar* _tmp8_ = NULL;
		gchar** _tmp9_ = NULL;
		gchar** _tmp10_ = NULL;
		gint parts_length1 = 0;
		gint _parts_size_ = 0;
		gchar** _tmp11_ = NULL;
		gint _tmp11__length1 = 0;
		_tmp7_ = qualified_name;
		gxml_xdocument_check_invalid_characters (_tmp7_, "new Document's root");
		_tmp8_ = qualified_name;
		_tmp10_ = _tmp9_ = g_strsplit (_tmp8_, ":", 0);
		parts = _tmp10_;
		parts_length1 = _vala_array_length (_tmp9_);
		_parts_size_ = parts_length1;
		_tmp11_ = parts;
		_tmp11__length1 = parts_length1;
		if (_tmp11__length1 == 2) {
			const gchar* _tmp12_ = NULL;
			gchar* expected_uri = NULL;
			gchar* _tmp16_ = NULL;
			gboolean _tmp17_ = FALSE;
			gchar** _tmp18_ = NULL;
			gint _tmp18__length1 = 0;
			const gchar* _tmp19_ = NULL;
			_tmp12_ = namespace_uri;
			if (_tmp12_ == NULL) {
				const gchar* _tmp13_ = NULL;
				gchar* _tmp14_ = NULL;
				gchar* _tmp15_ = NULL;
				_tmp13_ = qualified_name;
				_tmp14_ = g_strdup_printf ("namespace_uri is null but qualified_name [%s] has prefixed part.  Both" \
" should either be null or not null.", _tmp13_);
				_tmp15_ = _tmp14_;
				gxml_warning (GXML_DOM_EXCEPTION_NAMESPACE, _tmp15_);
				_g_free0 (_tmp15_);
			}
			_tmp16_ = g_strdup ("http://www.w3.org/XML/1998/namespace");
			expected_uri = _tmp16_;
			_tmp18_ = parts;
			_tmp18__length1 = parts_length1;
			_tmp19_ = _tmp18_[0];
			if (g_strcmp0 (_tmp19_, "xml") == 0) {
				const gchar* _tmp20_ = NULL;
				const gchar* _tmp21_ = NULL;
				_tmp20_ = namespace_uri;
				_tmp21_ = expected_uri;
				_tmp17_ = g_strcmp0 (_tmp20_, _tmp21_) != 0;
			} else {
				_tmp17_ = FALSE;
			}
			if (_tmp17_) {
				const gchar* _tmp22_ = NULL;
				const gchar* _tmp23_ = NULL;
				const gchar* _tmp24_ = NULL;
				gchar* _tmp25_ = NULL;
				gchar* _tmp26_ = NULL;
				_tmp22_ = qualified_name;
				_tmp23_ = namespace_uri;
				_tmp24_ = expected_uri;
				_tmp25_ = g_strdup_printf ("qualified_name '%s' specifies namespace 'xml' but namespace_uri is '%s" \
"' and not '%s'", _tmp22_, _tmp23_, _tmp24_);
				_tmp26_ = _tmp25_;
				gxml_warning (GXML_DOM_EXCEPTION_NAMESPACE, _tmp26_);
				_g_free0 (_tmp26_);
			}
			_g_free0 (expected_uri);
		}
		parts = (_vala_array_free (parts, parts_length1, (GDestroyNotify) g_free), NULL);
	}
	_tmp28_ = namespace_uri;
	if (_tmp28_ != NULL) {
		gboolean _tmp29_ = FALSE;
		_tmp29_ = gxml_implementation_has_feature (self, "XML", NULL);
		_tmp27_ = !_tmp29_;
	} else {
		_tmp27_ = FALSE;
	}
	if (_tmp27_) {
		const gchar* _tmp30_ = NULL;
		gchar* _tmp31_ = NULL;
		gchar* _tmp32_ = NULL;
		_tmp30_ = namespace_uri;
		_tmp31_ = g_strdup_printf ("Implementation lacks feature 'XML' but a namespace_uri ('%s') was spec" \
"ified anyway.", _tmp30_);
		_tmp32_ = _tmp31_;
		gxml_warning (GXML_DOM_EXCEPTION_NAMESPACE, _tmp32_);
		_g_free0 (_tmp32_);
	}
}


void gxml_implementation_check_wrong_document (GXmlImplementation* self, GXmlxDocumentType* doctype) {
	gboolean _tmp0_ = FALSE;
	GXmlxDocumentType* _tmp1_ = NULL;
	g_return_if_fail (self != NULL);
	_tmp1_ = doctype;
	if (_tmp1_ != NULL) {
		GXmlxDocumentType* _tmp2_ = NULL;
		GXmlxDocument* _tmp3_ = NULL;
		GXmlxDocument* _tmp4_ = NULL;
		_tmp2_ = doctype;
		_tmp3_ = gxml_xnode_get_owner_document ((GXmlxNode*) _tmp2_);
		_tmp4_ = _tmp3_;
		_tmp0_ = _tmp4_ != NULL;
	} else {
		_tmp0_ = FALSE;
	}
	if (_tmp0_) {
		gxml_warning (GXML_DOM_EXCEPTION_WRONG_DOCUMENT, "The supplied doctype is already connected to an existing document.");
	}
}


/**
 * Creates a xDocument according to this {@link GXml.Implementation}.
 *
 * Version: DOM Level 3 Core<<BR>>
 * URL: [[http://www.w3.org/TR/DOM-Level-3-Core/core.html#Level-2-Core-DOM-createDocument]]

 * @param namespace_uri URI for the namespace in which this xDocument belongs, or %NULL
 * @param qualified_name A qualified name for the xDocument, or %NULL
 * @param doctype The type of the document, or %NULL
 *
 * @return The new document
 */
GXmlxDocument* gxml_implementation_create_document (GXmlImplementation* self, const gchar* namespace_uri, const gchar* qualified_name, GXmlxDocumentType* doctype) {
	GXmlxDocument* result = NULL;
	GXmlxDocument* doc = NULL;
	const gchar* _tmp0_ = NULL;
	const gchar* _tmp1_ = NULL;
	GXmlxDocumentType* _tmp2_ = NULL;
	const gchar* _tmp3_ = NULL;
	const gchar* _tmp4_ = NULL;
	GXmlxDocumentType* _tmp5_ = NULL;
	GXmlxDocument* _tmp6_ = NULL;
	g_return_val_if_fail (self != NULL, NULL);
	_tmp0_ = namespace_uri;
	_tmp1_ = qualified_name;
	gxml_implementation_check_namespace (self, _tmp0_, _tmp1_);
	_tmp2_ = doctype;
	gxml_implementation_check_wrong_document (self, _tmp2_);
	_tmp3_ = namespace_uri;
	_tmp4_ = qualified_name;
	_tmp5_ = doctype;
	_tmp6_ = gxml_xdocument_new_with_implementation (self, _tmp3_, _tmp4_, _tmp5_);
	_g_object_unref0 (doc);
	doc = _tmp6_;
	result = doc;
	return result;
}


/**
 * Reports whether we support a feature at a given version level.
 *
 * Version: DOM Level 1 Core<<BR>>
 * URL: [[http://www.w3.org/TR/REC-DOM-Level-1/level-one-core.html#method-hasFeature]]
 *
 * TODO: implement more of this, using libxml2's parser.h's xmlGetFeature, xmlHasFeature, etc.
 *
 * @param feature A feature we might support, usually something like 'xml' or 'html'
 * @param version A possible version of the feature, or %NULL if any version will do
 *
 * @return true if we support the specified feature, false otherwise
 */
gboolean gxml_implementation_has_feature (GXmlImplementation* self, const gchar* feature, const gchar* version) {
	gboolean result = FALSE;
	const gchar* _tmp0_ = NULL;
	const gchar* _tmp1_ = NULL;
	GQuark _tmp3_ = 0U;
	static GQuark _tmp2_label0 = 0;
	static GQuark _tmp2_label1 = 0;
	g_return_val_if_fail (self != NULL, FALSE);
	g_return_val_if_fail (feature != NULL, FALSE);
	_tmp0_ = feature;
	_tmp1_ = _tmp0_;
	_tmp3_ = (NULL == _tmp1_) ? 0 : g_quark_from_string (_tmp1_);
	if ((_tmp3_ == ((0 != _tmp2_label0) ? _tmp2_label0 : (_tmp2_label0 = g_quark_from_static_string ("xml")))) || (_tmp3_ == ((0 != _tmp2_label1) ? _tmp2_label1 : (_tmp2_label1 = g_quark_from_static_string ("XML"))))) {
		switch (0) {
			default:
			{
				const gchar* _tmp4_ = NULL;
				const gchar* _tmp5_ = NULL;
				GQuark _tmp7_ = 0U;
				static GQuark _tmp6_label0 = 0;
				static GQuark _tmp6_label1 = 0;
				_tmp4_ = version;
				_tmp5_ = _tmp4_;
				_tmp7_ = (NULL == _tmp5_) ? 0 : g_quark_from_string (_tmp5_);
				if ((_tmp7_ == ((0 != _tmp6_label0) ? _tmp6_label0 : (_tmp6_label0 = g_quark_from_static_string (NULL)))) || (_tmp7_ == ((0 != _tmp6_label1) ? _tmp6_label1 : (_tmp6_label1 = g_quark_from_static_string ("1.0"))))) {
					switch (0) {
						default:
						{
							result = TRUE;
							return result;
						}
					}
				} else {
					switch (0) {
						default:
						{
							result = FALSE;
							return result;
						}
					}
				}
			}
		}
	} else {
		switch (0) {
			default:
			{
				result = FALSE;
				return result;
			}
		}
	}
}


static GObject * gxml_implementation_constructor (GType type, guint n_construct_properties, GObjectConstructParam * construct_properties) {
	GObject * obj;
	GObjectClass * parent_class;
	GXmlImplementation * self;
	parent_class = G_OBJECT_CLASS (gxml_implementation_parent_class);
	obj = parent_class->constructor (type, n_construct_properties, construct_properties);
	self = G_TYPE_CHECK_INSTANCE_CAST (obj, GXML_TYPE_IMPLEMENTATION, GXmlImplementation);
	gxml_init_init ();
	return obj;
}


static void gxml_implementation_class_init (GXmlImplementationClass * klass) {
	gxml_implementation_parent_class = g_type_class_peek_parent (klass);
	G_OBJECT_CLASS (klass)->constructor = gxml_implementation_constructor;
}


static void gxml_implementation_instance_init (GXmlImplementation * self) {
}


/**
 * Describes the features available in this
 * implementation of the DOM.
 *
 * This can be accessed from a {@link GXml.xDocument}
 * object. Provided a possible feature and the feature's
 * version, it can tell the client whether it is here
 * implemented.
 *
 * Version: DOM Level 1 Core<<BR>>
 * URL: [[http://www.w3.org/TR/REC-DOM-Level-1/level-one-core.html#ID-102161490]]
 */
GType gxml_implementation_get_type (void) {
	static volatile gsize gxml_implementation_type_id__volatile = 0;
	if (g_once_init_enter (&gxml_implementation_type_id__volatile)) {
		static const GTypeInfo g_define_type_info = { sizeof (GXmlImplementationClass), (GBaseInitFunc) NULL, (GBaseFinalizeFunc) NULL, (GClassInitFunc) gxml_implementation_class_init, (GClassFinalizeFunc) NULL, NULL, sizeof (GXmlImplementation), 0, (GInstanceInitFunc) gxml_implementation_instance_init, NULL };
		GType gxml_implementation_type_id;
		gxml_implementation_type_id = g_type_register_static (G_TYPE_OBJECT, "GXmlImplementation", &g_define_type_info, 0);
		g_once_init_leave (&gxml_implementation_type_id__volatile, gxml_implementation_type_id);
	}
	return gxml_implementation_type_id__volatile;
}


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;
}



