// Copyright 2016 The Vanadium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

// +build java android
// +build cgo

package main

import (
	"unsafe"
)

// #include <stdlib.h>
// #include <string.h>
// #include "jni_wrapper.h"
// #include "lib.h"
import "C"

var (
	jVM                      *C.JavaVM
	arrayListClass           jArrayListClass
	idClass                  jIdClass
	syncgroupMemberInfoClass jSyncgroupMemberInfo
	syncgroupSpecClass       jSyncgroupSpec
	verrorClass              jVErrorClass
)

// JNI_OnLoad is called when System.loadLibrary is called. We need to cache the
// *JavaVM because that's the only way to get hold of a JNIEnv that is needed
// for any JNI operation.
//
// Reference: https://developer.android.com/training/articles/perf-jni.html#native_libraries
//
//export JNI_OnLoad
func JNI_OnLoad(vm *C.JavaVM, reserved unsafe.Pointer) C.jint {
	var env *C.JNIEnv
	if C.GetEnv(vm, unsafe.Pointer(&env), C.JNI_VERSION_1_6) != C.JNI_OK {
		return C.JNI_ERR
	}
	jVM = vm

	v23_syncbase_Init(C.v23_syncbase_Bool(1))
	arrayListClass = newJArrayListClass(env)
	idClass = newJIdClass(env)
	syncgroupMemberInfoClass = newJSyncgroupMemberInfo(env)
	syncgroupSpecClass = newJSyncgroupSpec(env)
	verrorClass = newJVErrorClass(env)

	return C.JNI_VERSION_1_6
}

func Java_io_v_syncbase_internal_Service_GetPermissions(env *C.JNIEnv, cls C.jclass) C.jobject {
	return nil
}
func Java_io_v_syncbase_internal_Service_SetPermissions(env *C.JNIEnv, cls C.jclass, obj C.jobject) {}

//export Java_io_v_syncbase_internal_Service_ListDatabases
func Java_io_v_syncbase_internal_Service_ListDatabases(env *C.JNIEnv, cls C.jclass) C.jobject {
	var cIds C.v23_syncbase_Ids
	var cErr C.v23_syncbase_VError
	v23_syncbase_ServiceListDatabases(&cIds, &cErr)
	obj := C.NewObjectA(env, arrayListClass.class, arrayListClass.init, nil)
	// TODO(razvanm): populate the obj based on the data from cIds.
	return obj
}

func Java_io_v_syncbase_internal_Database_GetPermissions(env *C.JNIEnv, cls C.jclass, name C.jstring) C.jobject {
	return nil
}
func Java_io_v_syncbase_internal_Database_SetPermissions(env *C.JNIEnv, cls C.jclass, name C.jstring, perms C.jobject) {
}

// maybeThrowException takes ownership of cErr and throws a Java exception if
// cErr represents a non-nil error. Returns a boolean indicating whether an
// exception was thrown.
func maybeThrowException(env *C.JNIEnv, cErr *C.v23_syncbase_VError) bool {
	if obj := cErr.extractToJava(env); obj != nil {
		C.Throw(env, obj)
		return true
	}
	return false
}

//export Java_io_v_syncbase_internal_Database_Create
func Java_io_v_syncbase_internal_Database_Create(env *C.JNIEnv, cls C.jclass, name C.jstring, perms C.jobject) {
	cName := newVStringFromJava(env, name)
	var cErr C.v23_syncbase_VError
	// TODO(razvanm): construct a proper C.v23_syncbase_Permissions based on
	// the perms object.
	v23_syncbase_DbCreate(cName, C.v23_syncbase_Permissions{}, &cErr)
	maybeThrowException(env, &cErr)
}

//export Java_io_v_syncbase_internal_Database_Destroy
func Java_io_v_syncbase_internal_Database_Destroy(env *C.JNIEnv, cls C.jclass, name C.jstring) {
	cName := newVStringFromJava(env, name)
	var cErr C.v23_syncbase_VError
	v23_syncbase_DbDestroy(cName, &cErr)
	maybeThrowException(env, &cErr)
}

