| // Copyright 2015 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 |
| |
| package context |
| |
| import ( |
| "v.io/v23/context" |
| jutil "v.io/x/jni/util" |
| ) |
| |
| // #include "jni.h" |
| // #include <stdlib.h> |
| import "C" |
| |
| var ( |
| classSign = jutil.ClassSign("java.lang.Class") |
| // Global reference for io.v.v23.context.VContextImpl class. |
| jVContextImplClass C.jclass |
| // Global reference for java.jutil.concurrent.CountDownLatch class. |
| jCountDownLatchClass C.jclass |
| ) |
| |
| // Init initializes the JNI code with the given Java environment. This method |
| // must be called from the main Java thread. |
| // NOTE: Because CGO creates package-local types and because this method may be |
| // invoked from a different package, Java environment is passed in an empty |
| // interface and then cast into the package-local environment type. |
| func Init(jEnv interface{}) error { |
| // Cache global references to all Java classes used by the package. This is |
| // necessary because JNI gets access to the class loader only in the system |
| // thread, so we aren't able to invoke FindClass in other threads. |
| class, err := jutil.JFindClass(jEnv, "io/v/v23/context/VContextImpl") |
| if err != nil { |
| return err |
| } |
| jVContextImplClass = C.jclass(class) |
| class, err = jutil.JFindClass(jEnv, "java/util/concurrent/CountDownLatch") |
| if err != nil { |
| return err |
| } |
| jCountDownLatchClass = C.jclass(class) |
| return nil |
| } |
| |
| //export Java_io_v_v23_context_VContextImpl_nativeCreate |
| func Java_io_v_v23_context_VContextImpl_nativeCreate(env *C.JNIEnv, jVContextImpl C.jclass) C.jobject { |
| ctx, cancel := context.RootContext() |
| jContext, err := JavaContext(env, ctx, cancel) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| return C.jobject(jContext) |
| } |
| |
| //export Java_io_v_v23_context_VContextImpl_nativeDeadline |
| func Java_io_v_v23_context_VContextImpl_nativeDeadline(env *C.JNIEnv, jVContextImpl C.jobject, goPtr C.jlong) C.jobject { |
| d, ok := (*(*context.T)(jutil.Ptr(goPtr))).Deadline() |
| if !ok { |
| return nil |
| } |
| jDeadline, err := jutil.JTime(env, d) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| return C.jobject(jDeadline) |
| } |
| |
| //export Java_io_v_v23_context_VContextImpl_nativeDone |
| func Java_io_v_v23_context_VContextImpl_nativeDone(env *C.JNIEnv, jVContextImpl C.jobject, goPtr C.jlong) C.jobject { |
| c := (*(*context.T)(jutil.Ptr(goPtr))).Done() |
| jCounter, err := JavaCountDownLatch(env, c) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| return C.jobject(jCounter) |
| } |
| |
| //export Java_io_v_v23_context_VContextImpl_nativeValue |
| func Java_io_v_v23_context_VContextImpl_nativeValue(env *C.JNIEnv, jVContextImpl C.jobject, goPtr C.jlong, jKey C.jobject) C.jobject { |
| key, err := GoContextKey(env, jKey) |
| value := (*(*context.T)(jutil.Ptr(goPtr))).Value(key) |
| jValue, err := JavaContextValue(env, value) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| return C.jobject(jValue) |
| } |
| |
| //export Java_io_v_v23_context_VContextImpl_nativeWithCancel |
| func Java_io_v_v23_context_VContextImpl_nativeWithCancel(env *C.JNIEnv, jVContextImpl C.jobject, goPtr C.jlong) C.jobject { |
| ctx, cancelFunc := context.WithCancel((*context.T)(jutil.Ptr(goPtr))) |
| jCtx, err := JavaContext(env, ctx, cancelFunc) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| return C.jobject(jCtx) |
| } |
| |
| //export Java_io_v_v23_context_VContextImpl_nativeWithDeadline |
| func Java_io_v_v23_context_VContextImpl_nativeWithDeadline(env *C.JNIEnv, jVContextImpl C.jobject, goPtr C.jlong, jDeadline C.jobject) C.jobject { |
| deadline, err := jutil.GoTime(env, jDeadline) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| ctx, cancelFunc := context.WithDeadline((*context.T)(jutil.Ptr(goPtr)), deadline) |
| jCtx, err := JavaContext(env, ctx, cancelFunc) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| return C.jobject(jCtx) |
| } |
| |
| //export Java_io_v_v23_context_VContextImpl_nativeWithTimeout |
| func Java_io_v_v23_context_VContextImpl_nativeWithTimeout(env *C.JNIEnv, jVContextImpl C.jobject, goPtr C.jlong, jTimeout C.jobject) C.jobject { |
| timeout, err := jutil.GoDuration(env, jTimeout) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| ctx, cancelFunc := context.WithTimeout((*context.T)(jutil.Ptr(goPtr)), timeout) |
| jCtx, err := JavaContext(env, ctx, cancelFunc) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| return C.jobject(jCtx) |
| } |
| |
| //export Java_io_v_v23_context_VContextImpl_nativeWithValue |
| func Java_io_v_v23_context_VContextImpl_nativeWithValue(env *C.JNIEnv, jVContextImpl C.jobject, goPtr C.jlong, jKey C.jobject, jValue C.jobject) C.jobject { |
| key, err := GoContextKey(env, jKey) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| value, err := GoContextValue(env, jValue) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| ctx := context.WithValue((*context.T)(jutil.Ptr(goPtr)), key, value) |
| jCtx, err := JavaContext(env, ctx, nil) |
| if err != nil { |
| jutil.JThrowV(env, err) |
| return nil |
| } |
| return C.jobject(jCtx) |
| } |
| |
| //export Java_io_v_v23_context_VContextImpl_nativeCancel |
| func Java_io_v_v23_context_VContextImpl_nativeCancel(env *C.JNIEnv, jVContextImpl C.jobject, goCancelPtr C.jlong) { |
| if goCancelPtr != 0 { |
| (*(*context.CancelFunc)(jutil.Ptr(goCancelPtr)))() |
| } |
| } |
| |
| //export Java_io_v_v23_context_VContextImpl_nativeFinalize |
| func Java_io_v_v23_context_VContextImpl_nativeFinalize(env *C.JNIEnv, jVContextImpl C.jobject, goPtr C.jlong, goCancelPtr C.jlong) { |
| jutil.GoUnref(jutil.Ptr(goPtr)) |
| if goCancelPtr != 0 { |
| jutil.GoUnref(jutil.Ptr(goCancelPtr)) |
| } |
| } |