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

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

#define NATURAL_COLLATE_SUPERDIGIT ((gunichar) ':')
#define NATURAL_COLLATE_NUM_SENTINEL ((gunichar) 0x2)
#define NATURAL_COLLATE_COLLATION_SENTINEL "\x01\x01\x01"
#if !defined(VALA_STRICT_C)
#if !defined(__clang__) && defined(__GNUC__) && (__GNUC__ >= 14)
#pragma GCC diagnostic warning "-Wincompatible-pointer-types"
#elif defined(__clang__) && (__clang_major__ >= 16)
#pragma clang diagnostic ignored "-Wincompatible-function-pointer-types"
#pragma clang diagnostic ignored "-Wincompatible-pointer-types"
#endif
#endif
#if !defined(VALA_EXTERN)
#if defined(_MSC_VER)
#define VALA_EXTERN __declspec(dllexport) extern
#elif __GNUC__ >= 4
#define VALA_EXTERN __attribute__((visibility("default"))) extern
#else
#define VALA_EXTERN extern
#endif
#endif

#define _g_free0(var) (var = (g_free (var), NULL))
#define _vala_assert(expr, msg) if G_LIKELY (expr) ; else g_assertion_message_expr (G_LOG_DOMAIN, __FILE__, __LINE__, G_STRFUNC, msg);
#define _vala_return_if_fail(expr, msg) if G_LIKELY (expr) ; else { g_return_if_fail_warning (G_LOG_DOMAIN, G_STRFUNC, msg); return; }
#define _vala_return_val_if_fail(expr, msg, val) if G_LIKELY (expr) ; else { g_return_if_fail_warning (G_LOG_DOMAIN, G_STRFUNC, msg); return val; }
#define _vala_warn_if_fail(expr, msg) if G_LIKELY (expr) ; else g_warn_message (G_LOG_DOMAIN, __FILE__, __LINE__, G_STRFUNC, msg);

VALA_EXTERN gint natural_collate_read_number (gchar* s,
                                  glong* byte_index);
VALA_EXTERN gint natural_collate_compare (const gchar* str1,
                              const gchar* str2);
VALA_EXTERN gchar* natural_collate_collate_key (gchar* str);
static inline gpointer _vala_memdup2 (gconstpointer mem,
                        gsize byte_size);

static gunichar
string_get_char (const gchar* self,
                 glong index)
{
	gunichar result;
	g_return_val_if_fail (self != NULL, 0U);
	result = g_utf8_get_char (((gchar*) self) + index);
	return result;
}

static gint
string_index_of_nth_char (const gchar* self,
                          glong c)
{
	gchar* _tmp0_;
	gint result;
	g_return_val_if_fail (self != NULL, -1);
	_tmp0_ = g_utf8_offset_to_pointer (self, c);
	result = (gint) (_tmp0_ - ((gchar*) self));
	return result;
}

static glong
string_strnlen (gchar* str,
                glong maxlen)
{
	gchar* end = NULL;
	gchar* _tmp0_;
	gchar* _tmp1_;
	glong result;
	_tmp0_ = memchr (str, 0, (gsize) maxlen);
	end = _tmp0_;
	_tmp1_ = end;
	if (_tmp1_ == NULL) {
		result = maxlen;
		return result;
	} else {
		gchar* _tmp2_;
		_tmp2_ = end;
		result = (glong) (_tmp2_ - str);
		return result;
	}
}

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

gint
natural_collate_read_number (gchar* s,
                             glong* byte_index)
{
	gint number = 0;
	gint result;
	g_return_val_if_fail (s != NULL, -1);
	number = 0;
	while (TRUE) {
		gboolean _tmp0_ = FALSE;
		gint _tmp1_;
		gint _tmp2_;
		gint second_char = 0;
		gchar* _tmp3_;
		_tmp1_ = strlen (s);
		_tmp2_ = _tmp1_;
		if (_tmp2_ != 0) {
			_tmp0_ = g_unichar_isdigit (string_get_char (s, (glong) 0));
		} else {
			_tmp0_ = FALSE;
		}
		if (!_tmp0_) {
			break;
		}
		number = number * 10;
		number += g_unichar_digit_value (string_get_char (s, (glong) 0));
		second_char = string_index_of_nth_char (s, (glong) 1);
		_tmp3_ = string_substring (s, (glong) second_char, (glong) -1);
		_g_free0 (s);
		s = _tmp3_;
		*byte_index = (*byte_index) + second_char;
	}
	result = number;
	_g_free0 (s);
	return result;
}

