Categories
Development

Casting a borrowed reference with a lifetime to a raw pointer in Rust

I am new to rust and am trying to wrap my head around lifetimes. Please consider the following code:

use jni::JNIEnv;

pub struct CameraAppEngine<'a> {
    _env: &'a JNIEnv<'a>,
    _width: i32,
    _height: i32
}

impl<'a> CameraAppEngine<'a> {
    pub fn new(_env: &'a JNIEnv<'a>, _width: i32, _height: i32) -> CameraAppEngine {
        CameraAppEngine { _env, _width, _height }
    }

    pub fn env(&'a self) -> JNIEnv<'a> {
        JNIEnv::from_raw(self._env).unwrap() // error!
    }
}

The JNIEnv::from_raw method has a type signature of from_raw(ptr: *mut JNIEnv) -> Result<Self>, so this results in the compile error:

|         JNIEnv::from_raw(self._env).unwrap()
|                          ^^^^^^^^^ types differ in mutability
|
= note: expected raw pointer `*mut *const jni::sys::JNINativeInterface_`
                found reference `&'a jni::JNIEnv<'a>`

I then tried JNIEnv::from_raw(self._env as *mut JNIEnv<'a>).unwrap(), but this results in:

|         JNIEnv::from_raw(self._env as *mut JNIEnv<'a>).unwrap() // error!
|                          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected *-ptr, found struct `jni::JNIEnv`
|
= note: expected raw pointer `*mut *const jni::sys::JNINativeInterface_`
            found raw pointer `*mut jni::JNIEnv<'a>`

error[E0606]: casting `&'a jni::JNIEnv<'a>` as `*mut jni::JNIEnv<'a>` is invalid
--> native_app/src/camera_engine.rs:16:26
|
|         JNIEnv::from_raw(self._env as *mut JNIEnv<'a>).unwrap() // error!
|                          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^

How do I get a valid JNIEnv out of the reference in the struct?

Cheers and thank you for your time!

Update

Here is a less contrived way to demonstrate the prolem.

pub fn create_camera_session(&'a mut self, surface: jobject) {
    // error!
    let window = ffi::ANativeWindow_fromSurface(self._env as *mut JNIEnv<'a>, surface);
}

This results in:

error[E0606]: casting `&'a jni::JNIEnv<'a>` as `*mut jni::JNIEnv<'a>` is invalid

The type signature of ANativeWindow_fromSurface is ANativeWindow_fromSurface(env: *mut JNIEnv, surface: jobject) -> *mut ANativeWindow.

Leave a Reply

Your email address will not be published. Required fields are marked *