//export Java_io_v_syncbase_internal_Database_Exists
func Java_io_v_syncbase_internal_Database_Exists(env *C.JNIEnv, cls C.jclass, name C.jstring) C.jboolean {
	cName := newVStringFromJava(env, name)
	var r C.v23_syncbase_Bool
	var cErr C.v23_syncbase_VError
	v23_syncbase_DbExists(cName, &r, &cErr)
	maybeThrowException(env, &cErr)
	return C.jboolean(r)
}

//export Java_io_v_syncbase_internal_Database_BeginBatch
func Java_io_v_syncbase_internal_Database_BeginBatch(env *C.JNIEnv, cls C.jclass, name C.jstring, opts C.jobject) C.jstring {
	cName := newVStringFromJava(env, name)
	var cHandle C.v23_syncbase_String
	var cErr C.v23_syncbase_VError
	// TODO(razvanm): construct a C.v23_syncbase_BatchOptions from opts.
	v23_syncbase_DbBeginBatch(cName, C.v23_syncbase_BatchOptions{}, &cHandle, &cErr)
	if maybeThrowException(env, &cErr) {
		return nil
	}
	return cHandle.extractToJava(env)
}

//export Java_io_v_syncbase_internal_Database_ListCollections
func Java_io_v_syncbase_internal_Database_ListCollections(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring) C.jobject {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	var cIds C.v23_syncbase_Ids
	var cErr C.v23_syncbase_VError
	v23_syncbase_DbListCollections(cName, cHandle, &cIds, &cErr)
	if maybeThrowException(env, &cErr) {
		return nil
	}
	return cIds.extractToJava(env)
}

//export Java_io_v_syncbase_internal_Database_Commit
func Java_io_v_syncbase_internal_Database_Commit(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring) {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	var cErr C.v23_syncbase_VError
	v23_syncbase_DbCommit(cName, cHandle, &cErr)
	maybeThrowException(env, &cErr)
}

//export Java_io_v_syncbase_internal_Database_Abort
func Java_io_v_syncbase_internal_Database_Abort(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring) {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	var cErr C.v23_syncbase_VError
	v23_syncbase_DbAbort(cName, cHandle, &cErr)
	maybeThrowException(env, &cErr)
}

//export Java_io_v_syncbase_internal_Database_GetResumeMarker
func Java_io_v_syncbase_internal_Database_GetResumeMarker(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring) C.jbyteArray {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	var cMarker C.v23_syncbase_Bytes
	var cErr C.v23_syncbase_VError
	v23_syncbase_DbGetResumeMarker(cName, cHandle, &cMarker, &cErr)
	if maybeThrowException(env, &cErr) {
		return nil
	}
	return cMarker.extractToJava(env)
}

//export Java_io_v_syncbase_internal_Database_ListSyncgroups
func Java_io_v_syncbase_internal_Database_ListSyncgroups(env *C.JNIEnv, cls C.jclass, name C.jstring) C.jobject {
	cName := newVStringFromJava(env, name)
	var cIds C.v23_syncbase_Ids
	var cErr C.v23_syncbase_VError
	v23_syncbase_DbListSyncgroups(cName, &cIds, &cErr)
	if maybeThrowException(env, &cErr) {
		return nil
	}
	return cIds.extractToJava(env)
}

//export Java_io_v_syncbase_internal_Database_CreateSyncgroup
func Java_io_v_syncbase_internal_Database_CreateSyncgroup(env *C.JNIEnv, cls C.jclass, name C.jstring, sgId C.jobject, spec C.jobject, info C.jobject) {
	cName := newVStringFromJava(env, name)
	cSgId := newVIdFromJava(env, sgId)
	cSpec := newVSyngroupSpecFromJava(env, spec)
	cMyInfo := newVSyncgroupMemberInfoFromJava(env, info)
	var cErr C.v23_syncbase_VError
	v23_syncbase_DbCreateSyncgroup(cName, cSgId, cSpec, cMyInfo, &cErr)
	maybeThrowException(env, &cErr)
}

