jni,cmd/tailscale: replace jni.JVMFor with direct cast

The JVMFor function converted an uintptr to a pointer, which is not
guaranteed to work in general. This change removes JVMFor, forcing the
unsafe conversion to the user of the jni packge.

Updates tailscale/tailscale#1195

Signed-off-by: Elias Naur <mail@eliasnaur.com>
pull/6/head
Elias Naur 4 years ago
parent d3dc208237
commit 61d9733b24

@ -38,7 +38,7 @@ type backend struct {
// when no nameservers are provided by Tailscale.
avoidEmptyDNS bool
jvm jni.JVM
jvm *jni.JVM
}
type androidRouter struct {
@ -64,7 +64,7 @@ var fallbackNameservers = []netaddr.IP{netaddr.IPv4(8, 8, 8, 8), netaddr.IPv4(8,
// VPN status was revoked.
var errVPNNotPrepared = errors.New("VPN service not prepared or was revoked")
func newBackend(dataDir string, jvm jni.JVM, store *stateStore, settings func(*router.Config) error) (*backend, error) {
func newBackend(dataDir string, jvm *jni.JVM, store *stateStore, settings func(*router.Config) error) (*backend, error) {
logf := logger.RusagePrefixLog(log.Printf)
b := &backend{
jvm: jvm,

@ -12,6 +12,7 @@ import (
"strings"
"sync"
"time"
"unsafe"
"gioui.org/app"
"gioui.org/io/system"
@ -29,7 +30,7 @@ import (
//go:generate go run github.com/go-bindata/go-bindata/go-bindata -nocompress -o logo.go tailscale.png google.png
type App struct {
jvm jni.JVM
jvm *jni.JVM
// appCtx is a global reference to the com.tailscale.ipn.App instance.
appCtx jni.Object
@ -116,7 +117,7 @@ var backendEvents = make(chan UIEvent)
func main() {
a := &App{
jvm: jni.JVMFor(app.JavaVM()),
jvm: (*jni.JVM)(unsafe.Pointer(app.JavaVM())),
appCtx: jni.Object(app.AppContext()),
updates: make(chan struct{}, 1),
}

@ -16,7 +16,7 @@ import (
// backend by androidx.security.crypto.EncryptedSharedPreferences (see
// App.java).
type stateStore struct {
jvm jni.JVM
jvm *jni.JVM
// appCtx is the global Android app context.
appCtx jni.Object
@ -25,7 +25,7 @@ type stateStore struct {
decrypt jni.MethodID
}
func newStateStore(jvm jni.JVM, appCtx jni.Object) *stateStore {
func newStateStore(jvm *jni.JVM, appCtx jni.Object) *stateStore {
s := &stateStore{
jvm: jvm,
appCtx: appCtx,

@ -50,9 +50,7 @@ __attribute__ ((visibility ("hidden"))) jsize _jni_GetArrayLength(JNIEnv *env, j
*/
import "C"
type JVM struct {
jvm *C.JavaVM
}
type JVM C.JavaVM
type Env struct {
env *C.JNIEnv
@ -73,32 +71,30 @@ const (
False Boolean = C.JNI_FALSE
)
func JVMFor(jvmPtr uintptr) JVM {
return JVM{
jvm: (*C.JavaVM)(unsafe.Pointer(jvmPtr)),
}
}
func EnvFor(envPtr uintptr) Env {
return Env{
env: (*C.JNIEnv)(unsafe.Pointer(envPtr)),
}
}
func javavm(vm *JVM) *C.JavaVM {
return (*C.JavaVM)(unsafe.Pointer(vm))
}
// Do invokes a function with a temporary JVM environment. The
// environment is not valid after the function returns.
func Do(vm JVM, f func(env Env) error) error {
func Do(vm *JVM, f func(env Env) error) error {
runtime.LockOSThread()
defer runtime.UnlockOSThread()
var env *C.JNIEnv
if res := C._jni_GetEnv(vm.jvm, &env, C.JNI_VERSION_1_6); res != C.JNI_OK {
if res := C._jni_GetEnv(javavm(vm), &env, C.JNI_VERSION_1_6); res != C.JNI_OK {
if res != C.JNI_EDETACHED {
panic(fmt.Errorf("JNI GetEnv failed with error %d", res))
}
if C._jni_AttachCurrentThread(vm.jvm, &env, nil) != C.JNI_OK {
if C._jni_AttachCurrentThread(javavm(vm), &env, nil) != C.JNI_OK {
panic(errors.New("runInJVM: AttachCurrentThread failed"))
}
defer C._jni_DetachCurrentThread(vm.jvm)
defer C._jni_DetachCurrentThread(javavm(vm))
}
return f(Env{env})

Loading…
Cancel
Save