gint
natural_collate_compare (const gchar* str1,
                         const gchar* str2)
{
	GCompareFunc _tmp0_;
	gchar* _tmp1_;
	gchar* _tmp2_;
	gchar* _tmp3_;
	gchar* _tmp4_;
	gchar* _tmp5_;
	gchar* _tmp6_;
	gint _tmp7_;
	gint result;
	g_return_val_if_fail (str1 != NULL, -1);
	g_return_val_if_fail (str2 != NULL, -1);
	_tmp0_ = ((GCompareFunc) g_strcmp0);
	_tmp1_ = g_strdup (str1);
	_tmp2_ = natural_collate_collate_key (_tmp1_);
	_tmp3_ = _tmp2_;
	_tmp4_ = g_strdup (str2);
	_tmp5_ = natural_collate_collate_key (_tmp4_);
	_tmp6_ = _tmp5_;
	_tmp7_ = _tmp0_ (_tmp3_, _tmp6_);
	_g_free0 (_tmp6_);
	_g_free0 (_tmp3_);
	result = _tmp7_;
	return result;
}

static gboolean
string_contains (const gchar* self,
                 const gchar* needle)
{
	gchar* _tmp0_;
	gboolean result;
	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*
g_unichar_to_string (gunichar self)
{
	gchar* str = NULL;
	gchar* _tmp0_;
	gchar* result;
	_tmp0_ = g_new0 (gchar, 7);
	str = (gchar*) _tmp0_;
	g_unichar_to_utf8 (self, str);
	result = str;
	return result;
}

gchar*
natural_collate_collate_key (gchar* str)
{
	gchar* _result_ = NULL;
	gchar* _tmp0_;
	gboolean eos = FALSE;
	gint _tmp1_;
	gint _tmp2_;
	const gchar* _tmp46_;
	gchar* _tmp47_;
	gchar* _tmp48_;
	gchar* _tmp49_;
	gchar* result;
	g_return_val_if_fail (str != NULL, NULL);
	_vala_assert (g_utf8_validate (str, (gssize) -1, NULL), "str.validate()");
	_tmp0_ = g_strdup ("");
	_result_ = _tmp0_;
	_tmp1_ = strlen (str);
	_tmp2_ = _tmp1_;
	eos = _tmp2_ == 0;
	while (TRUE) {
		glong position = 0L;
		const gchar* _tmp7_;
		gchar* _tmp8_;
		gchar* _tmp9_;
		gchar* _tmp10_;
		gchar* _tmp11_;
		gchar* _tmp12_;
		gchar* _tmp13_;
		gint _tmp14_;
		gint _tmp15_;
		gint _tmp44_;
		gint _tmp45_;
		if (!(!eos)) {
			break;
		}
		_vala_assert (g_utf8_validate (str, (gssize) -1, NULL), "str.validate()");
		position = 0L;
		while (TRUE) {
			gchar* _tmp3_;
			gchar* _tmp4_;
			gboolean _tmp5_;
			glong _tmp6_;
			_tmp3_ = g_unichar_to_string (string_get_char (str, position));
			_tmp4_ = _tmp3_;
			_tmp5_ = !(!string_contains ("0123456789", _tmp4_));
			_g_free0 (_tmp4_);
			if (_tmp5_) {
				break;
			}
			_tmp6_ = position;
			position = _tmp6_ + 1;
		}
		_tmp7_ = _result_;
		_tmp8_ = string_substring (str, (glong) 0, position);
		_tmp9_ = _tmp8_;
		_tmp10_ = g_utf8_collate_key (_tmp9_, (gssize) -1);
		_tmp11_ = _tmp10_;
		_tmp12_ = g_strconcat (_tmp7_, _tmp11_, NULL);
		_g_free0 (_result_);
		_result_ = _tmp12_;
		_g_free0 (_tmp11_);
		_g_free0 (_tmp9_);
		_tmp13_ = string_substring (str, position, (glong) -1);
		_g_free0 (str);
		str = _tmp13_;
		_tmp14_ = strlen (str);
		_tmp15_ = _tmp14_;
		eos = _tmp15_ == 0;
		position = 0L;
		if (!eos) {
			gint number = 0;
			gchar* _tmp16_;
			gint _tmp17_;
			gchar* _tmp18_;
			gint number_of_superdigits = 0;
			gchar* _tmp19_;
			gchar* _tmp20_;
			gint _tmp21_;
			gint _tmp22_;
			gint _tmp23_;
			gchar* to_append = NULL;
			gchar* _tmp24_;
			const gchar* _tmp31_;
			gchar* _tmp32_;
			gchar* _tmp33_;
			gchar* _tmp34_;
			const gchar* _tmp35_;
			gchar* _tmp36_;
			gchar* _tmp37_;
			gchar* _tmp38_;
			gchar* _tmp39_;
			gchar* _tmp40_;
			gchar* _tmp41_;
			const gchar* _tmp42_;
			gchar* _tmp43_;
			_tmp16_ = g_strdup (str);
			_tmp17_ = natural_collate_read_number (_tmp16_, &position);
			number = _tmp17_;
			_tmp18_ = string_substring (str, position, (glong) -1);
			_g_free0 (str);
			str = _tmp18_;
			_tmp19_ = g_strdup_printf ("%i", number);
			_tmp20_ = _tmp19_;
			_tmp21_ = strlen (_tmp20_);
			_tmp22_ = _tmp21_;
			_tmp23_ = _tmp22_;
			_g_free0 (_tmp20_);
			number_of_superdigits = _tmp23_;
			_tmp24_ = g_strdup ("");
			to_append = _tmp24_;
			{
				gint i = 0;
				i = 1;
				{
					gboolean _tmp25_ = FALSE;
					_tmp25_ = TRUE;
					while (TRUE) {
						const gchar* _tmp27_;
						gchar* _tmp28_;
						gchar* _tmp29_;
						gchar* _tmp30_;
						if (!_tmp25_) {
							gint _tmp26_;
							_tmp26_ = i;
							i = _tmp26_ + 1;
						}
						_tmp25_ = FALSE;
						if (!(i < number_of_superdigits)) {
							break;
						}
						_tmp27_ = to_append;
						_tmp28_ = g_unichar_to_string (NATURAL_COLLATE_SUPERDIGIT);
						_tmp29_ = _tmp28_;
						_tmp30_ = g_strconcat (_tmp27_, _tmp29_, NULL);
						_g_free0 (to_append);
						to_append = _tmp30_;
						_g_free0 (_tmp29_);
					}
				}
			}
			_tmp31_ = to_append;
			_tmp32_ = g_strdup_printf ("%i", number);
			_tmp33_ = _tmp32_;
			_tmp34_ = g_strconcat (_tmp31_, _tmp33_, NULL);
			_g_free0 (to_append);
			to_append = _tmp34_;
			_g_free0 (_tmp33_);
			_tmp35_ = _result_;
			_tmp36_ = g_strconcat (_tmp35_, NATURAL_COLLATE_COLLATION_SENTINEL, NULL);
			_tmp37_ = _tmp36_;
			_tmp38_ = g_unichar_to_string (NATURAL_COLLATE_NUM_SENTINEL);
			_tmp39_ = _tmp38_;
			_tmp40_ = g_strconcat (_tmp37_, _tmp39_, NULL);
			_tmp41_ = _tmp40_;
			_tmp42_ = to_append;
			_tmp43_ = g_strconcat (_tmp41_, _tmp42_, NULL);
			_g_free0 (_result_);
			_result_ = _tmp43_;
			_g_free0 (_tmp41_);
			_g_free0 (_tmp39_);
			_g_free0 (_tmp37_);
			_g_free0 (to_append);
		}
		_tmp44_ = strlen (str);
		_tmp45_ = _tmp44_;
		eos = _tmp45_ == 0;
	}
	_tmp46_ = _result_;
	_tmp47_ = g_unichar_to_string (NATURAL_COLLATE_NUM_SENTINEL);
	_tmp48_ = _tmp47_;
	_tmp49_ = g_strconcat (_tmp46_, _tmp48_, NULL);
	_g_free0 (_result_);
	_result_ = _tmp49_;
	_g_free0 (_tmp48_);
	result = _result_;
	_g_free0 (str);
	return result;
}

static inline gpointer
_vala_memdup2 (gconstpointer mem,
               gsize byte_size)
{
	gpointer new_mem;
	if (mem && byte_size != 0) {
		new_mem = g_malloc (byte_size);
		memcpy (new_mem, mem, byte_size);
	} else {
		new_mem = NULL;
	}
	return new_mem;
}