func Java_io_v_syncbase_internal_Database_JoinSyncgroup(env *C.JNIEnv, cls C.jclass, name C.jstring, sgId C.jobject, info C.jobject) C.jobject {
	return nil
}
func Java_io_v_syncbase_internal_Database_LeaveSyncgroup(env *C.JNIEnv, cls C.jclass, name C.jstring, sgId C.jobject) {
}
func Java_io_v_syncbase_internal_Database_DestroySyncgroup(env *C.JNIEnv, cls C.jclass, name C.jstring, sgId C.jobject) {
}
func Java_io_v_syncbase_internal_Database_EjectFromSyncgroup(env *C.JNIEnv, cls C.jclass, name C.jstring, sgId C.jobject, member C.jstring) {
}
func Java_io_v_syncbase_internal_Database_GetSyncgroupSpec(env *C.JNIEnv, cls C.jclass, name C.jstring, sgId C.jobject) C.jobject {
	return nil
}
func Java_io_v_syncbase_internal_Database_SetSyncgroupSpec(env *C.JNIEnv, cls C.jclass, name C.jstring, sgId C.jobject, spec C.jobject) {
}
func Java_io_v_syncbase_internal_Database_GetSyncgroupMembers(env *C.JNIEnv, cls C.jclass, name C.jstring, sgId C.jobject) C.jobject {
	return nil
}
func Java_io_v_syncbase_internal_Database_WatchPatterns(env *C.JNIEnv, cls C.jclass, name C.jstring, resumeMaker C.jbyteArray, patters C.jobject, callbacks C.jobject) {
}

func Java_io_v_syncbase_internal_Collection_GetPermissions(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring) C.jobject {
	return nil
}
func Java_io_v_syncbase_internal_Collection_SetPermissions(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring, perms C.jobject) {
}

//export Java_io_v_syncbase_internal_Collection_Create
func Java_io_v_syncbase_internal_Collection_Create(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring, perms C.jobject) {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	var cErr C.v23_syncbase_VError
	// TODO(razvanm): construct a proper C.v23_syncbase_Permissions based on
	// the perms object.
	v23_syncbase_CollectionCreate(cName, cHandle, C.v23_syncbase_Permissions{}, &cErr)
	maybeThrowException(env, &cErr)
}

//export Java_io_v_syncbase_internal_Collection_Destroy
func Java_io_v_syncbase_internal_Collection_Destroy(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring) {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	var cErr C.v23_syncbase_VError
	v23_syncbase_CollectionDestroy(cName, cHandle, &cErr)
	maybeThrowException(env, &cErr)
}

//export Java_io_v_syncbase_internal_Collection_Exists
func Java_io_v_syncbase_internal_Collection_Exists(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring) C.jboolean {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	var r C.v23_syncbase_Bool
	var cErr C.v23_syncbase_VError
	v23_syncbase_CollectionExists(cName, cHandle, &r, &cErr)
	maybeThrowException(env, &cErr)
	return C.jboolean(r)
}

//export Java_io_v_syncbase_internal_Collection_DeleteRange
func Java_io_v_syncbase_internal_Collection_DeleteRange(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring, start C.jbyteArray, limit C.jbyteArray) {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	cStart := newVBytesFromJava(env, start)
	cLimit := newVBytesFromJava(env, limit)
	var cErr C.v23_syncbase_VError
	v23_syncbase_CollectionDeleteRange(cName, cHandle, cStart, cLimit, &cErr)
	maybeThrowException(env, &cErr)
}

func Java_io_v_syncbase_internal_Collection_Scan(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring, start C.jbyteArray, limit C.jbyteArray, callbacks C.jobject) {
}

//export Java_io_v_syncbase_internal_Row_Exists
func Java_io_v_syncbase_internal_Row_Exists(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring) C.jboolean {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	var r C.v23_syncbase_Bool
	var cErr C.v23_syncbase_VError
	v23_syncbase_RowExists(cName, cHandle, &r, &cErr)
	maybeThrowException(env, &cErr)
	return C.jboolean(r)
}

//export Java_io_v_syncbase_internal_Row_Get
func Java_io_v_syncbase_internal_Row_Get(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring) C.jbyteArray {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	var r C.v23_syncbase_Bytes
	var cErr C.v23_syncbase_VError
	v23_syncbase_RowGet(cName, cHandle, &r, &cErr)
	maybeThrowException(env, &cErr)
	return r.extractToJava(env)
}

