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

/* Copyright 2012-2015 -- pancake, eddyb, ritesh */

#include <vala.h>
#include <glib-object.h>
#include <stdlib.h>
#include <string.h>
#include <glib.h>
#include <valagee.h>
#include <valacodegen.h>
#include <stdio.h>
#include <glib/gstdio.h>

#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 TYPE_VALABIND_WRITER (valabind_writer_get_type ())
#define VALABIND_WRITER(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), TYPE_VALABIND_WRITER, ValabindWriter))
#define VALABIND_WRITER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), TYPE_VALABIND_WRITER, ValabindWriterClass))
#define IS_VALABIND_WRITER(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), TYPE_VALABIND_WRITER))
#define IS_VALABIND_WRITER_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), TYPE_VALABIND_WRITER))
#define VALABIND_WRITER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), TYPE_VALABIND_WRITER, ValabindWriterClass))

typedef struct _ValabindWriter ValabindWriter;
typedef struct _ValabindWriterClass ValabindWriterClass;
typedef struct _ValabindWriterPrivate ValabindWriterPrivate;

#define TYPE_NODE_FFI_WRITER (node_ffi_writer_get_type ())
#define NODE_FFI_WRITER(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), TYPE_NODE_FFI_WRITER, NodeFFIWriter))
#define NODE_FFI_WRITER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), TYPE_NODE_FFI_WRITER, NodeFFIWriterClass))
#define IS_NODE_FFI_WRITER(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), TYPE_NODE_FFI_WRITER))
#define IS_NODE_FFI_WRITER_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), TYPE_NODE_FFI_WRITER))
#define NODE_FFI_WRITER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), TYPE_NODE_FFI_WRITER, NodeFFIWriterClass))

typedef struct _NodeFFIWriter NodeFFIWriter;
typedef struct _NodeFFIWriterClass NodeFFIWriterClass;
typedef struct _NodeFFIWriterPrivate NodeFFIWriterPrivate;
#define _g_free0(var) (var = (g_free (var), NULL))
#define _vala_code_node_unref0(var) ((var == NULL) ? NULL : (var = (vala_code_node_unref (var), NULL)))
#define _g_regex_unref0(var) ((var == NULL) ? NULL : (var = (g_regex_unref (var), NULL)))
#define _fclose0(var) ((var == NULL) ? NULL : (var = (fclose (var), NULL)))

struct _ValabindWriter {
	ValaCodeVisitor parent_instance;
	ValabindWriterPrivate * priv;
	gchar* modulename;
	gchar* library;
	gboolean pkgmode;
	gboolean camelgetters;
	gchar* pkgname;
	gchar** include_dirs;
	gchar** namespaces;
	ValaCodeContext* context;
	gchar* vapidir;
	GList* source_files;
	GList* packages;
	GList* defines;
	gboolean glibmode;
	GList* includefiles;
};

struct _ValabindWriterClass {
	ValaCodeVisitorClass parent_class;
	void (*write) (ValabindWriter* self, const gchar* file);
	gchar* (*get_filename) (ValabindWriter* self, const gchar* base_name);
};

struct _NodeFFIWriter {
	ValabindWriter parent_instance;
	NodeFFIWriterPrivate * priv;
};

struct _NodeFFIWriterClass {
	ValabindWriterClass parent_class;
};

struct _NodeFFIWriterPrivate {
	gchar* ns_pfx;
	gchar* bind;
	gchar* enum_fmt;
	gchar* enum_vals;
};

static gint NodeFFIWriter_private_offset;
static gpointer node_ffi_writer_parent_class = NULL;

VALA_EXTERN GType valabind_writer_get_type (void) G_GNUC_CONST ;
G_DEFINE_AUTOPTR_CLEANUP_FUNC (ValabindWriter, vala_code_visitor_unref)
VALA_EXTERN GType node_ffi_writer_get_type (void) G_GNUC_CONST ;
G_DEFINE_AUTOPTR_CLEANUP_FUNC (NodeFFIWriter, vala_code_visitor_unref)
VALA_EXTERN gchar* valabind_writer_get_filename (ValabindWriter* self,
                                     const gchar* base_name);
VALA_EXTERN void valabind_writer_write (ValabindWriter* self,
                            const gchar* file);
VALA_EXTERN NodeFFIWriter* node_ffi_writer_new (void);
VALA_EXTERN NodeFFIWriter* node_ffi_writer_construct (GType object_type);
VALA_EXTERN ValabindWriter* valabind_writer_new (void);
VALA_EXTERN ValabindWriter* valabind_writer_construct (GType object_type);
static gchar* node_ffi_writer_real_get_filename (ValabindWriter* base,
                                          const gchar* base_name);
static gchar* node_ffi_writer_type_name (NodeFFIWriter* self,
                                  ValaDataType* type,
                                  gboolean ignoreRef);
VALA_EXTERN void warning (const gchar* msg);
VALA_EXTERN gchar* valabind_writer_sep (ValabindWriter* self,
                            const gchar* str,
                            const gchar* separator);
VALA_EXTERN gint array_length (ValaArrayType* array);
VALA_EXTERN gboolean valabind_writer_use_namespace (ValabindWriter* self,
                                        ValaNamespace* ns);
static void node_ffi_writer_visit_enum (NodeFFIWriter* self,
                                 ValaEnum* e,
                                 const gchar* pfx);
VALA_EXTERN void valabind_writer_add_includes (ValabindWriter* self,
                                   ValaSymbol* s);
VALA_EXTERN void notice (const gchar* msg);
static void node_ffi_writer_real_visit_struct (ValaCodeVisitor* base,
                                        ValaStruct* s);
static void node_ffi_writer_real_visit_class (ValaCodeVisitor* base,
                                       ValaClass* c);
static void node_ffi_writer_real_visit_field (ValaCodeVisitor* base,
                                       ValaField* f);
static void node_ffi_writer_real_visit_method (ValaCodeVisitor* base,
                                        ValaMethod* m);
static void node_ffi_writer_real_visit_namespace (ValaCodeVisitor* base,
                                           ValaNamespace* ns);
static void node_ffi_writer_real_write (ValabindWriter* base,
                                 const gchar* file);
VALA_EXTERN void error (const gchar* msg);
VALA_EXTERN gchar* get_enums_for (const gchar* str,
                      GList* includefiles);
static void node_ffi_writer_finalize (ValaCodeVisitor * obj);
static GType node_ffi_writer_get_type_once (void);
static void _vala_array_destroy (gpointer array,
                          gssize array_length,
                          GDestroyNotify destroy_func);
static void _vala_array_free (gpointer array,
                       gssize array_length,
                       GDestroyNotify destroy_func);
static gssize _vala_array_length (gpointer array);

static inline gpointer
node_ffi_writer_get_instance_private (NodeFFIWriter* self)
{
	return G_STRUCT_MEMBER_P (self, NodeFFIWriter_private_offset);
}

NodeFFIWriter*
node_ffi_writer_construct (GType object_type)
{
	NodeFFIWriter* self = NULL;
	self = (NodeFFIWriter*) valabind_writer_construct (object_type);
	return self;
}

NodeFFIWriter*
node_ffi_writer_new (void)
{
	return node_ffi_writer_construct (TYPE_NODE_FFI_WRITER);
}

static gchar*
node_ffi_writer_real_get_filename (ValabindWriter* base,
                                   const gchar* base_name)
{
	NodeFFIWriter * self;
	gchar* _tmp0_;
	gchar* result;
	self = (NodeFFIWriter*) base;
	g_return_val_if_fail (base_name != NULL, NULL);
	_tmp0_ = g_strconcat (base_name, ".js", NULL);
	result = _tmp0_;
	return result;
}

static gpointer
_vala_code_node_ref0 (gpointer self)
{
	return self ? vala_code_node_ref (self) : NULL;
}

