// JNI functions for the Go <=> Java bridge.
//   gobind -lang=java structs
//
// File is generated by gobind. Do not edit.

#include <android/log.h>
#include <stdint.h>
#include "seq.h"
#include "_cgo_export.h"
#include "structs.h"

jclass proxy_class_structs_I;
jmethodID proxy_class_structs_I_cons;
static jmethodID mid_I_M;
jclass proxy_class_structs_S;
jmethodID proxy_class_structs_S_cons;
jclass proxy_class_structs_S2;
jmethodID proxy_class_structs_S2_cons;
jclass proxy_class_structs_Structs;
jmethodID proxy_class_structs_Structs_cons;

JNIEXPORT void JNICALL
Java_structs_Structs__1init(JNIEnv *env, jclass _unused) {
    jclass clazz;
    clazz = (*env)->FindClass(env, "structs/S");
    proxy_class_structs_S = (*env)->NewGlobalRef(env, clazz);
    proxy_class_structs_S_cons = (*env)->GetMethodID(env, clazz, "<init>", "(Lgo/Seq$Ref;)V");
    clazz = (*env)->FindClass(env, "structs/S2");
    proxy_class_structs_S2 = (*env)->NewGlobalRef(env, clazz);
    proxy_class_structs_S2_cons = (*env)->GetMethodID(env, clazz, "<init>", "(Lgo/Seq$Ref;)V");
    clazz = (*env)->FindClass(env, "structs/Structs_");
    proxy_class_structs_Structs = (*env)->NewGlobalRef(env, clazz);
    proxy_class_structs_Structs_cons = (*env)->GetMethodID(env, clazz, "<init>", "(Lgo/Seq$Ref;)V");
    clazz = (*env)->FindClass(env, "structs/Structs$proxyI");
    proxy_class_structs_I = (*env)->NewGlobalRef(env, clazz);
    proxy_class_structs_I_cons = (*env)->GetMethodID(env, clazz, "<init>", "(Lgo/Seq$Ref;)V");
    clazz = (*env)->FindClass(env, "structs/I");
    mid_I_M = (*env)->GetMethodID(env, clazz, "m", "()V");
    
}

JNIEXPORT jobject JNICALL
Java_structs_Structs_identity(JNIEnv* env, jclass _clazz, jobject s) {
    int32_t _s = go_seq_to_refnum(env, s);
    int32_t r0 = proxystructs__Identity(_s);
    jobject _r0 = go_seq_from_refnum(env, r0, proxy_class_structs_S, proxy_class_structs_S_cons);
    return _r0;
}

JNIEXPORT jobject JNICALL
Java_structs_Structs_identityWithError(JNIEnv* env, jclass _clazz, jobject s) {
    int32_t _s = go_seq_to_refnum(env, s);
    struct proxystructs__IdentityWithError_return res = proxystructs__IdentityWithError(_s);
    jobject _r0 = go_seq_from_refnum(env, res.r0, proxy_class_structs_S, proxy_class_structs_S_cons);
    jobject _r1 = go_seq_from_refnum(env, res.r1, proxy_class__error, proxy_class__error_cons);
    go_seq_maybe_throw_exception(env, _r1);
    return _r0;
}

JNIEXPORT jobject JNICALL
Java_structs_S__1_1New(JNIEnv *env, jclass clazz) {
    int32_t refnum = new_structs_S();
    return go_seq_from_refnum(env, refnum, NULL, NULL);
}

JNIEXPORT jobject JNICALL
Java_structs_S_identity(JNIEnv* env, jobject __this__) {
    int32_t o = go_seq_to_refnum_go(env, __this__);
    struct proxystructs_S_Identity_return res = proxystructs_S_Identity(o);
    jobject _r0 = go_seq_from_refnum(env, res.r0, proxy_class_structs_S, proxy_class_structs_S_cons);
    jobject _r1 = go_seq_from_refnum(env, res.r1, proxy_class__error, proxy_class__error_cons);
    go_seq_maybe_throw_exception(env, _r1);
    return _r0;
}

JNIEXPORT jdouble JNICALL
Java_structs_S_sum(JNIEnv* env, jobject __this__) {
    int32_t o = go_seq_to_refnum_go(env, __this__);
    double r0 = proxystructs_S_Sum(o);
    jdouble _r0 = (jdouble)r0;
    return _r0;
}

JNIEXPORT void JNICALL
Java_structs_S_setX(JNIEnv *env, jobject this, jdouble v) {
    int32_t o = go_seq_to_refnum_go(env, this);
    double _v = (double)v;
    proxystructs_S_X_Set(o, _v);
}

JNIEXPORT jdouble JNICALL
Java_structs_S_getX(JNIEnv *env, jobject this) {
    int32_t o = go_seq_to_refnum_go(env, this);
    double r0 = proxystructs_S_X_Get(o);
    jdouble _r0 = (jdouble)r0;
    return _r0;
}

JNIEXPORT void JNICALL
Java_structs_S_setY(JNIEnv *env, jobject this, jdouble v) {
    int32_t o = go_seq_to_refnum_go(env, this);
    double _v = (double)v;
    proxystructs_S_Y_Set(o, _v);
}

JNIEXPORT jdouble JNICALL
Java_structs_S_getY(JNIEnv *env, jobject this) {
    int32_t o = go_seq_to_refnum_go(env, this);
    double r0 = proxystructs_S_Y_Get(o);
    jdouble _r0 = (jdouble)r0;
    return _r0;
}

JNIEXPORT jobject JNICALL
Java_structs_S2__1_1New(JNIEnv *env, jclass clazz) {
    int32_t refnum = new_structs_S2();
    return go_seq_from_refnum(env, refnum, NULL, NULL);
}

JNIEXPORT void JNICALL
Java_structs_S2_m(JNIEnv* env, jobject __this__) {
    int32_t o = go_seq_to_refnum_go(env, __this__);
    proxystructs_S2_M(o);
}

JNIEXPORT jstring JNICALL
Java_structs_S2_string(JNIEnv* env, jobject __this__) {
    int32_t o = go_seq_to_refnum_go(env, __this__);
    nstring r0 = proxystructs_S2_String(o);
    jstring _r0 = go_seq_to_java_string(env, r0);
    return _r0;
}

JNIEXPORT jobject JNICALL
Java_structs_Structs_1__1_1New(JNIEnv *env, jclass clazz) {
    int32_t refnum = new_structs_Structs();
    return go_seq_from_refnum(env, refnum, NULL, NULL);
}

JNIEXPORT void JNICALL
Java_structs_Structs_1_m(JNIEnv* env, jobject __this__) {
    int32_t o = go_seq_to_refnum_go(env, __this__);
    proxystructs_Structs_M(o);
}

JNIEXPORT void JNICALL
Java_structs_Structs_00024proxyI_m(JNIEnv* env, jobject __this__) {
    int32_t o = go_seq_to_refnum_go(env, __this__);
    proxystructs_I_M(o);
}

void cproxystructs_I_M(int32_t refnum) {
    JNIEnv *env = go_seq_push_local_frame(0);
    jobject o = go_seq_from_refnum(env, refnum, proxy_class_structs_I, proxy_class_structs_I_cons);
    (*env)->CallVoidMethod(env, o, mid_I_M);
    go_seq_pop_local_frame(env);
}