//export Java_io_v_syncbase_internal_Row_Put
func Java_io_v_syncbase_internal_Row_Put(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring, value C.jbyteArray) {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	var cErr C.v23_syncbase_VError
	cValue := newVBytesFromJava(env, value)
	v23_syncbase_RowPut(cName, cHandle, cValue, &cErr)
	maybeThrowException(env, &cErr)
}

//export Java_io_v_syncbase_internal_Row_Delete
func Java_io_v_syncbase_internal_Row_Delete(env *C.JNIEnv, cls C.jclass, name C.jstring, handle C.jstring) {
	cName := newVStringFromJava(env, name)
	cHandle := newVStringFromJava(env, handle)
	var cErr C.v23_syncbase_VError
	v23_syncbase_RowDelete(cName, cHandle, &cErr)
	maybeThrowException(env, &cErr)
}

//export Java_io_v_syncbase_internal_Blessings_DebugString
func Java_io_v_syncbase_internal_Blessings_DebugString(env *C.JNIEnv, cls C.jclass) C.jstring {
	var cDebugString C.v23_syncbase_String
	v23_syncbase_BlessingStoreDebugString(&cDebugString)
	return cDebugString.extractToJava(env)
}

//export Java_io_v_syncbase_internal_Blessings_AppBlessingFromContext
func Java_io_v_syncbase_internal_Blessings_AppBlessingFromContext(env *C.JNIEnv, cls C.jclass) C.jstring {
	var cBlessing C.v23_syncbase_String
	var cErr C.v23_syncbase_VError
	v23_syncbase_AppBlessingFromContext(&cBlessing, &cErr)
	maybeThrowException(env, &cErr)
	return cBlessing.extractToJava(env)
}

//export Java_io_v_syncbase_internal_Blessings_UserBlessingFromContext
func Java_io_v_syncbase_internal_Blessings_UserBlessingFromContext(env *C.JNIEnv, cls C.jclass) C.jstring {
	var cBlessing C.v23_syncbase_String
	var cErr C.v23_syncbase_VError
	v23_syncbase_UserBlessingFromContext(&cBlessing, &cErr)
	maybeThrowException(env, &cErr)
	return cBlessing.extractToJava(env)
}

//export Java_io_v_syncbase_internal_Util_Encode
func Java_io_v_syncbase_internal_Util_Encode(env *C.JNIEnv, cls C.jclass, s C.jstring) C.jstring {
	cPlainStr := newVStringFromJava(env, s)
	var cEncodedStr C.v23_syncbase_String
	v23_syncbase_Encode(cPlainStr, &cEncodedStr)
	return cEncodedStr.extractToJava(env)
}

//export Java_io_v_syncbase_internal_Util_EncodeId
func Java_io_v_syncbase_internal_Util_EncodeId(env *C.JNIEnv, cls C.jclass, obj C.jobject) C.jstring {
	cId := newVIdFromJava(env, obj)
	var cEncodedId C.v23_syncbase_String
	v23_syncbase_EncodeId(cId, &cEncodedId)
	return cEncodedId.extractToJava(env)
}

//export Java_io_v_syncbase_internal_Util_NamingJoin
func Java_io_v_syncbase_internal_Util_NamingJoin(env *C.JNIEnv, cls C.jclass, obj C.jobject) C.jstring {
	cElements := newVStringsFromJava(env, obj)
	var cStr C.v23_syncbase_String
	v23_syncbase_NamingJoin(cElements, &cStr)
	return cStr.extractToJava(env)
}

// The functions below are defined in this file and not in jni_types.go due to
// "inconsistent definitions" errors for various functions (C.NewObjectA and
// C.SetObjectField for example).

// extractToJava creates an Id object from a v23_syncbase_Id.
func (x *C.v23_syncbase_Id) extractToJava(env *C.JNIEnv) C.jobject {
	obj := C.NewObjectA(env, idClass.class, idClass.init, nil)
	C.SetObjectField(env, obj, idClass.blessing, x.blessing.extractToJava(env))
	C.SetObjectField(env, obj, idClass.name, x.name.extractToJava(env))
	x.free()
	return obj
}