static gchar*
string_replace (const gchar* self,
                const gchar* old,
                const gchar* replacement)
{
	gboolean _tmp0_ = FALSE;
	gboolean _tmp1_ = FALSE;
	GError* _inner_error0_ = NULL;
	gchar* result;
	g_return_val_if_fail (self != NULL, NULL);
	g_return_val_if_fail (old != NULL, NULL);
	g_return_val_if_fail (replacement != NULL, NULL);
	if ((*((gchar*) self)) == '\0') {
		_tmp1_ = TRUE;
	} else {
		_tmp1_ = (*((gchar*) old)) == '\0';
	}
	if (_tmp1_) {
		_tmp0_ = TRUE;
	} else {
		_tmp0_ = g_strcmp0 (old, replacement) == 0;
	}
	if (_tmp0_) {
		gchar* _tmp2_;
		_tmp2_ = g_strdup (self);
		result = _tmp2_;
		return result;
	}
	{
		GRegex* regex = NULL;
		gchar* _tmp3_;
		gchar* _tmp4_;
		GRegex* _tmp5_;
		GRegex* _tmp6_;
		gchar* _tmp7_ = NULL;
		GRegex* _tmp8_;
		gchar* _tmp9_;
		gchar* _tmp10_;
		_tmp3_ = g_regex_escape_string (old, -1);
		_tmp4_ = _tmp3_;
		_tmp5_ = g_regex_new (_tmp4_, 0, 0, &_inner_error0_);
		_tmp6_ = _tmp5_;
		_g_free0 (_tmp4_);
		regex = _tmp6_;
		if (G_UNLIKELY (_inner_error0_ != NULL)) {
			if (_inner_error0_->domain == G_REGEX_ERROR) {
				goto __catch0_g_regex_error;
			}
			g_critical ("file %s: line %d: unexpected 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;
		}
		_tmp8_ = regex;
		_tmp9_ = g_regex_replace_literal (_tmp8_, self, (gssize) -1, 0, replacement, 0, &_inner_error0_);
		_tmp7_ = _tmp9_;
		if (G_UNLIKELY (_inner_error0_ != NULL)) {
			_g_regex_unref0 (regex);
			if (_inner_error0_->domain == G_REGEX_ERROR) {
				goto __catch0_g_regex_error;
			}
			g_critical ("file %s: line %d: unexpected 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;
		}
		_tmp10_ = _tmp7_;
		_tmp7_ = NULL;
		result = _tmp10_;
		_g_free0 (_tmp7_);
		_g_regex_unref0 (regex);
		return result;
	}
	goto __finally0;
	__catch0_g_regex_error:
	{
		g_clear_error (&_inner_error0_);
		g_assert_not_reached ();
	}
	__finally0:
	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;
}

static gchar*
node_ffi_writer_type_name (NodeFFIWriter* self,
                           ValaDataType* type,
                           gboolean ignoreRef)
{
	gboolean _tmp57_ = FALSE;
	gchar* generic = NULL;
	gchar* _tmp65_;
	gchar* _type = NULL;
	gchar* _tmp81_;
	gchar* local_ns_pfx = NULL;
	const gchar* _tmp82_;
	gchar* _tmp83_;
	gboolean _tmp84_ = FALSE;
	ValaTypeSymbol* _tmp85_;
	ValaTypeSymbol* _tmp86_;
	const gchar* _tmp101_;
	gchar** _tmp102_;
	gchar** _tmp103_;
	gchar** _tmp104_;
	gint _tmp104__length1;
	const gchar* _tmp105_;
	gchar* _tmp106_;
	const gchar* _tmp107_;
	const gchar* _tmp108_;
	gchar* _tmp109_;
	gchar* _tmp110_;
	gchar* _tmp111_;
	const gchar* _tmp112_;
	gchar* _tmp113_;
	const gchar* _tmp114_;
	gchar* _tmp115_;
	const gchar* _tmp116_;
	const gchar* _tmp117_;
	GQuark _tmp119_ = 0U;
	static GQuark _tmp118_label0 = 0;
	static GQuark _tmp118_label1 = 0;
	static GQuark _tmp118_label2 = 0;
	static GQuark _tmp118_label3 = 0;
	static GQuark _tmp118_label4 = 0;
	static GQuark _tmp118_label5 = 0;
	static GQuark _tmp118_label6 = 0;
	static GQuark _tmp118_label7 = 0;
	static GQuark _tmp118_label8 = 0;
	static GQuark _tmp118_label9 = 0;
	static GQuark _tmp118_label10 = 0;
	static GQuark _tmp118_label11 = 0;
	static GQuark _tmp118_label12 = 0;
	static GQuark _tmp118_label13 = 0;
	static GQuark _tmp118_label14 = 0;
	static GQuark _tmp118_label15 = 0;
	static GQuark _tmp118_label16 = 0;
	static GQuark _tmp118_label17 = 0;
	static GQuark _tmp118_label18 = 0;
	static GQuark _tmp118_label19 = 0;
	static GQuark _tmp118_label20 = 0;
	static GQuark _tmp118_label21 = 0;
	const gchar* _tmp135_;
	gchar* _tmp136_;
	const gchar* _tmp137_;
	gchar* result;
	g_return_val_if_fail (self != NULL, NULL);
	g_return_val_if_fail (type != NULL, NULL);
	if (type == NULL) {
		gchar* _tmp0_;
		warning ("Cannot resolve type");
		_tmp0_ = g_strdup ("throw TypeError('Unresolved type')");
		result = _tmp0_;
		return result;
	}
	if (G_TYPE_CHECK_INSTANCE_TYPE (type, VALA_TYPE_ENUM_VALUE_TYPE)) {
		gchar* _tmp1_;
		_tmp1_ = g_strdup ("_.int");
		result = _tmp1_;
		return result;
	}
	if (G_TYPE_CHECK_INSTANCE_TYPE (type, VALA_TYPE_GENERIC_TYPE)) {
		gchar* _tmp2_;
		_tmp2_ = vala_data_type_to_qualified_string (type, NULL);
		result = _tmp2_;
		return result;
	}
	if (G_TYPE_CHECK_INSTANCE_TYPE (type, VALA_TYPE_DELEGATE_TYPE)) {
		ValaDelegateType* _delegate = NULL;
		ValaDelegateType* _tmp3_;
		gchar* ret = NULL;
		ValaDelegateType* _tmp4_;
		ValaDataType* _tmp5_;
		gchar* _tmp6_;
		gchar* args = NULL;
		gchar* _tmp7_;
		const gchar* _tmp26_;
		const gchar* _tmp27_;
		gchar* _tmp28_;
		_tmp3_ = _vala_code_node_ref0 (G_TYPE_CHECK_INSTANCE_TYPE (type, VALA_TYPE_DELEGATE_TYPE) ? ((ValaDelegateType*) type) : NULL);
		_delegate = _tmp3_;
		_tmp4_ = _delegate;
		_tmp5_ = vala_data_type_get_return_type ((ValaDataType*) _tmp4_);
		_tmp6_ = node_ffi_writer_type_name (self, _tmp5_, FALSE);
		ret = _tmp6_;
		_tmp7_ = g_strdup ("");
		args = _tmp7_;
		{
			ValaList* _param_list = NULL;
			ValaDelegateType* _tmp8_;
			ValaList* _tmp9_;
			gint _param_size = 0;
			ValaList* _tmp10_;
			gint _tmp11_;
			gint _tmp12_;
			gint _param_index = 0;
			_tmp8_ = _delegate;
			_tmp9_ = vala_data_type_get_parameters ((ValaDataType*) _tmp8_);
			_param_list = _tmp9_;
			_tmp10_ = _param_list;
			_tmp11_ = vala_collection_get_size ((ValaCollection*) _tmp10_);
			_tmp12_ = _tmp11_;
			_param_size = _tmp12_;
			_param_index = -1;
			while (TRUE) {
				gint _tmp13_;
				gint _tmp14_;
				ValaParameter* param = NULL;
				ValaList* _tmp15_;
				gpointer _tmp16_;
				const gchar* _tmp17_;
				gchar* _tmp18_;
				gchar* _tmp19_;
				ValaParameter* _tmp20_;
				ValaDataType* _tmp21_;
				ValaDataType* _tmp22_;
				gchar* _tmp23_;
				gchar* _tmp24_;
				gchar* _tmp25_;
				_param_index = _param_index + 1;
				_tmp13_ = _param_index;
				_tmp14_ = _param_size;
				if (!(_tmp13_ < _tmp14_)) {
					break;
				}
				_tmp15_ = _param_list;
				_tmp16_ = vala_list_get (_tmp15_, _param_index);
				param = (ValaParameter*) _tmp16_;
				_tmp17_ = args;
				_tmp18_ = valabind_writer_sep ((ValabindWriter*) self, _tmp17_, ", ");
				_tmp19_ = _tmp18_;
				_tmp20_ = param;
				_tmp21_ = vala_variable_get_variable_type ((ValaVariable*) _tmp20_);
				_tmp22_ = _tmp21_;
				_tmp23_ = node_ffi_writer_type_name (self, _tmp22_, FALSE);
				_tmp24_ = _tmp23_;
				_tmp25_ = g_strconcat (_tmp19_, _tmp24_, NULL);
				_g_free0 (args);
				args = _tmp25_;
				_g_free0 (_tmp24_);
				_g_free0 (_tmp19_);
				_vala_code_node_unref0 (param);
			}
		}
		_tmp26_ = ret;
		_tmp27_ = args;
		_tmp28_ = g_strdup_printf ("_.delegate(%s, [%s])", _tmp26_, _tmp27_);
		result = _tmp28_;
		_g_free0 (args);
		_g_free0 (ret);
		_vala_code_node_unref0 (_delegate);
		return result;
	}
	if (G_TYPE_CHECK_INSTANCE_TYPE (type, VALA_TYPE_POINTER_TYPE)) {
		ValaPointerType* pointer = NULL;
		ValaPointerType* _tmp29_;
		ValaPointerType* _tmp30_;
		ValaDataType* _tmp31_;
		ValaDataType* _tmp32_;
		gchar* _tmp33_;
		gchar* _tmp34_;
		gchar* _tmp35_;
		gchar* _tmp36_;
		gchar* _tmp37_;
		gchar* _tmp38_;
		_tmp29_ = _vala_code_node_ref0 (G_TYPE_CHECK_INSTANCE_CAST (type, VALA_TYPE_POINTER_TYPE, ValaPointerType));
		pointer = _tmp29_;
		_tmp30_ = pointer;
		_tmp31_ = vala_pointer_type_get_base_type (_tmp30_);
		_tmp32_ = _tmp31_;
		_tmp33_ = node_ffi_writer_type_name (self, _tmp32_, TRUE);
		_tmp34_ = _tmp33_;
		_tmp35_ = g_strconcat ("_.ptr(", _tmp34_, NULL);
		_tmp36_ = _tmp35_;
		_tmp37_ = g_strconcat (_tmp36_, ")", NULL);
		_tmp38_ = _tmp37_;
		_g_free0 (_tmp36_);
		_g_free0 (_tmp34_);
		result = _tmp38_;
		_vala_code_node_unref0 (pointer);
		return result;
	}
	if (G_TYPE_CHECK_INSTANCE_TYPE (type, VALA_TYPE_ARRAY_TYPE)) {
		ValaArrayType* array = NULL;
		ValaArrayType* _tmp39_;
		gchar* element = NULL;
		ValaArrayType* _tmp40_;
		ValaDataType* _tmp41_;
		ValaDataType* _tmp42_;
		gchar* _tmp43_;
		gint len = 0;
		ValaArrayType* _tmp44_;
		const gchar* _tmp50_;
		gchar* _tmp51_;
		gchar* _tmp52_;
		gchar* _tmp53_;
		gchar* _tmp54_;
		gchar* _tmp55_;
		gchar* _tmp56_;
		_tmp39_ = _vala_code_node_ref0 (G_TYPE_CHECK_INSTANCE_TYPE (type, VALA_TYPE_ARRAY_TYPE) ? ((ValaArrayType*) type) : NULL);
		array = _tmp39_;
		_tmp40_ = array;
		_tmp41_ = vala_array_type_get_element_type (_tmp40_);
		_tmp42_ = _tmp41_;
		_tmp43_ = node_ffi_writer_type_name (self, _tmp42_, FALSE);
		element = _tmp43_;
		_tmp44_ = array;
		len = array_length (_tmp44_);
		if (len < 0) {
			const gchar* _tmp45_;
			gchar* _tmp46_;
			gchar* _tmp47_;
			gchar* _tmp48_;
			gchar* _tmp49_;
			_tmp45_ = element;
			_tmp46_ = g_strconcat ("_.ptr(", _tmp45_, NULL);
			_tmp47_ = _tmp46_;
			_tmp48_ = g_strconcat (_tmp47_, ")", NULL);
			_tmp49_ = _tmp48_;
			_g_free0 (_tmp47_);
			result = _tmp49_;
			_g_free0 (element);
			_vala_code_node_unref0 (array);
			return result;
		}
		_tmp50_ = element;
		_tmp51_ = g_strconcat ("_.array(", _tmp50_, NULL);
		_tmp52_ = _tmp51_;
		_tmp53_ = g_strdup_printf (", %d)", len);
		_tmp54_ = _tmp53_;
		_tmp55_ = g_strconcat (_tmp52_, _tmp54_, NULL);
		_tmp56_ = _tmp55_;
		_g_free0 (_tmp54_);
		_g_free0 (_tmp52_);
		result = _tmp56_;
		_g_free0 (element);
		_vala_code_node_unref0 (array);
		return result;
	}
	if (!ignoreRef) {
		_tmp57_ = G_TYPE_CHECK_INSTANCE_TYPE (type, VALA_TYPE_REFERENCE_TYPE);
	} else {
		_tmp57_ = FALSE;
	}
	if (_tmp57_) {
		gchar* unref_type = NULL;
		gchar* _tmp58_;
		const gchar* _tmp59_;
		const gchar* _tmp60_;
		gchar* _tmp61_;
		gchar* _tmp62_;
		gchar* _tmp63_;
		gchar* _tmp64_;
		_tmp58_ = node_ffi_writer_type_name (self, type, TRUE);
		unref_type = _tmp58_;
		_tmp59_ = unref_type;
		if (g_strcmp0 (_tmp59_, "_.CString") == 0) {
			result = unref_type;
			return result;
		}
		_tmp60_ = unref_type;
		_tmp61_ = g_strconcat ("_.ref(", _tmp60_, NULL);
		_tmp62_ = _tmp61_;
		_tmp63_ = g_strconcat (_tmp62_, ")", NULL);
		_tmp64_ = _tmp63_;
		_g_free0 (_tmp62_);
		result = _tmp64_;
		_g_free0 (unref_type);
		return result;
	}
	_tmp65_ = g_strdup ("");
	generic = _tmp65_;
	{
		ValaList* _t_list = NULL;
		ValaList* _tmp66_;
		gint _t_size = 0;
		ValaList* _tmp67_;
		gint _tmp68_;
		gint _tmp69_;
		gint _t_index = 0;
		_tmp66_ = vala_data_type_get_type_arguments (type);
		_t_list = _tmp66_;
		_tmp67_ = _t_list;
		_tmp68_ = vala_collection_get_size ((ValaCollection*) _tmp67_);
		_tmp69_ = _tmp68_;
		_t_size = _tmp69_;
		_t_index = -1;
		while (TRUE) {
			gint _tmp70_;
			gint _tmp71_;
			ValaDataType* t = NULL;
			ValaList* _tmp72_;
			gpointer _tmp73_;
			const gchar* _tmp74_;
			gchar* _tmp75_;
			gchar* _tmp76_;
			ValaDataType* _tmp77_;
			gchar* _tmp78_;
			gchar* _tmp79_;
			gchar* _tmp80_;
			_t_index = _t_index + 1;
			_tmp70_ = _t_index;
			_tmp71_ = _t_size;
			if (!(_tmp70_ < _tmp71_)) {
				break;
			}
			_tmp72_ = _t_list;
			_tmp73_ = vala_list_get (_tmp72_, _t_index);
			t = (ValaDataType*) _tmp73_;
			_tmp74_ = generic;
			_tmp75_ = valabind_writer_sep ((ValabindWriter*) self, _tmp74_, ", ");
			_tmp76_ = _tmp75_;
			_tmp77_ = t;
			_tmp78_ = node_ffi_writer_type_name (self, _tmp77_, FALSE);
			_tmp79_ = _tmp78_;
			_tmp80_ = g_strconcat (_tmp76_, _tmp79_, NULL);
			_g_free0 (generic);
			generic = _tmp80_;
			_g_free0 (_tmp79_);
			_g_free0 (_tmp76_);
			_vala_code_node_unref0 (t);
		}
	}
	_tmp81_ = vala_code_node_to_string ((ValaCodeNode*) type);
	_type = _tmp81_;
	_tmp82_ = self->priv->ns_pfx;
	_tmp83_ = g_strdup (_tmp82_);
	local_ns_pfx = _tmp83_;
	_tmp85_ = vala_data_type_get_type_symbol (type);
	_tmp86_ = _tmp85_;
	if (_tmp86_ != NULL) {
		ValaTypeSymbol* _tmp87_;
		ValaTypeSymbol* _tmp88_;
		ValaSymbol* _tmp89_;
		ValaSymbol* _tmp90_;
		_tmp87_ = vala_data_type_get_type_symbol (type);
		_tmp88_ = _tmp87_;
		_tmp89_ = vala_symbol_get_parent_symbol ((ValaSymbol*) _tmp88_);
		_tmp90_ = _tmp89_;
		_tmp84_ = G_TYPE_CHECK_INSTANCE_TYPE (_tmp90_, VALA_TYPE_NAMESPACE);
	} else {
		_tmp84_ = FALSE;
	}
	if (_tmp84_) {
		ValaNamespace* local_ns = NULL;
		ValaTypeSymbol* _tmp91_;
		ValaTypeSymbol* _tmp92_;
		ValaSymbol* _tmp93_;
		ValaSymbol* _tmp94_;
		ValaNamespace* _tmp95_;
		ValaNamespace* _tmp96_;
		_tmp91_ = vala_data_type_get_type_symbol (type);
		_tmp92_ = _tmp91_;
		_tmp93_ = vala_symbol_get_parent_symbol ((ValaSymbol*) _tmp92_);
		_tmp94_ = _tmp93_;
		_tmp95_ = _vala_code_node_ref0 (G_TYPE_CHECK_INSTANCE_CAST (_tmp94_, VALA_TYPE_NAMESPACE, ValaNamespace));
		local_ns = _tmp95_;
		_tmp96_ = local_ns;
		if (valabind_writer_use_namespace ((ValabindWriter*) self, _tmp96_)) {
			ValaNamespace* _tmp97_;
			gchar* _tmp98_;
			gchar* _tmp99_;
			gchar* _tmp100_;
			_tmp97_ = local_ns;
			_tmp98_ = vala_symbol_get_full_name ((ValaSymbol*) _tmp97_);
			_tmp99_ = _tmp98_;
			_tmp100_ = g_strconcat (_tmp99_, ".", NULL);
			_g_free0 (local_ns_pfx);
			local_ns_pfx = _tmp100_;
			_g_free0 (_tmp99_);
		}
		_vala_code_node_unref0 (local_ns);
	}
	_tmp101_ = _type;
	_tmp103_ = _tmp102_ = g_strsplit (_tmp101_, "<", 2);
	_tmp104_ = _tmp103_;
	_tmp104__length1 = _vala_array_length (_tmp102_);
	_tmp105_ = _tmp104_[0];
	_tmp106_ = g_strdup (_tmp105_);
	_g_free0 (_type);
	_type = _tmp106_;
	_tmp104_ = (_vala_array_free (_tmp104_, _tmp104__length1, (GDestroyNotify) g_free), NULL);
	_tmp107_ = _type;
	_tmp108_ = local_ns_pfx;
	_tmp109_ = string_replace (_tmp107_, _tmp108_, "");
	_tmp110_ = _tmp109_;
	_tmp111_ = string_replace (_tmp110_, ".", "");
	_g_free0 (_type);
	_type = _tmp111_;
	_g_free0 (_tmp110_);
	_tmp112_ = _type;
	_tmp113_ = string_replace (_tmp112_, "?", "");
	_g_free0 (_type);
	_type = _tmp113_;
	_tmp114_ = _type;
	_tmp115_ = string_replace (_tmp114_, "unsigned ", "u");
	_g_free0 (_type);
	_type = _tmp115_;
	_tmp116_ = _type;
	_tmp117_ = _tmp116_;
	_tmp119_ = (NULL == _tmp117_) ? 0 : g_quark_from_string (_tmp117_);
	if ((_tmp119_ == ((0 != _tmp118_label0) ? _tmp118_label0 : (_tmp118_label0 = g_quark_from_static_string ("gconstpointer")))) || (_tmp119_ == ((0 != _tmp118_label1) ? _tmp118_label1 : (_tmp118_label1 = g_quark_from_static_string ("gpointer"))))) {
		switch (0) {
			default:
			{
				gchar* _tmp120_;
				_tmp120_ = g_strdup ("_.ptr(_.void)");
				result = _tmp120_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if (_tmp119_ == ((0 != _tmp118_label2) ? _tmp118_label2 : (_tmp118_label2 = g_quark_from_static_string ("gboolean")))) {
		switch (0) {
			default:
			{
				gchar* _tmp121_;
				_tmp121_ = g_strdup ("_.bool");
				result = _tmp121_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if (_tmp119_ == ((0 != _tmp118_label3) ? _tmp118_label3 : (_tmp118_label3 = g_quark_from_static_string ("gchar")))) {
		switch (0) {
			default:
			{
				gchar* _tmp122_;
				_tmp122_ = g_strdup ("_.char");
				result = _tmp122_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if (_tmp119_ == ((0 != _tmp118_label4) ? _tmp118_label4 : (_tmp118_label4 = g_quark_from_static_string ("gint")))) {
		switch (0) {
			default:
			{
				gchar* _tmp123_;
				_tmp123_ = g_strdup ("_.int");
				result = _tmp123_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if (_tmp119_ == ((0 != _tmp118_label5) ? _tmp118_label5 : (_tmp118_label5 = g_quark_from_static_string ("guint")))) {
		switch (0) {
			default:
			{
				gchar* _tmp124_;
				_tmp124_ = g_strdup ("_.uint");
				result = _tmp124_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if (_tmp119_ == ((0 != _tmp118_label6) ? _tmp118_label6 : (_tmp118_label6 = g_quark_from_static_string ("glong")))) {
		switch (0) {
			default:
			{
				gchar* _tmp125_;
				_tmp125_ = g_strdup ("_.long");
				result = _tmp125_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if ((_tmp119_ == ((0 != _tmp118_label7) ? _tmp118_label7 : (_tmp118_label7 = g_quark_from_static_string ("ut8")))) || (_tmp119_ == ((0 != _tmp118_label8) ? _tmp118_label8 : (_tmp118_label8 = g_quark_from_static_string ("guint8"))))) {
		switch (0) {
			default:
			{
				gchar* _tmp126_;
				_tmp126_ = g_strdup ("_.uint8");
				result = _tmp126_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if ((_tmp119_ == ((0 != _tmp118_label9) ? _tmp118_label9 : (_tmp118_label9 = g_quark_from_static_string ("ut16")))) || (_tmp119_ == ((0 != _tmp118_label10) ? _tmp118_label10 : (_tmp118_label10 = g_quark_from_static_string ("guint16"))))) {
		switch (0) {
			default:
			{
				gchar* _tmp127_;
				_tmp127_ = g_strdup ("_.uint16");
				result = _tmp127_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if ((_tmp119_ == ((0 != _tmp118_label11) ? _tmp118_label11 : (_tmp118_label11 = g_quark_from_static_string ("st32")))) || (_tmp119_ == ((0 != _tmp118_label12) ? _tmp118_label12 : (_tmp118_label12 = g_quark_from_static_string ("gint32"))))) {
		switch (0) {
			default:
			{
				gchar* _tmp128_;
				_tmp128_ = g_strdup ("_.int32");
				result = _tmp128_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if ((_tmp119_ == ((0 != _tmp118_label13) ? _tmp118_label13 : (_tmp118_label13 = g_quark_from_static_string ("ut32")))) || (_tmp119_ == ((0 != _tmp118_label14) ? _tmp118_label14 : (_tmp118_label14 = g_quark_from_static_string ("guint32"))))) {
		switch (0) {
			default:
			{
				gchar* _tmp129_;
				_tmp129_ = g_strdup ("_.uint32");
				result = _tmp129_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if ((_tmp119_ == ((0 != _tmp118_label15) ? _tmp118_label15 : (_tmp118_label15 = g_quark_from_static_string ("st64")))) || (_tmp119_ == ((0 != _tmp118_label16) ? _tmp118_label16 : (_tmp118_label16 = g_quark_from_static_string ("gint64"))))) {
		switch (0) {
			default:
			{
				gchar* _tmp130_;
				_tmp130_ = g_strdup ("_.int64");
				result = _tmp130_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if ((_tmp119_ == ((0 != _tmp118_label17) ? _tmp118_label17 : (_tmp118_label17 = g_quark_from_static_string ("ut64")))) || (_tmp119_ == ((0 != _tmp118_label18) ? _tmp118_label18 : (_tmp118_label18 = g_quark_from_static_string ("guint64"))))) {
		switch (0) {
			default:
			{
				gchar* _tmp131_;
				_tmp131_ = g_strdup ("_.uint64");
				result = _tmp131_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if (_tmp119_ == ((0 != _tmp118_label19) ? _tmp118_label19 : (_tmp118_label19 = g_quark_from_static_string ("gfloat")))) {
		switch (0) {
			default:
			{
				gchar* _tmp132_;
				_tmp132_ = g_strdup ("_.float");
				result = _tmp132_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if (_tmp119_ == ((0 != _tmp118_label20) ? _tmp118_label20 : (_tmp118_label20 = g_quark_from_static_string ("gdouble")))) {
		switch (0) {
			default:
			{
				gchar* _tmp133_;
				_tmp133_ = g_strdup ("_.double");
				result = _tmp133_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	} else if (_tmp119_ == ((0 != _tmp118_label21) ? _tmp118_label21 : (_tmp118_label21 = g_quark_from_static_string ("string")))) {
		switch (0) {
			default:
			{
				gchar* _tmp134_;
				_tmp134_ = g_strdup ("_.CString");
				result = _tmp134_;
				_g_free0 (local_ns_pfx);
				_g_free0 (_type);
				_g_free0 (generic);
				return result;
			}
		}
	}
	_tmp135_ = _type;
	_tmp136_ = g_strconcat ("_.", _tmp135_, NULL);
	_g_free0 (_type);
	_type = _tmp136_;
	_tmp137_ = generic;
	if (g_strcmp0 (_tmp137_, "") != 0) {
		const gchar* _tmp138_;
		const gchar* _tmp139_;
		gchar* _tmp140_;
		gchar* _tmp141_;
		gchar* _tmp142_;
		gchar* _tmp143_;
		gchar* _tmp144_;
		_tmp138_ = _type;
		_tmp139_ = generic;
		_tmp140_ = g_strconcat ("(", _tmp139_, NULL);
		_tmp141_ = _tmp140_;
		_tmp142_ = g_strconcat (_tmp141_, ")", NULL);
		_tmp143_ = _tmp142_;
		_tmp144_ = g_strconcat (_tmp138_, _tmp143_, NULL);
		_g_free0 (_type);
		_type = _tmp144_;
		_g_free0 (_tmp143_);
		_g_free0 (_tmp141_);
	}
	result = _type;
	_g_free0 (local_ns_pfx);
	_g_free0 (generic);
	return result;
}

static void
node_ffi_writer_visit_enum (NodeFFIWriter* self,
                            ValaEnum* e,
                            const gchar* pfx)
{
	gchar* _tmp0_;
	gchar* _tmp1_;
	gchar* _tmp2_;
	gchar* _tmp3_;
	g_return_if_fail (self != NULL);
	g_return_if_fail (e != NULL);
	g_return_if_fail (pfx != NULL);
	valabind_writer_add_includes ((ValabindWriter*) self, (ValaSymbol*) e);
	_tmp0_ = vala_symbol_get_full_name ((ValaSymbol*) e);
	_tmp1_ = _tmp0_;
	_tmp2_ = g_strconcat (">\x1b[1menum\x1b[0m ", _tmp1_, NULL);
	_tmp3_ = _tmp2_;
	notice (_tmp3_);
	_g_free0 (_tmp3_);
	_g_free0 (_tmp1_);
	if (g_strcmp0 (pfx, "") == 0) {
		const gchar* _tmp4_;
		const gchar* _tmp5_;
		const gchar* _tmp6_;
		gchar* _tmp7_;
		gchar* _tmp8_;
		gchar* _tmp9_;
		_tmp4_ = self->priv->enum_fmt;
		_tmp5_ = vala_symbol_get_name ((ValaSymbol*) e);
		_tmp6_ = _tmp5_;
		_tmp7_ = g_strdup_printf ("exports.%s = {}/*types.Enum*/;\\n", _tmp6_);
		_tmp8_ = _tmp7_;
		_tmp9_ = g_strconcat (_tmp4_, _tmp8_, NULL);
		_g_free0 (self->priv->enum_fmt);
		self->priv->enum_fmt = _tmp9_;
		_g_free0 (_tmp8_);
	} else {
		const gchar* _tmp10_;
		gchar* _tmp11_;
		gchar* _tmp12_;
		const gchar* _tmp13_;
		const gchar* _tmp14_;
		gchar* _tmp15_;
		gchar* _tmp16_;
		gchar* _tmp17_;
		_tmp10_ = self->priv->bind;
		_tmp11_ = valabind_writer_sep ((ValabindWriter*) self, _tmp10_, ",");
		_tmp12_ = _tmp11_;
		_tmp13_ = vala_symbol_get_name ((ValaSymbol*) e);
		_tmp14_ = _tmp13_;
		_tmp15_ = g_strdup_printf ("\n\t\t$%s: {}/*types.Enum*/", _tmp14_);
		_tmp16_ = _tmp15_;
		_tmp17_ = g_strconcat (_tmp12_, _tmp16_, NULL);
		_g_free0 (self->priv->bind);
		self->priv->bind = _tmp17_;
		_g_free0 (_tmp16_);
		_g_free0 (_tmp12_);
	}
	{
		ValaList* _v_list = NULL;
		ValaList* _tmp18_;
		gint _v_size = 0;
		ValaList* _tmp19_;
		gint _tmp20_;
		gint _tmp21_;
		gint _v_index = 0;
		_tmp18_ = vala_enum_get_values (e);
		_v_list = _tmp18_;
		_tmp19_ = _v_list;
		_tmp20_ = vala_collection_get_size ((ValaCollection*) _tmp19_);
		_tmp21_ = _tmp20_;
		_v_size = _tmp21_;
		_v_index = -1;
		while (TRUE) {
			gint _tmp22_;
			gint _tmp23_;
			ValaEnumValue* v = NULL;
			ValaList* _tmp24_;
			gpointer _tmp25_;
			const gchar* _tmp26_;
			const gchar* _tmp27_;
			const gchar* _tmp28_;
			ValaEnumValue* _tmp29_;
			const gchar* _tmp30_;
			const gchar* _tmp31_;
			gchar* _tmp32_;
			gchar* _tmp33_;
			gchar* _tmp34_;
			const gchar* _tmp35_;
			ValaEnumValue* _tmp36_;
			gchar* _tmp37_;
			gchar* _tmp38_;
			gchar* _tmp39_;
			gchar* _tmp40_;
			gchar* _tmp41_;
			_v_index = _v_index + 1;
			_tmp22_ = _v_index;
			_tmp23_ = _v_size;
			if (!(_tmp22_ < _tmp23_)) {
				break;
			}
			_tmp24_ = _v_list;
			_tmp25_ = vala_list_get (_tmp24_, _v_index);
			v = (ValaEnumValue*) _tmp25_;
			_tmp26_ = self->priv->enum_fmt;
			_tmp27_ = vala_symbol_get_name ((ValaSymbol*) e);
			_tmp28_ = _tmp27_;
			_tmp29_ = v;
			_tmp30_ = vala_symbol_get_name ((ValaSymbol*) _tmp29_);
			_tmp31_ = _tmp30_;
			_tmp32_ = g_strdup_printf ("exports.%s%s.%s = %%d;\\n", pfx, _tmp28_, _tmp31_);
			_tmp33_ = _tmp32_;
			_tmp34_ = g_strconcat (_tmp26_, _tmp33_, NULL);
			_g_free0 (self->priv->enum_fmt);
			self->priv->enum_fmt = _tmp34_;
			_g_free0 (_tmp33_);
			_tmp35_ = self->priv->enum_vals;
			_tmp36_ = v;
			_tmp37_ = vala_get_ccode_name ((ValaCodeNode*) _tmp36_);
			_tmp38_ = _tmp37_;
			_tmp39_ = g_strconcat (",", _tmp38_, NULL);
			_tmp40_ = _tmp39_;
			_tmp41_ = g_strconcat (_tmp35_, _tmp40_, NULL);
			_g_free0 (self->priv->enum_vals);
			self->priv->enum_vals = _tmp41_;
			_g_free0 (_tmp40_);
			_g_free0 (_tmp38_);
			_vala_code_node_unref0 (v);
		}
	}
}

static void
node_ffi_writer_real_visit_struct (ValaCodeVisitor* base,
                                   ValaStruct* s)
{
	NodeFFIWriter * self;
	gchar* _tmp0_;
	gchar* _tmp1_;
	gchar* _tmp2_;
	gchar* _tmp3_;
	gchar* name = NULL;
	gchar* _tmp4_;
	gchar* _tmp5_;
	const gchar* _tmp6_;
	gchar* _tmp7_;
	gchar* _tmp8_;
	gchar* _tmp9_;
	gchar* _tmp10_;
	const gchar* _tmp11_;
	gchar* _tmp12_;
	gchar* _tmp13_;
	const gchar* _tmp14_;
	gchar* _tmp15_;
	gchar* _tmp16_;
	gchar* _tmp17_;
	gint visible_methods = 0;
	const gchar* _tmp54_;
	gchar* _tmp55_;
	gchar* _tmp56_;
	gchar* _tmp57_;
	self = (NodeFFIWriter*) base;
	g_return_if_fail (s != NULL);
	valabind_writer_add_includes ((ValabindWriter*) self, (ValaSymbol*) s);
	_tmp0_ = vala_symbol_get_full_name ((ValaSymbol*) s);
	_tmp1_ = _tmp0_;
	_tmp2_ = g_strconcat (">\x1b[1mstruct\x1b[0m ", _tmp1_, NULL);
	_tmp3_ = _tmp2_;
	notice (_tmp3_);
	_g_free0 (_tmp3_);
	_g_free0 (_tmp1_);
	_tmp4_ = vala_symbol_get_full_name ((ValaSymbol*) s);
	_tmp5_ = _tmp4_;
	_tmp6_ = self->priv->ns_pfx;
	_tmp7_ = string_replace (_tmp5_, _tmp6_, "");
	_tmp8_ = _tmp7_;
	_tmp9_ = string_replace (_tmp8_, ".", "");
	_tmp10_ = _tmp9_;
	_g_free0 (_tmp8_);
	_g_free0 (_tmp5_);
	name = _tmp10_;
	_tmp11_ = self->priv->bind;
	_tmp12_ = valabind_writer_sep ((ValabindWriter*) self, _tmp11_, ",\n");
	_tmp13_ = _tmp12_;
	_tmp14_ = name;
	_tmp15_ = g_strdup_printf ("\t%s: function() {return [{", _tmp14_);
	_tmp16_ = _tmp15_;
	_tmp17_ = g_strconcat (_tmp13_, _tmp16_, NULL);
	_g_free0 (self->priv->bind);
	self->priv->bind = _tmp17_;
	_g_free0 (_tmp16_);
	_g_free0 (_tmp13_);
	{
		ValaList* _f_list = NULL;
		ValaList* _tmp18_;
		gint _f_size = 0;
		ValaList* _tmp19_;
		gint _tmp20_;
		gint _tmp21_;
		gint _f_index = 0;
		_tmp18_ = vala_struct_get_fields (s);
		_f_list = _tmp18_;
		_tmp19_ = _f_list;
		_tmp20_ = vala_collection_get_size ((ValaCollection*) _tmp19_);
		_tmp21_ = _tmp20_;
		_f_size = _tmp21_;
		_f_index = -1;
		while (TRUE) {
			gint _tmp22_;
			gint _tmp23_;
			ValaField* f = NULL;
			ValaList* _tmp24_;
			gpointer _tmp25_;
			ValaField* _tmp26_;
			_f_index = _f_index + 1;
			_tmp22_ = _f_index;
			_tmp23_ = _f_size;
			if (!(_tmp22_ < _tmp23_)) {
				break;
			}
			_tmp24_ = _f_list;
			_tmp25_ = vala_list_get (_tmp24_, _f_index);
			f = (ValaField*) _tmp25_;
			_tmp26_ = f;
			vala_code_node_accept ((ValaCodeNode*) _tmp26_, (ValaCodeVisitor*) self);
			_vala_code_node_unref0 (f);
		}
	}
	visible_methods = 0;
	{
		ValaList* _m_list = NULL;
		ValaList* _tmp27_;
		gint _m_size = 0;
		ValaList* _tmp28_;
		gint _tmp29_;
		gint _tmp30_;
		gint _m_index = 0;
		_tmp27_ = vala_struct_get_methods (s);
		_m_list = _tmp27_;
		_tmp28_ = _m_list;
		_tmp29_ = vala_collection_get_size ((ValaCollection*) _tmp28_);
		_tmp30_ = _tmp29_;
		_m_size = _tmp30_;
		_m_index = -1;
		while (TRUE) {
			gint _tmp31_;
			gint _tmp32_;
			ValaMethod* m = NULL;
			ValaList* _tmp33_;
			gpointer _tmp34_;
			gboolean _tmp35_ = FALSE;
			ValaMethod* _tmp36_;
			_m_index = _m_index + 1;
			_tmp31_ = _m_index;
			_tmp32_ = _m_size;
			if (!(_tmp31_ < _tmp32_)) {
				break;
			}
			_tmp33_ = _m_list;
			_tmp34_ = vala_list_get (_tmp33_, _m_index);
			m = (ValaMethod*) _tmp34_;
			_tmp36_ = m;
			if (!vala_symbol_is_private_symbol ((ValaSymbol*) _tmp36_)) {
				ValaMethod* _tmp37_;
				const gchar* _tmp38_;
				const gchar* _tmp39_;
				_tmp37_ = m;
				_tmp38_ = vala_symbol_get_name ((ValaSymbol*) _tmp37_);
				_tmp39_ = _tmp38_;
				_tmp35_ = g_strcmp0 (_tmp39_, "cast") != 0;
			} else {
				_tmp35_ = FALSE;
			}
			if (_tmp35_) {
				gint _tmp40_;
				_tmp40_ = visible_methods;
				visible_methods = _tmp40_ + 1;
			}
			_vala_code_node_unref0 (m);
		}
	}
	if (visible_methods > 0) {
		const gchar* _tmp41_;
		gchar* _tmp42_;
		gchar* _tmp43_;
		gchar* _tmp44_;
		_tmp41_ = self->priv->bind;
		_tmp42_ = valabind_writer_sep ((ValabindWriter*) self, _tmp41_, "\n\t");
		_tmp43_ = _tmp42_;
		_tmp44_ = g_strconcat (_tmp43_, "}, {", NULL);
		_g_free0 (self->priv->bind);
		self->priv->bind = _tmp44_;
		_g_free0 (_tmp43_);
		{
			ValaList* _m_list = NULL;
			ValaList* _tmp45_;
			gint _m_size = 0;
			ValaList* _tmp46_;
			gint _tmp47_;
			gint _tmp48_;
			gint _m_index = 0;
			_tmp45_ = vala_struct_get_methods (s);
			_m_list = _tmp45_;
			_tmp46_ = _m_list;
			_tmp47_ = vala_collection_get_size ((ValaCollection*) _tmp46_);
			_tmp48_ = _tmp47_;
			_m_size = _tmp48_;
			_m_index = -1;
			while (TRUE) {
				gint _tmp49_;
				gint _tmp50_;
				ValaMethod* m = NULL;
				ValaList* _tmp51_;
				gpointer _tmp52_;
				ValaMethod* _tmp53_;
				_m_index = _m_index + 1;
				_tmp49_ = _m_index;
				_tmp50_ = _m_size;
				if (!(_tmp49_ < _tmp50_)) {
					break;
				}
				_tmp51_ = _m_list;
				_tmp52_ = vala_list_get (_tmp51_, _m_index);
				m = (ValaMethod*) _tmp52_;
				_tmp53_ = m;
				vala_code_node_accept ((ValaCodeNode*) _tmp53_, (ValaCodeVisitor*) self);
				_vala_code_node_unref0 (m);
			}
		}
	}
	_tmp54_ = self->priv->bind;
	_tmp55_ = valabind_writer_sep ((ValabindWriter*) self, _tmp54_, "\n\t");
	_tmp56_ = _tmp55_;
	_tmp57_ = g_strconcat (_tmp56_, "}];}", NULL);
	_g_free0 (self->priv->bind);
	self->priv->bind = _tmp57_;
	_g_free0 (_tmp56_);
	_g_free0 (name);
}

static void
node_ffi_writer_real_visit_class (ValaCodeVisitor* base,
                                  ValaClass* c)
{
	NodeFFIWriter * self;
	gboolean is_generic = FALSE;
	gchar* _tmp0_;
	gchar* _tmp1_;
	gchar* _tmp2_;
	gchar* _tmp3_;
	gchar* name = NULL;
	gchar* _tmp4_;
	gchar* _tmp5_;
	const gchar* _tmp6_;
	gchar* _tmp7_;
	gchar* _tmp8_;
	gchar* _tmp9_;
	gchar* _tmp10_;
	const gchar* _tmp29_;
	gchar* _tmp30_;
	gchar* _tmp31_;
	const gchar* _tmp32_;
	gchar* _tmp33_;
	gchar* _tmp34_;
	gchar* _tmp35_;
	const gchar* _tmp51_;
	gchar* _tmp52_;
	const gchar* _tmp62_;
	gchar* _tmp63_;
	gchar* _tmp64_;
	gchar* _tmp65_;
	gchar* freefun = NULL;
	gboolean _tmp80_ = FALSE;
	const gchar* _tmp81_;
	const gchar* _tmp102_;
	gchar* _tmp103_;
	gchar* _tmp104_;
	gchar* _tmp105_;
	self = (NodeFFIWriter*) base;
	g_return_if_fail (c != NULL);
	is_generic = FALSE;
	valabind_writer_add_includes ((ValabindWriter*) self, (ValaSymbol*) c);
	_tmp0_ = vala_symbol_get_full_name ((ValaSymbol*) c);
	_tmp1_ = _tmp0_;
	_tmp2_ = g_strconcat (">\x1b[1mclass\x1b[0m ", _tmp1_, NULL);
	_tmp3_ = _tmp2_;
	notice (_tmp3_);
	_g_free0 (_tmp3_);
	_g_free0 (_tmp1_);
	_tmp4_ = vala_symbol_get_full_name ((ValaSymbol*) c);
	_tmp5_ = _tmp4_;
	_tmp6_ = self->priv->ns_pfx;
	_tmp7_ = string_replace (_tmp5_, _tmp6_, "");
	_tmp8_ = _tmp7_;
	_tmp9_ = string_replace (_tmp8_, ".", "");
	_tmp10_ = _tmp9_;
	_g_free0 (_tmp8_);
	_g_free0 (_tmp5_);
	name = _tmp10_;
	{
		ValaList* _s_list = NULL;
		ValaList* _tmp11_;
		gint _s_size = 0;
		ValaList* _tmp12_;
		gint _tmp13_;
		gint _tmp14_;
		gint _s_index = 0;
		_tmp11_ = vala_object_type_symbol_get_structs ((ValaObjectTypeSymbol*) c);
		_s_list = _tmp11_;
		_tmp12_ = _s_list;
		_tmp13_ = vala_collection_get_size ((ValaCollection*) _tmp12_);
		_tmp14_ = _tmp13_;
		_s_size = _tmp14_;
		_s_index = -1;
		while (TRUE) {
			gint _tmp15_;
			gint _tmp16_;
			ValaStruct* s = NULL;
			ValaList* _tmp17_;
			gpointer _tmp18_;
			ValaStruct* _tmp19_;
			_s_index = _s_index + 1;
			_tmp15_ = _s_index;
			_tmp16_ = _s_size;
			if (!(_tmp15_ < _tmp16_)) {
				break;
			}
			_tmp17_ = _s_list;
			_tmp18_ = vala_list_get (_tmp17_, _s_index);
			s = (ValaStruct*) _tmp18_;
			_tmp19_ = s;
			vala_code_node_accept ((ValaCodeNode*) _tmp19_, (ValaCodeVisitor*) self);
			_vala_code_node_unref0 (s);
		}
	}
	{
		ValaList* _k_list = NULL;
		ValaList* _tmp20_;
		gint _k_size = 0;
		ValaList* _tmp21_;
		gint _tmp22_;
		gint _tmp23_;
		gint _k_index = 0;
		_tmp20_ = vala_object_type_symbol_get_classes ((ValaObjectTypeSymbol*) c);
		_k_list = _tmp20_;
		_tmp21_ = _k_list;
		_tmp22_ = vala_collection_get_size ((ValaCollection*) _tmp21_);
		_tmp23_ = _tmp22_;
		_k_size = _tmp23_;
		_k_index = -1;
		while (TRUE) {
			gint _tmp24_;
			gint _tmp25_;
			ValaClass* k = NULL;
			ValaList* _tmp26_;
			gpointer _tmp27_;
			ValaClass* _tmp28_;
			_k_index = _k_index + 1;
			_tmp24_ = _k_index;
			_tmp25_ = _k_size;
			if (!(_tmp24_ < _tmp25_)) {
				break;
			}
			_tmp26_ = _k_list;
			_tmp27_ = vala_list_get (_tmp26_, _k_index);
			k = (ValaClass*) _tmp27_;
			_tmp28_ = k;
			vala_code_node_accept ((ValaCodeNode*) _tmp28_, (ValaCodeVisitor*) self);
			_vala_code_node_unref0 (k);
		}
	}
	_tmp29_ = self->priv->bind;
	_tmp30_ = valabind_writer_sep ((ValabindWriter*) self, _tmp29_, ",\n");
	_tmp31_ = _tmp30_;
	_tmp32_ = name;
	_tmp33_ = g_strdup_printf ("\t%s: function(", _tmp32_);
	_tmp34_ = _tmp33_;
	_tmp35_ = g_strconcat (_tmp31_, _tmp34_, NULL);
	_g_free0 (self->priv->bind);
	self->priv->bind = _tmp35_;
	_g_free0 (_tmp34_);
	_g_free0 (_tmp31_);
	{
		ValaList* _t_list = NULL;
		ValaList* _tmp36_;
		gint _t_size = 0;
		ValaList* _tmp37_;
		gint _tmp38_;
		gint _tmp39_;
		gint _t_index = 0;
		_tmp36_ = vala_object_type_symbol_get_type_parameters ((ValaObjectTypeSymbol*) c);
		_t_list = _tmp36_;
		_tmp37_ = _t_list;
		_tmp38_ = vala_collection_get_size ((ValaCollection*) _tmp37_);
		_tmp39_ = _tmp38_;
		_t_size = _tmp39_;
		_t_index = -1;
		while (TRUE) {
			gint _tmp40_;
			gint _tmp41_;
			ValaTypeParameter* t = NULL;
			ValaList* _tmp42_;
			gpointer _tmp43_;
			const gchar* _tmp44_;
			gchar* _tmp45_;
			gchar* _tmp46_;
			ValaTypeParameter* _tmp47_;
			const gchar* _tmp48_;
			const gchar* _tmp49_;
			gchar* _tmp50_;
			_t_index = _t_index + 1;
			_tmp40_ = _t_index;
			_tmp41_ = _t_size;
			if (!(_tmp40_ < _tmp41_)) {
				break;
			}
			_tmp42_ = _t_list;
			_tmp43_ = vala_list_get (_tmp42_, _t_index);
			t = (ValaTypeParameter*) _tmp43_;
			is_generic = TRUE;
			_tmp44_ = self->priv->bind;
			_tmp45_ = valabind_writer_sep ((ValabindWriter*) self, _tmp44_, ", ");
			_tmp46_ = _tmp45_;
			_tmp47_ = t;
			_tmp48_ = vala_symbol_get_name ((ValaSymbol*) _tmp47_);
			_tmp49_ = _tmp48_;
			_tmp50_ = g_strconcat (_tmp46_, _tmp49_, NULL);
			_g_free0 (self->priv->bind);
			self->priv->bind = _tmp50_;
			_g_free0 (_tmp46_);
			_vala_code_node_unref0 (t);
		}
	}
	_tmp51_ = self->priv->bind;
	_tmp52_ = g_strconcat (_tmp51_, ") {return [{", NULL);
	_g_free0 (self->priv->bind);
	self->priv->bind = _tmp52_;
	{
		ValaList* _f_list = NULL;
		ValaList* _tmp53_;
		gint _f_size = 0;
		ValaList* _tmp54_;
		gint _tmp55_;
		gint _tmp56_;
		gint _f_index = 0;
		_tmp53_ = vala_object_type_symbol_get_fields ((ValaObjectTypeSymbol*) c);
		_f_list = _tmp53_;
		_tmp54_ = _f_list;
		_tmp55_ = vala_collection_get_size ((ValaCollection*) _tmp54_);
		_tmp56_ = _tmp55_;
		_f_size = _tmp56_;
		_f_index = -1;
		while (TRUE) {
			gint _tmp57_;
			gint _tmp58_;
			ValaField* f = NULL;
			ValaList* _tmp59_;
			gpointer _tmp60_;
			ValaField* _tmp61_;
			_f_index = _f_index + 1;
			_tmp57_ = _f_index;
			_tmp58_ = _f_size;
			if (!(_tmp57_ < _tmp58_)) {
				break;
			}
			_tmp59_ = _f_list;
			_tmp60_ = vala_list_get (_tmp59_, _f_index);
			f = (ValaField*) _tmp60_;
			_tmp61_ = f;
			vala_code_node_accept ((ValaCodeNode*) _tmp61_, (ValaCodeVisitor*) self);
			_vala_code_node_unref0 (f);
		}
	}
	_tmp62_ = self->priv->bind;
	_tmp63_ = valabind_writer_sep ((ValabindWriter*) self, _tmp62_, "\n\t");
	_tmp64_ = _tmp63_;
	_tmp65_ = g_strconcat (_tmp64_, "}, {", NULL);
	_g_free0 (self->priv->bind);
	self->priv->bind = _tmp65_;
	_g_free0 (_tmp64_);
	{
		ValaList* _e_list = NULL;
		ValaList* _tmp66_;
		gint _e_size = 0;
		ValaList* _tmp67_;
		gint _tmp68_;
		gint _tmp69_;
		gint _e_index = 0;
		_tmp66_ = vala_object_type_symbol_get_enums ((ValaObjectTypeSymbol*) c);
		_e_list = _tmp66_;
		_tmp67_ = _e_list;
		_tmp68_ = vala_collection_get_size ((ValaCollection*) _tmp67_);
		_tmp69_ = _tmp68_;
		_e_size = _tmp69_;
		_e_index = -1;
		while (TRUE) {
			gint _tmp70_;
			gint _tmp71_;
			ValaEnum* e = NULL;
			ValaList* _tmp72_;
			gpointer _tmp73_;
			ValaEnum* _tmp74_;
			const gchar* _tmp75_;
			gchar* _tmp76_;
			gchar* _tmp77_;
			_e_index = _e_index + 1;
			_tmp70_ = _e_index;
			_tmp71_ = _e_size;
			if (!(_tmp70_ < _tmp71_)) {
				break;
			}
			_tmp72_ = _e_list;
			_tmp73_ = vala_list_get (_tmp72_, _e_index);
			e = (ValaEnum*) _tmp73_;
			_tmp74_ = e;
			_tmp75_ = name;
			_tmp76_ = g_strconcat (_tmp75_, ".", NULL);
			_tmp77_ = _tmp76_;
			node_ffi_writer_visit_enum (self, _tmp74_, _tmp77_);
			_g_free0 (_tmp77_);
			_vala_code_node_unref0 (e);
		}
	}
	freefun = NULL;
	if (vala_is_reference_counting ((ValaTypeSymbol*) c)) {
		gchar* _tmp78_;
		_tmp78_ = vala_get_ccode_unref_function ((ValaObjectTypeSymbol*) c);
		_g_free0 (freefun);
		freefun = _tmp78_;
	} else {
		gchar* _tmp79_;
		_tmp79_ = vala_get_ccode_free_function ((ValaTypeSymbol*) c);
		_g_free0 (freefun);
		freefun = _tmp79_;
	}
	_tmp81_ = freefun;
	if (_tmp81_ != NULL) {
		const gchar* _tmp82_;
		_tmp82_ = freefun;
		_tmp80_ = g_strcmp0 (_tmp82_, "") != 0;
	} else {
		_tmp80_ = FALSE;
	}
	if (_tmp80_) {
		const gchar* _tmp85_;
		gchar* _tmp86_;
		gchar* _tmp87_;
		const gchar* _tmp88_;
		const gchar* _tmp89_;
		gchar* _tmp90_;
		gchar* _tmp91_;
		gchar* _tmp92_;
		if (is_generic) {
			const gchar* _tmp83_;
			gchar* _tmp84_;
			_tmp83_ = name;
			_tmp84_ = g_strconcat (_tmp83_, "(G)", NULL);
			_g_free0 (name);
			name = _tmp84_;
		}
		_tmp85_ = self->priv->bind;
		_tmp86_ = valabind_writer_sep ((ValabindWriter*) self, _tmp85_, ",");
		_tmp87_ = _tmp86_;
		_tmp88_ = freefun;
		_tmp89_ = name;
		_tmp90_ = g_strdup_printf ("\n\t\tdelete: ['%s', _.void, [_.ref(_.%s)]]", _tmp88_, _tmp89_);
		_tmp91_ = _tmp90_;
		_tmp92_ = g_strconcat (_tmp87_, _tmp91_, NULL);
		_g_free0 (self->priv->bind);
		self->priv->bind = _tmp92_;
		_g_free0 (_tmp91_);
		_g_free0 (_tmp87_);
	}
	{
		ValaList* _m_list = NULL;
		ValaList* _tmp93_;
		gint _m_size = 0;
		ValaList* _tmp94_;
		gint _tmp95_;
		gint _tmp96_;
		gint _m_index = 0;
		_tmp93_ = vala_object_type_symbol_get_methods ((ValaObjectTypeSymbol*) c);
		_m_list = _tmp93_;
		_tmp94_ = _m_list;
		_tmp95_ = vala_collection_get_size ((ValaCollection*) _tmp94_);
		_tmp96_ = _tmp95_;
		_m_size = _tmp96_;
		_m_index = -1;
		while (TRUE) {
			gint _tmp97_;
			gint _tmp98_;
			ValaMethod* m = NULL;
			ValaList* _tmp99_;
			gpointer _tmp100_;
			ValaMethod* _tmp101_;
			_m_index = _m_index + 1;
			_tmp97_ = _m_index;
			_tmp98_ = _m_size;
			if (!(_tmp97_ < _tmp98_)) {
				break;
			}
			_tmp99_ = _m_list;
			_tmp100_ = vala_list_get (_tmp99_, _m_index);
			m = (ValaMethod*) _tmp100_;
			_tmp101_ = m;
			vala_code_visitor_visit_method ((ValaCodeVisitor*) self, _tmp101_);
			_vala_code_node_unref0 (m);
		}
	}
	_tmp102_ = self->priv->bind;
	_tmp103_ = valabind_writer_sep ((ValabindWriter*) self, _tmp102_, "\n\t");
	_tmp104_ = _tmp103_;
	_tmp105_ = g_strconcat (_tmp104_, "}];}", NULL);
	_g_free0 (self->priv->bind);
	self->priv->bind = _tmp105_;
	_g_free0 (_tmp104_);
	_g_free0 (freefun);
	_g_free0 (name);
}

static void
node_ffi_writer_real_visit_field (ValaCodeVisitor* base,
                                  ValaField* f)
{
	NodeFFIWriter * self;
	gchar* name = NULL;
	const gchar* _tmp0_;
	const gchar* _tmp1_;
	gchar* _tmp2_;
	const gchar* _tmp3_;
	const gchar* _tmp5_;
	gchar* _tmp6_;
	gchar* _tmp7_;
	const gchar* _tmp8_;
	ValaDataType* _tmp9_;
	ValaDataType* _tmp10_;
	gchar* _tmp11_;
	gchar* _tmp12_;
	gchar* _tmp13_;
	gchar* _tmp14_;
	gchar* _tmp15_;
	self = (NodeFFIWriter*) base;
	g_return_if_fail (f != NULL);
	_tmp0_ = vala_symbol_get_name ((ValaSymbol*) f);
	_tmp1_ = _tmp0_;
	_tmp2_ = g_strdup (_tmp1_);
	name = _tmp2_;
	_tmp3_ = name;
	if (g_strcmp0 (_tmp3_, "buffer") == 0) {
		gchar* _tmp4_;
		_tmp4_ = g_strdup ("buf");
		_g_free0 (name);
		name = _tmp4_;
	}
	_tmp5_ = self->priv->bind;
	_tmp6_ = valabind_writer_sep ((ValabindWriter*) self, _tmp5_, ",");
	_tmp7_ = _tmp6_;
	_tmp8_ = name;
	_tmp9_ = vala_variable_get_variable_type ((ValaVariable*) f);
	_tmp10_ = _tmp9_;
	_tmp11_ = node_ffi_writer_type_name (self, _tmp10_, FALSE);
	_tmp12_ = _tmp11_;
	_tmp13_ = g_strdup_printf ("\n\t\t%s: %s", _tmp8_, _tmp12_);
	_tmp14_ = _tmp13_;
	_tmp15_ = g_strconcat (_tmp7_, _tmp14_, NULL);
	_g_free0 (self->priv->bind);
	self->priv->bind = _tmp15_;
	_g_free0 (_tmp14_);
	_g_free0 (_tmp12_);
	_g_free0 (_tmp7_);
	_g_free0 (name);
}

static void
node_ffi_writer_real_visit_method (ValaCodeVisitor* base,
                                   ValaMethod* m)
{
	NodeFFIWriter * self;
	gboolean _tmp0_ = FALSE;
	ValaSymbol* parent = NULL;
	ValaSymbol* _tmp3_;
	ValaSymbol* _tmp4_;
	ValaSymbol* _tmp5_;
	gchar* cname = NULL;
	gchar* _tmp6_;
	gchar* name = NULL;
	const gchar* _tmp7_;
	const gchar* _tmp8_;
	gchar* _tmp9_;
	gboolean is_static = FALSE;
	ValaMemberBinding _tmp10_;
	ValaMemberBinding _tmp11_;
	gboolean is_constructor = FALSE;
	gboolean _tmp12_ = FALSE;
	ValaSymbol* _tmp13_;
	gboolean parent_is_class = FALSE;
	gboolean _tmp15_ = FALSE;
	ValaDataType* _tmp18_ = NULL;
	ValaParameter* _tmp19_;
	ValaParameter* _tmp20_;
	ValaDataType* this_type = NULL;
	ValaDataType* _tmp25_;
	gchar* func = NULL;
	gchar* _tmp26_;
	gboolean variadic = FALSE;
	const gchar* _tmp71_ = NULL;
	const gchar* _tmp72_;
	gchar* _tmp73_;
	const gchar* _tmp74_;
	gchar* _tmp75_;
	gchar* _tmp76_;
	const gchar* _tmp77_;
	gchar* _tmp78_;
	gboolean _tmp79_ = FALSE;
	self = (NodeFFIWriter*) base;
	g_return_if_fail (m != NULL);
	if (vala_symbol_is_private_symbol ((ValaSymbol*) m)) {
		_tmp0_ = TRUE;
	} else {
		const gchar* _tmp1_;
		const gchar* _tmp2_;
		_tmp1_ = vala_symbol_get_name ((ValaSymbol*) m);
		_tmp2_ = _tmp1_;
		_tmp0_ = g_strcmp0 (_tmp2_, "cast") == 0;
	}
	if (_tmp0_) {
		return;
	}
	valabind_writer_add_includes ((ValabindWriter*) self, (ValaSymbol*) m);
	_tmp3_ = vala_symbol_get_parent_symbol ((ValaSymbol*) m);
	_tmp4_ = _tmp3_;
	_tmp5_ = _vala_code_node_ref0 (_tmp4_);
	parent = _tmp5_;
	_tmp6_ = vala_get_ccode_name ((ValaCodeNode*) m);
	cname = _tmp6_;
	_tmp7_ = vala_symbol_get_name ((ValaSymbol*) m);
	_tmp8_ = _tmp7_;
	_tmp9_ = g_strdup (_tmp8_);
	name = _tmp9_;
	_tmp10_ = vala_method_get_binding (m);
	_tmp11_ = _tmp10_;
	is_static = (_tmp11_ & VALA_MEMBER_BINDING_STATIC) != 0;
	is_constructor = G_TYPE_CHECK_INSTANCE_TYPE (m, VALA_TYPE_CREATION_METHOD);
	_tmp13_ = parent;
	if (G_TYPE_CHECK_INSTANCE_TYPE (_tmp13_, VALA_TYPE_CLASS)) {
		_tmp12_ = TRUE;
	} else {
		ValaSymbol* _tmp14_;
		_tmp14_ = parent;
		_tmp12_ = G_TYPE_CHECK_INSTANCE_TYPE (_tmp14_, VALA_TYPE_STRUCT);
	}
	parent_is_class = _tmp12_;
	if (parent_is_class) {
		_tmp15_ = is_static;
	} else {
		_tmp15_ = FALSE;
	}
	if (_tmp15_) {
		const gchar* _tmp16_;
		gchar* _tmp17_;
		_tmp16_ = name;
		_tmp17_ = g_strconcat ("$", _tmp16_, NULL);
		_g_free0 (name);
		name = _tmp17_;
	}
	_tmp19_ = vala_method_get_this_parameter (m);
	_tmp20_ = _tmp19_;
	if (_tmp20_ == NULL) {
		_tmp18_ = NULL;
	} else {
		ValaParameter* _tmp21_;
		ValaParameter* _tmp22_;
		ValaDataType* _tmp23_;
		ValaDataType* _tmp24_;
		_tmp21_ = vala_method_get_this_parameter (m);
		_tmp22_ = _tmp21_;
		_tmp23_ = vala_variable_get_variable_type ((ValaVariable*) _tmp22_);
		_tmp24_ = _tmp23_;
		_tmp18_ = _tmp24_;
	}
	_tmp25_ = _vala_code_node_ref0 (_tmp18_);
	this_type = _tmp25_;
	_tmp26_ = g_strdup ("\n\t\t");
	func = _tmp26_;
	if (is_constructor) {
		const gchar* _tmp27_;
		const gchar* _tmp28_;
		ValaDataType* _tmp29_;
		gchar* _tmp30_;
		gchar* _tmp31_;
		gchar* _tmp32_;
		gchar* _tmp33_;
		gchar* _tmp34_;
		_tmp27_ = func;
		_tmp28_ = cname;
		_tmp29_ = this_type;
		_tmp30_ = node_ffi_writer_type_name (self, _tmp29_, FALSE);
		_tmp31_ = _tmp30_;
		_tmp32_ = g_strdup_printf ("$constructor: ['%s', %s, [", _tmp28_, _tmp31_);
		_tmp33_ = _tmp32_;
		_tmp34_ = g_strconcat (_tmp27_, _tmp33_, NULL);
		_g_free0 (func);
		func = _tmp34_;
		_g_free0 (_tmp33_);
		_g_free0 (_tmp31_);
	} else {
		const gchar* _tmp35_;
		const gchar* _tmp36_;
		const gchar* _tmp37_;
		ValaDataType* _tmp38_;
		ValaDataType* _tmp39_;
		gchar* _tmp40_;
		gchar* _tmp41_;
		gchar* _tmp42_;
		gchar* _tmp43_;
		gchar* _tmp44_;
		ValaDataType* _tmp45_;
		_tmp35_ = func;
		_tmp36_ = name;
		_tmp37_ = cname;
		_tmp38_ = vala_callable_get_return_type ((ValaCallable*) m);
		_tmp39_ = _tmp38_;
		_tmp40_ = node_ffi_writer_type_name (self, _tmp39_, FALSE);
		_tmp41_ = _tmp40_;
		_tmp42_ = g_strdup_printf ("%s: ['%s', %s, [", _tmp36_, _tmp37_, _tmp41_);
		_tmp43_ = _tmp42_;
		_tmp44_ = g_strconcat (_tmp35_, _tmp43_, NULL);
		_g_free0 (func);
		func = _tmp44_;
		_g_free0 (_tmp43_);
		_g_free0 (_tmp41_);
		_tmp45_ = this_type;
		if (_tmp45_ != NULL) {
			const gchar* _tmp46_;
			ValaDataType* _tmp47_;
			gchar* _tmp48_;
			gchar* _tmp49_;
			gchar* _tmp50_;
			_tmp46_ = func;
			_tmp47_ = this_type;
			_tmp48_ = node_ffi_writer_type_name (self, _tmp47_, FALSE);
			_tmp49_ = _tmp48_;
			_tmp50_ = g_strconcat (_tmp46_, _tmp49_, NULL);
			_g_free0 (func);
			func = _tmp50_;
			_g_free0 (_tmp49_);
		}
	}
	variadic = FALSE;
	{
		ValaList* _param_list = NULL;
		ValaList* _tmp51_;
		gint _param_size = 0;
		ValaList* _tmp52_;
		gint _tmp53_;
		gint _tmp54_;
		gint _param_index = 0;
		_tmp51_ = vala_callable_get_parameters ((ValaCallable*) m);
		_param_list = _tmp51_;
		_tmp52_ = _param_list;
		_tmp53_ = vala_collection_get_size ((ValaCollection*) _tmp52_);
		_tmp54_ = _tmp53_;
		_param_size = _tmp54_;
		_param_index = -1;
		while (TRUE) {
			gint _tmp55_;
			gint _tmp56_;
			ValaParameter* param = NULL;
			ValaList* _tmp57_;
			gpointer _tmp58_;
			ValaParameter* _tmp59_;
			gboolean _tmp60_;
			gboolean _tmp61_;
			const gchar* _tmp62_;
			gchar* _tmp63_;
			gchar* _tmp64_;
			ValaParameter* _tmp65_;
			ValaDataType* _tmp66_;
			ValaDataType* _tmp67_;
			gchar* _tmp68_;
			gchar* _tmp69_;
			gchar* _tmp70_;
			_param_index = _param_index + 1;
			_tmp55_ = _param_index;
			_tmp56_ = _param_size;
			if (!(_tmp55_ < _tmp56_)) {
				break;
			}
			_tmp57_ = _param_list;
			_tmp58_ = vala_list_get (_tmp57_, _param_index);
			param = (ValaParameter*) _tmp58_;
			_tmp59_ = param;
			_tmp60_ = vala_parameter_get_ellipsis (_tmp59_);
			_tmp61_ = _tmp60_;
			if (_tmp61_) {
				variadic = TRUE;
				_vala_code_node_unref0 (param);
				continue;
			}
			_tmp62_ = func;
			_tmp63_ = valabind_writer_sep ((ValabindWriter*) self, _tmp62_, ", ");
			_tmp64_ = _tmp63_;
			_tmp65_ = param;
			_tmp66_ = vala_variable_get_variable_type ((ValaVariable*) _tmp65_);
			_tmp67_ = _tmp66_;
			_tmp68_ = node_ffi_writer_type_name (self, _tmp67_, FALSE);
			_tmp69_ = _tmp68_;
			_tmp70_ = g_strconcat (_tmp64_, _tmp69_, NULL);
			_g_free0 (func);
			func = _tmp70_;
			_g_free0 (_tmp69_);
			_g_free0 (_tmp64_);
			_vala_code_node_unref0 (param);
		}
	}
	if (variadic) {
		_tmp71_ = "], 'variadic']";
	} else {
		_tmp71_ = "]]";
	}
	_tmp72_ = func;
	_tmp73_ = g_strconcat (_tmp72_, _tmp71_, NULL);
	_g_free0 (func);
	func = _tmp73_;
	_tmp74_ = self->priv->bind;
	_tmp75_ = valabind_writer_sep ((ValabindWriter*) self, _tmp74_, ",");
	_tmp76_ = _tmp75_;
	_tmp77_ = func;
	_tmp78_ = g_strconcat (_tmp76_, _tmp77_, NULL);
	_g_free0 (self->priv->bind);
	self->priv->bind = _tmp78_;
	_g_free0 (_tmp76_);
	if (parent_is_class) {
		const gchar* _tmp80_;
		_tmp80_ = name;
		_tmp79_ = g_strcmp0 (_tmp80_, "iterator") == 0;
	} else {
		_tmp79_ = FALSE;
	}
	if (_tmp79_) {
		const gchar* _tmp81_;
		gchar* _tmp82_;
		_tmp81_ = self->priv->bind;
		_tmp82_ = g_strconcat (_tmp81_, ",\n\t\tforEach: defaults.forEach", NULL);
		_g_free0 (self->priv->bind);
		self->priv->bind = _tmp82_;
	}
	_g_free0 (func);
	_vala_code_node_unref0 (this_type);
	_g_free0 (name);
	_g_free0 (cname);
	_vala_code_node_unref0 (parent);
}

static void
node_ffi_writer_real_visit_namespace (ValaCodeVisitor* base,
                                      ValaNamespace* ns)
{
	NodeFFIWriter * self;
	gchar* name = NULL;
	gchar* _tmp0_;
	gboolean use = FALSE;
	const gchar* _tmp3_;
	const gchar* _tmp16_;
	self = (NodeFFIWriter*) base;
	g_return_if_fail (ns != NULL);
	_tmp0_ = vala_symbol_get_full_name ((ValaSymbol*) ns);
	name = _tmp0_;
	use = valabind_writer_use_namespace ((ValabindWriter*) self, ns);
	if (use) {
		const gchar* _tmp1_;
		gchar* _tmp2_;
		_tmp1_ = name;
		_tmp2_ = g_strconcat (_tmp1_, ".", NULL);
		_g_free0 (self->priv->ns_pfx);
		self->priv->ns_pfx = _tmp2_;
	}
	_tmp3_ = self->priv->ns_pfx;
	if (_tmp3_ != NULL) {
		const gchar* _tmp4_;
		gchar* _tmp5_;
		gchar* _tmp6_;
		_tmp4_ = name;
		_tmp5_ = g_strconcat (">\x1b[1mns\x1b[0m ", _tmp4_, NULL);
		_tmp6_ = _tmp5_;
		notice (_tmp6_);
		_g_free0 (_tmp6_);
		valabind_writer_add_includes ((ValabindWriter*) self, (ValaSymbol*) ns);
	}
	{
		ValaList* _n_list = NULL;
		ValaList* _tmp7_;
		gint _n_size = 0;
		ValaList* _tmp8_;
		gint _tmp9_;
		gint _tmp10_;
		gint _n_index = 0;
		_tmp7_ = vala_namespace_get_namespaces (ns);
		_n_list = _tmp7_;
		_tmp8_ = _n_list;
		_tmp9_ = vala_collection_get_size ((ValaCollection*) _tmp8_);
		_tmp10_ = _tmp9_;
		_n_size = _tmp10_;
		_n_index = -1;
		while (TRUE) {
			gint _tmp11_;
			gint _tmp12_;
			ValaNamespace* n = NULL;
			ValaList* _tmp13_;
			gpointer _tmp14_;
			ValaNamespace* _tmp15_;
			_n_index = _n_index + 1;
			_tmp11_ = _n_index;
			_tmp12_ = _n_size;
			if (!(_tmp11_ < _tmp12_)) {
				break;
			}
			_tmp13_ = _n_list;
			_tmp14_ = vala_list_get (_tmp13_, _n_index);
			n = (ValaNamespace*) _tmp14_;
			_tmp15_ = n;
			vala_code_node_accept ((ValaCodeNode*) _tmp15_, (ValaCodeVisitor*) self);
			_vala_code_node_unref0 (n);
		}
	}
	_tmp16_ = self->priv->ns_pfx;
	if (_tmp16_ != NULL) {
		if (!use) {
			const gchar* _tmp17_;
			const gchar* _tmp18_;
			gchar* _tmp19_;
			gchar* _tmp20_;
			gchar* _tmp21_;
			const gchar* _tmp22_;
			gchar* _tmp23_;
			gchar* _tmp24_;
			const gchar* _tmp25_;
			gchar* _tmp26_;
			gchar* _tmp27_;
			gchar* _tmp28_;
			const gchar* _tmp50_;
			gchar* _tmp51_;
			gchar* _tmp52_;
			gchar* _tmp53_;
			_tmp17_ = name;
			_tmp18_ = self->priv->ns_pfx;
			_tmp19_ = string_replace (_tmp17_, _tmp18_, "");
			_tmp20_ = _tmp19_;
			_tmp21_ = string_replace (_tmp20_, ".", "");
			_g_free0 (name);
			name = _tmp21_;
			_g_free0 (_tmp20_);
			_tmp22_ = self->priv->bind;
			_tmp23_ = valabind_writer_sep ((ValabindWriter*) self, _tmp22_, ",\n");
			_tmp24_ = _tmp23_;
			_tmp25_ = name;
			_tmp26_ = g_strdup_printf ("\t$%s: function() {return {", _tmp25_);
			_tmp27_ = _tmp26_;
			_tmp28_ = g_strconcat (_tmp24_, _tmp27_, NULL);
			_g_free0 (self->priv->bind);
			self->priv->bind = _tmp28_;
			_g_free0 (_tmp27_);
			_g_free0 (_tmp24_);
			{
				ValaList* _m_list = NULL;
				ValaList* _tmp29_;
				gint _m_size = 0;
				ValaList* _tmp30_;
				gint _tmp31_;
				gint _tmp32_;
				gint _m_index = 0;
				_tmp29_ = vala_namespace_get_methods (ns);
				_m_list = _tmp29_;
				_tmp30_ = _m_list;
				_tmp31_ = vala_collection_get_size ((ValaCollection*) _tmp30_);
				_tmp32_ = _tmp31_;
				_m_size = _tmp32_;
				_m_index = -1;
				while (TRUE) {
					gint _tmp33_;
					gint _tmp34_;
					ValaMethod* m = NULL;
					ValaList* _tmp35_;
					gpointer _tmp36_;
					ValaMethod* _tmp37_;
					_m_index = _m_index + 1;
					_tmp33_ = _m_index;
					_tmp34_ = _m_size;
					if (!(_tmp33_ < _tmp34_)) {
						break;
					}
					_tmp35_ = _m_list;
					_tmp36_ = vala_list_get (_tmp35_, _m_index);
					m = (ValaMethod*) _tmp36_;
					_tmp37_ = m;
					vala_code_node_accept ((ValaCodeNode*) _tmp37_, (ValaCodeVisitor*) self);
					_vala_code_node_unref0 (m);
				}
			}
			{
				ValaList* _e_list = NULL;
				ValaList* _tmp38_;
				gint _e_size = 0;
				ValaList* _tmp39_;
				gint _tmp40_;
				gint _tmp41_;
				gint _e_index = 0;
				_tmp38_ = vala_namespace_get_enums (ns);
				_e_list = _tmp38_;
				_tmp39_ = _e_list;
				_tmp40_ = vala_collection_get_size ((ValaCollection*) _tmp39_);
				_tmp41_ = _tmp40_;
				_e_size = _tmp41_;
				_e_index = -1;
				while (TRUE) {
					gint _tmp42_;
					gint _tmp43_;
					ValaEnum* e = NULL;
					ValaList* _tmp44_;
					gpointer _tmp45_;
					ValaEnum* _tmp46_;
					const gchar* _tmp47_;
					gchar* _tmp48_;
					gchar* _tmp49_;
					_e_index = _e_index + 1;
					_tmp42_ = _e_index;
					_tmp43_ = _e_size;
					if (!(_tmp42_ < _tmp43_)) {
						break;
					}
					_tmp44_ = _e_list;
					_tmp45_ = vala_list_get (_tmp44_, _e_index);
					e = (ValaEnum*) _tmp45_;
					_tmp46_ = e;
					_tmp47_ = name;
					_tmp48_ = g_strconcat (_tmp47_, ".", NULL);
					_tmp49_ = _tmp48_;
					node_ffi_writer_visit_enum (self, _tmp46_, _tmp49_);
					_g_free0 (_tmp49_);
					_vala_code_node_unref0 (e);
				}
			}
			_tmp50_ = self->priv->bind;
			_tmp51_ = valabind_writer_sep ((ValabindWriter*) self, _tmp50_, "\n\t");
			_tmp52_ = _tmp51_;
			_tmp53_ = g_strconcat (_tmp52_, "};}", NULL);
			_g_free0 (self->priv->bind);
			self->priv->bind = _tmp53_;
			_g_free0 (_tmp52_);
		} else {
			{
				ValaList* _e_list = NULL;
				ValaList* _tmp54_;
				gint _e_size = 0;
				ValaList* _tmp55_;
				gint _tmp56_;
				gint _tmp57_;
				gint _e_index = 0;
				_tmp54_ = vala_namespace_get_enums (ns);
				_e_list = _tmp54_;
				_tmp55_ = _e_list;
				_tmp56_ = vala_collection_get_size ((ValaCollection*) _tmp55_);
				_tmp57_ = _tmp56_;
				_e_size = _tmp57_;
				_e_index = -1;
				while (TRUE) {
					gint _tmp58_;
					gint _tmp59_;
					ValaEnum* e = NULL;
					ValaList* _tmp60_;
					gpointer _tmp61_;
					ValaEnum* _tmp62_;
					_e_index = _e_index + 1;
					_tmp58_ = _e_index;
					_tmp59_ = _e_size;
					if (!(_tmp58_ < _tmp59_)) {
						break;
					}
					_tmp60_ = _e_list;
					_tmp61_ = vala_list_get (_tmp60_, _e_index);
					e = (ValaEnum*) _tmp61_;
					_tmp62_ = e;
					node_ffi_writer_visit_enum (self, _tmp62_, "");
					_vala_code_node_unref0 (e);
				}
			}
		}
		{
			ValaList* _s_list = NULL;
			ValaList* _tmp63_;
			gint _s_size = 0;
			ValaList* _tmp64_;
			gint _tmp65_;
			gint _tmp66_;
			gint _s_index = 0;
			_tmp63_ = vala_namespace_get_structs (ns);
			_s_list = _tmp63_;
			_tmp64_ = _s_list;
			_tmp65_ = vala_collection_get_size ((ValaCollection*) _tmp64_);
			_tmp66_ = _tmp65_;
			_s_size = _tmp66_;
			_s_index = -1;
			while (TRUE) {
				gint _tmp67_;
				gint _tmp68_;
				ValaStruct* s = NULL;
				ValaList* _tmp69_;
				gpointer _tmp70_;
				ValaStruct* _tmp71_;
				_s_index = _s_index + 1;
				_tmp67_ = _s_index;
				_tmp68_ = _s_size;
				if (!(_tmp67_ < _tmp68_)) {
					break;
				}
				_tmp69_ = _s_list;
				_tmp70_ = vala_list_get (_tmp69_, _s_index);
				s = (ValaStruct*) _tmp70_;
				_tmp71_ = s;
				vala_code_node_accept ((ValaCodeNode*) _tmp71_, (ValaCodeVisitor*) self);
				_vala_code_node_unref0 (s);
			}
		}
		{
			ValaList* _c_list = NULL;
			ValaList* _tmp72_;
			gint _c_size = 0;
			ValaList* _tmp73_;
			gint _tmp74_;
			gint _tmp75_;
			gint _c_index = 0;
			_tmp72_ = vala_namespace_get_classes (ns);
			_c_list = _tmp72_;
			_tmp73_ = _c_list;
			_tmp74_ = vala_collection_get_size ((ValaCollection*) _tmp73_);
			_tmp75_ = _tmp74_;
			_c_size = _tmp75_;
			_c_index = -1;
			while (TRUE) {
				gint _tmp76_;
				gint _tmp77_;
				ValaClass* c = NULL;
				ValaList* _tmp78_;
				gpointer _tmp79_;
				ValaClass* _tmp80_;
				_c_index = _c_index + 1;
				_tmp76_ = _c_index;
				_tmp77_ = _c_size;
				if (!(_tmp76_ < _tmp77_)) {
					break;
				}
				_tmp78_ = _c_list;
				_tmp79_ = vala_list_get (_tmp78_, _c_index);
				c = (ValaClass*) _tmp79_;
				_tmp80_ = c;
				vala_code_node_accept ((ValaCodeNode*) _tmp80_, (ValaCodeVisitor*) self);
				_vala_code_node_unref0 (c);
			}
		}
	}
	if (use) {
		_g_free0 (self->priv->ns_pfx);
		self->priv->ns_pfx = NULL;
	}
	_g_free0 (name);
}

static void
node_ffi_writer_real_write (ValabindWriter* base,
                            const gchar* file)
{
	NodeFFIWriter * self;
	FILE* stream = NULL;
	FILE* _tmp0_;
	FILE* _tmp1_;
	ValaCodeContext* _tmp4_;
	ValaNamespace* _tmp5_;
	ValaNamespace* _tmp6_;
	FILE* _tmp7_;
	const gchar* _tmp8_;
	gchar* _tmp9_;
	gchar* _tmp10_;
	gchar* _tmp11_;
	gchar* _tmp12_;
	const gchar* _tmp13_;
	gchar* _tmp14_;
	gchar* _tmp15_;
	gchar* _tmp16_;
	gchar* _tmp17_;
	const gchar* _tmp18_;
	gchar* _tmp19_;
	gchar* _tmp20_;
	gchar* _tmp21_;
	gchar* _tmp22_;
	const gchar* _tmp23_;
	self = (NodeFFIWriter*) base;
	g_return_if_fail (file != NULL);
	_tmp0_ = g_fopen (file, "w");
	stream = _tmp0_;
	_tmp1_ = stream;
	if (_tmp1_ == NULL) {
		gchar* _tmp2_;
		gchar* _tmp3_;
		_tmp2_ = g_strdup_printf ("Cannot open %s for writing", file);
		_tmp3_ = _tmp2_;
		error (_tmp3_);
		_g_free0 (_tmp3_);
	}
	_tmp4_ = ((ValabindWriter*) self)->context;
	_tmp5_ = vala_code_context_get_root (_tmp4_);
	_tmp6_ = _tmp5_;
	vala_code_node_accept ((ValaCodeNode*) _tmp6_, (ValaCodeVisitor*) self);
	_tmp7_ = stream;
	_tmp8_ = ((ValabindWriter*) self)->modulename;
	_tmp9_ = g_strconcat ("\n/* DO NOT EDIT. Automatically generated by valabind from ", _tmp8_, NULL);
	_tmp10_ = _tmp9_;
	_tmp11_ = g_strconcat (_tmp10_, " */\n" \
"\n" \
"var ffi = require('ffi'), ref = require('ref'), Struct = require('ref-" \
"struct');\n" \
"var lib = new ffi.DynamicLibrary('lib", NULL);
	_tmp12_ = _tmp11_;
	_tmp13_ = ((ValabindWriter*) self)->modulename;
	_tmp14_ = g_strconcat (_tmp12_, _tmp13_, NULL);
	_tmp15_ = _tmp14_;
	_tmp16_ = g_strconcat (_tmp15_, "'+ffi.LIB_EXT);\n" \
"\n" \
"function Tname(T) {\n" \
"	return T.hasOwnProperty('$name') ? T.$name : T.name;\n" \
"}\n" \
"\n" \
"var types = exports.type = {};\n" \
"\n" \
"for(var i in ref.types)\n" \
"	if(i != 'Utf8String') // Try not to trip the deprecated warning.\n" \
"		types[i] = ref.types[i];\n" \
"\n" \
"types.staticCString = function staticCString(N) {\n" \
"	var r = Object.create(types.char);\n" \
"	r.name = 'char['+N+']';\n" \
"	r.size *= N;\n" \
"	r.get = function get(buf, offset) {\n" \
"		if(buf.isNull())\n" \
"			return null;\n" \
"		// TODO enforce maxLength of N\n" \
"		return buf.readCString(offset);\n" \
"	};\n" \
"	r.set = function set(buf, offset, val) {\n" \
"		// TODO enforce maxLength of N\n" \
"		return buf.writeCString(val, offset);\n" \
"	};\n" \
"	return r;\n" \
"};\n" \
"\n" \
"var ptrCache = [], ptrCacheTo = [];\n" \
"types.ptr = function PointerType(T) {\n" \
"	T = ref.coerceType(T);\n" \
"	if(T == types.char)\n" \
"		return types.CString;\n" \
"	var i = ptrCache.indexOf(T);\n" \
"	return i === -1 ? ptrCacheTo[ptrCache.push(T)-1] = ref.refType(T) : p" \
"trCacheTo[i];\n" \
"};\n" \
"\n" \
"var refCache = [], refCacheTo = [];\n" \
"types.ref = function ReferenceType(T) {\n" \
"	T = ref.coerceType(T);\n" \
"	var i = refCache.indexOf(T);\n" \
"	if(i !== -1)\n" \
"		return refCacheTo[i];\n" \
"	var p = types.ptr(T), r = refCacheTo[refCache.push(T)-1] = Object.cre" \
"ate(p);\n" \
"	r.indirection = 1;\n" \
"	r.size = ref.sizeof.pointer;\n" \
"	r.alignment = ref.alignof.pointer;\n" \
"	r.name = Tname(T)+'&';\n" \
"	r.ffi_type = ffi.FFI_TYPES.pointer;\n" \
"	r.get = function get(buf, offset) {\n" \
"		buf = ref.get(buf, offset, p);\n" \
"		if(buf.isNull())\n" \
"			return null;\n" \
"		return buf.deref();\n" \
"	};\n" \
"	r.set = function set(buf, offset, val) {\n" \
"		if(!val)\n" \
"			return ref.set(buf, offset, null, p);\n" \
"		if(!val.buffer)\n" \
"			throw new TypeError('valabind ['+r.name+']#set got a bad value');\n" \
"		return ref.set(buf, offset, val.buffer, p);\n" \
"	};\n" \
"	return r;\n" \
"};\n" \
"\n" \
"types.array = function ArrayType(T, N) {\n" \
"	T = ref.coerceType(T);\n" \
"	if(T == types.char)\n" \
"		return types.staticCString(N);\n" \
"	var r = Object.create(T);\n" \
"	r.size *= N;\n" \
"	r.name = Tname(T)+'['+N+']';\n" \
"	function ArrayType(buffer, base) {\n" \
"		this.buffer = buffer;\n" \
"		this._base = base;\n" \
"	}\n" \
"	ArrayType.prototype = [];\n" \
"	ArrayType.prototype.constructor = ArrayType;\n" \
"	for(var i = 0; i < N; i++)\n" \
"		Object.defineProperty(ArrayType.prototype, i, {\n" \
"			get: function get() {\n" \
"				return ref.get(this.buffer, this._base+T.size*i, T);\n" \
"			},\n" \
"			set: function set(val) {\n" \
"				return ref.set(this.buffer, this._base+T.size*i, val, T);\n" \
"			},\n" \
"			enumerable: true\n" \
"		});\n" \
"	r.get = function get(buf, offset) {\n" \
"		return new ArrayType(buf, offset);\n" \
"	};\n" \
"	r.set = function set(buf, offset, val) {\n" \
"		for(var i in val) {\n" \
"			if(isNaN(i = +i) || i >= N)\n" \
"				continue;\n" \
"			ref.set(buf, offset+T.size*i, val[i], T);\n" \
"		}\n" \
"	};\n" \
"	return r;\n" \
"};\n" \
"\n" \
"types.delegate = function DelegateType(ret, args) {\n" \
"	var p = types.ptr(types.void), r = Object.create(p);\n" \
"	r.indirection = 1;\n" \
"	r.name = Tname(ret)+'('+args.map(function(T) {return Tname(T);}).join" \
"(', ')+')';\n" \
"	r.get = function get(buf, offset) {\n" \
"		buf = ref.get(buf, offset, p);\n" \
"		if(buf.isNull())\n" \
"			return null;\n" \
"		return ffi.ForeignFunction(buf, ret, args);\n" \
"	};\n" \
"	r.set = function set(buf, offset, val) {\n" \
"		return ref.set(buf, offset, ffi.Callback(ret, args, void(0), val));\n" \
"	};\n" \
"	return r;\n" \
"};\n" \
"\n" \
"var defaults = {\n" \
"	forEach: function forEach(callback, thisArg) {\n" \
"		if({}.toString.call(callback) != '[object Function]')\n" \
"			throw new TypeError(callback + ' is not a function');\n" \
"\n" \
"		for(var T = thisArg || T, iter = this.iterator(); iter; iter = iter." \
"get_next())\n" \
"			callback.call(T, iter.get_data(), iter, this);\n" \
"	}\n" \
"};\n" \
"\n" \
"function bindings(s) {\n" \
"	function method(name, ret, args, static, more) {\n" \
"		var f = (more == 'variadic' ? ffi.VariadicForeignFunction :\n" \
"			ffi.ForeignFunction)(lib.get(name), ret, args);\n" \
"		if(static)\n" \
"			return f;\n" \
"		return function() {\n" \
"			[].unshift.call(arguments, this);\n" \
"			return f.apply(null, arguments);\n" \
"		};\n" \
"	}\n" \
"\n" \
"	function define(base, n, m) {\n" \
"		var static = n[0] == '$' && ((n = n.slice(1)), true);\n" \
"		static = static || base[0] == '$' && ((base = base.slice(1)), true);" \
"\n" \
"		if(Array.isArray(m))\n" \
"			m = method(m[0], m[1], m[2], static, m[3]);\n" \
"		static ? exports[base][n] = m : types[base].prototype[n] = m;\n" \
"	}\n" \
"\n" \
"	function makeGeneric(G, n) {\n" \
"		var cache = [], cacheTo = [];\n" \
"		types[n] = function() {\n" \
"			var l = arguments.length, args = [], c;\n" \
"\n" \
"			// Coerce all type arguments.\n" \
"			for(var i = 0; i < l; i++)\n" \
"				args[i] = ref.coerceType(arguments[i].$type || arguments[i]);\n" \
"\n" \
"			// Look in the cache, if the generic was already built.\n" \
"			for(var i = 0; i < cache.length; i++) {\n" \
"				if((c = cache[i]).length !== l)\n" \
"					continue;\n" \
"				for(var j = 0; j < l && c[j] === args[j]; j++);\n" \
"				if(j === l)\n" \
"					return cacheTo[i];\n" \
"			}\n" \
"\n" \
"			// Create the new generic.\n" \
"			var generic = cacheTo[cache.push(args)-1] = Struct(), g = G.apply(n" \
"ull, args);\n" \
"			generic.$name = n+'<'+args.map(function(T) {return Tname(T);}).join" \
"(', ')+'>';\n" \
"\n" \
"			// Define all the generic's propoerties.\n" \
"			for(var i in g[0])\n" \
"				generic.defineProperty(i, g[0][i]);\n" \
"\n" \
"			// Insert all the generic's methods.\n" \
"			if(g[1])\n" \
"				for(var i in g[1]) {\n" \
"					var m = g[1][i];\n" \
"					if(Array.isArray(m))\n" \
"						m = method(m[0], m[1], m[2], false, m[3]);\n" \
"					generic.prototype[i] = m;\n" \
"				}\n" \
"			return generic;\n" \
"		};\n" \
"	}\n" \
"	for(var i in s) {\n" \
"		if(s[i].length)\n" \
"			makeGeneric(s[i], i);\n" \
"		else if(i[0] == '$')\n" \
"			exports[i.slice(1)] = {};\n" \
"		else\n" \
"			exports[i] = types[i] = Struct(), types[i].$name = i;\n" \
"	}\n" \
"	for(var i in s) {\n" \
"		if(s[i].length) {\n" \
"			// TODO insert constructor\n" \
"			delete s[i];\n" \
"			continue;\n" \
"		}\n" \
"		s[i] = s[i]();\n" \
"		if(Array.isArray(s[i])) {\n" \
"			for(var j in s[i][0])\n" \
"				types[i].defineProperty(j, s[i][0][j]);\n" \
"			s[i] = s[i][1] || {};\n" \
"		}\n" \
"	}\n" \
"	for(var i in s) {\n" \
"		if('$constructor' in s[i]) {\n" \
"			var ctor = s[i].$constructor;\n" \
"			exports[i] = method(ctor[0], ctor[1], ctor[2], true, ctor[3]), expo" \
"rts[i].$type = types[i];\n" \
"			delete s[i].$constructor;\n" \
"		}\n" \
"		for(var j in s[i])\n" \
"			define(i, j, s[i][j]);\n" \
"	}\n" \
"}\n" \
"var _ = types;\n" \
"bindings({\n", NULL);
	_tmp17_ = _tmp16_;
	_tmp18_ = self->priv->bind;
	_tmp19_ = g_strconcat (_tmp17_, _tmp18_, NULL);
	_tmp20_ = _tmp19_;
	_tmp21_ = g_strconcat (_tmp20_, "\n});\n", NULL);
	_tmp22_ = _tmp21_;
	fputs (_tmp22_, _tmp7_);
	_g_free0 (_tmp22_);
	_g_free0 (_tmp20_);
	_g_free0 (_tmp17_);
	_g_free0 (_tmp15_);
	_g_free0 (_tmp12_);
	_g_free0 (_tmp10_);
	_tmp23_ = self->priv->enum_fmt;
	if (g_strcmp0 (_tmp23_, "") != 0) {
		gchar* enums_out = NULL;
		const gchar* _tmp24_;
		const gchar* _tmp25_;
		gchar* _tmp26_;
		gchar* _tmp27_;
		GList* _tmp28_;
		gchar* _tmp29_;
		gchar* _tmp30_;
		FILE* _tmp31_;
		const gchar* _tmp32_;
		_tmp24_ = self->priv->enum_fmt;
		_tmp25_ = self->priv->enum_vals;
		_tmp26_ = g_strdup_printf ("printf(\"%s\"%s)", _tmp24_, _tmp25_);
		_tmp27_ = _tmp26_;
		_tmp28_ = ((ValabindWriter*) self)->includefiles;
		_tmp29_ = get_enums_for (_tmp27_, _tmp28_);
		_tmp30_ = _tmp29_;
		_g_free0 (_tmp27_);
		enums_out = _tmp30_;
		_tmp31_ = stream;
		_tmp32_ = enums_out;
		fputs (_tmp32_, _tmp31_);
		_g_free0 (enums_out);
	}
	_fclose0 (stream);
}

static void
node_ffi_writer_class_init (NodeFFIWriterClass * klass,
                            gpointer klass_data)
{
	node_ffi_writer_parent_class = g_type_class_peek_parent (klass);
	((ValaCodeVisitorClass *) klass)->finalize = node_ffi_writer_finalize;
	g_type_class_adjust_private_offset (klass, &NodeFFIWriter_private_offset);
	((ValabindWriterClass *) klass)->get_filename = (gchar* (*) (ValabindWriter*, const gchar*)) node_ffi_writer_real_get_filename;
	((ValaCodeVisitorClass *) klass)->visit_struct = (void (*) (ValaCodeVisitor*, ValaStruct*)) node_ffi_writer_real_visit_struct;
	((ValaCodeVisitorClass *) klass)->visit_class = (void (*) (ValaCodeVisitor*, ValaClass*)) node_ffi_writer_real_visit_class;
	((ValaCodeVisitorClass *) klass)->visit_field = (void (*) (ValaCodeVisitor*, ValaField*)) node_ffi_writer_real_visit_field;
	((ValaCodeVisitorClass *) klass)->visit_method = (void (*) (ValaCodeVisitor*, ValaMethod*)) node_ffi_writer_real_visit_method;
	((ValaCodeVisitorClass *) klass)->visit_namespace = (void (*) (ValaCodeVisitor*, ValaNamespace*)) node_ffi_writer_real_visit_namespace;
	((ValabindWriterClass *) klass)->write = (void (*) (ValabindWriter*, const gchar*)) node_ffi_writer_real_write;
}

static void
node_ffi_writer_instance_init (NodeFFIWriter * self,
                               gpointer klass)
{
	gchar* _tmp0_;
	gchar* _tmp1_;
	gchar* _tmp2_;
	self->priv = node_ffi_writer_get_instance_private (self);
	_tmp0_ = g_strdup ("");
	self->priv->bind = _tmp0_;
	_tmp1_ = g_strdup ("");
	self->priv->enum_fmt = _tmp1_;
	_tmp2_ = g_strdup ("");
	self->priv->enum_vals = _tmp2_;
}

static void
node_ffi_writer_finalize (ValaCodeVisitor * obj)
{
	NodeFFIWriter * self;
	self = G_TYPE_CHECK_INSTANCE_CAST (obj, TYPE_NODE_FFI_WRITER, NodeFFIWriter);
	_g_free0 (self->priv->ns_pfx);
	_g_free0 (self->priv->bind);
	_g_free0 (self->priv->enum_fmt);
	_g_free0 (self->priv->enum_vals);
	VALA_CODE_VISITOR_CLASS (node_ffi_writer_parent_class)->finalize (obj);
}

static GType
node_ffi_writer_get_type_once (void)
{
	static const GTypeInfo g_define_type_info = { sizeof (NodeFFIWriterClass), (GBaseInitFunc) NULL, (GBaseFinalizeFunc) NULL, (GClassInitFunc) node_ffi_writer_class_init, (GClassFinalizeFunc) NULL, NULL, sizeof (NodeFFIWriter), 0, (GInstanceInitFunc) node_ffi_writer_instance_init, NULL };
	GType node_ffi_writer_type_id;
	node_ffi_writer_type_id = g_type_register_static (TYPE_VALABIND_WRITER, "NodeFFIWriter", &g_define_type_info, 0);
	NodeFFIWriter_private_offset = g_type_add_instance_private (node_ffi_writer_type_id, sizeof (NodeFFIWriterPrivate));
	return node_ffi_writer_type_id;
}

GType
node_ffi_writer_get_type (void)
{
	static volatile gsize node_ffi_writer_type_id__once = 0;
	if (g_once_init_enter (&node_ffi_writer_type_id__once)) {
		GType node_ffi_writer_type_id;
		node_ffi_writer_type_id = node_ffi_writer_get_type_once ();
		g_once_init_leave (&node_ffi_writer_type_id__once, node_ffi_writer_type_id);
	}
	return node_ffi_writer_type_id__once;
}

static void
_vala_array_destroy (gpointer array,
                     gssize array_length,
                     GDestroyNotify destroy_func)
{
	if ((array != NULL) && (destroy_func != NULL)) {
		gssize 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,
                  gssize array_length,
                  GDestroyNotify destroy_func)
{
	_vala_array_destroy (array, array_length, destroy_func);
	g_free (array);
}

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