// newVIds creates a v23_syncbase_Ids from a List<Id>.
func newVIdsFromJava(env *C.JNIEnv, obj C.jobject) C.v23_syncbase_Ids {
	if obj == nil {
		return C.v23_syncbase_Ids{}
	}
	listInterface := newJListInterface(env, obj)
	iterObj := C.CallObjectMethod(env, obj, listInterface.iterator)
	if C.ExceptionOccurred(env) != nil {
		panic("newVIds exception while trying to call List.iterator()")
	}

	iteratorInterface := newJIteratorInterface(env, iterObj)
	tmp := []C.v23_syncbase_Id{}
	for C.CallBooleanMethodA(env, iterObj, iteratorInterface.hasNext, nil) == C.JNI_TRUE {
		idObj := C.CallObjectMethod(env, iterObj, iteratorInterface.next)
		if C.ExceptionOccurred(env) != nil {
			panic("newVIds exception while trying to call Iterator.next()")
		}
		tmp = append(tmp, newVIdFromJava(env, idObj))
	}

	size := C.size_t(len(tmp)) * C.size_t(C.sizeof_v23_syncbase_Id)
	r := C.v23_syncbase_Ids{
		p: (*C.v23_syncbase_Id)(unsafe.Pointer(C.malloc(size))),
		n: C.int(len(tmp)),
	}
	for i := range tmp {
		*r.at(i) = tmp[i]
	}
	return r
}

// extractToJava constructs a jobject from a v23_syncbase_Ids. The pointers
// inside v23_syncbase_Ids will be freed.
func (x *C.v23_syncbase_Ids) extractToJava(env *C.JNIEnv) C.jobject {
	obj := C.NewObjectA(env, arrayListClass.class, arrayListClass.init, nil)
	for i := 0; i < int(x.n); i++ {
		idObj := x.at(i).extractToJava(env)
		arg := *(*C.jvalue)(unsafe.Pointer(&idObj))
		C.CallBooleanMethodA(env, obj, arrayListClass.add, &arg)
	}
	x.free()
	return obj
}

// newVStringsFromJava creates a v23_syncbase_Strings from a List<String>.
func newVStringsFromJava(env *C.JNIEnv, obj C.jobject) C.v23_syncbase_Strings {
	if obj == nil {
		return C.v23_syncbase_Strings{}
	}
	listInterface := newJListInterface(env, obj)
	iterObj := C.CallObjectMethod(env, obj, listInterface.iterator)
	if C.ExceptionOccurred(env) != nil {
		panic("newVStringsFromJava exception while trying to call List.iterator()")
	}

	iteratorInterface := newJIteratorInterface(env, iterObj)
	tmp := []C.v23_syncbase_String{}
	for C.CallBooleanMethodA(env, iterObj, iteratorInterface.hasNext, nil) == C.JNI_TRUE {
		stringObj := C.CallObjectMethod(env, iterObj, iteratorInterface.next)
		if C.ExceptionOccurred(env) != nil {
			panic("newVStringsFromJava exception while trying to call Iterator.next()")
		}
		tmp = append(tmp, newVStringFromJava(env, C.jstring(stringObj)))
	}

	size := C.size_t(len(tmp)) * C.size_t(C.sizeof_v23_syncbase_String)
	r := C.v23_syncbase_Strings{
		p: (*C.v23_syncbase_String)(unsafe.Pointer(C.malloc(size))),
		n: C.int(len(tmp)),
	}
	for i := range tmp {
		*r.at(i) = tmp[i]
	}
	return r
}

// extractToJava constructs a jobject from a v23_syncbase_VError. The pointers
// from inside v23_syncbase_VError will be freed.
func (x *C.v23_syncbase_VError) extractToJava(env *C.JNIEnv) C.jobject {
	if x.id.p == nil {
		return nil
	}
	obj := C.NewObjectA(env, verrorClass.class, verrorClass.init, nil)
	C.SetObjectField(env, obj, verrorClass.id, x.id.extractToJava(env))
	C.SetLongField(env, obj, verrorClass.actionCode, C.jlong(x.actionCode))
	C.SetObjectField(env, obj, verrorClass.message, x.msg.extractToJava(env))
	C.SetObjectField(env, obj, verrorClass.stack, x.stack.extractToJava(env))
	x.free()
	return obj
}
