2012-04-25 33 views
10

Tôi có một trình bao bọc JNI cho các hàm Java được gọi từ C ... Tôi đang cố gắng gọi một số phương thức từ các luồng khác nhau và tôi gặp lỗi khi cố gắng lấy một bản sao mới của con trỏ JNIEnv ... mã tôi đang sử dụng ở bên dưới và được gọi theo từng phương thức:JNI - nhiều chủ đề

 JNIEnv* GetJniEnvHandle(){ 
     ThreadInfo(); 
     JNIEnv *envLoc; 
     //if(Thread::CurrentThread->IsBackground || Thread::CurrentThread->IsThreadPoolThread) 
     jint envRes = vm->GetEnv((void**)&envLoc, JNI_VERSION_1_4); 
     if(envRes == JNI_OK){ 
      if(ThreadId != Thread::CurrentThread->ManagedThreadId) 
       jint res = vm->AttachCurrentThread((void**)&envLoc, NULL); 
     }else{   
      Log("Error obtaining JNIEnv* handle"); 
     } 
     return envLoc; 
    } 

JVM đã được khởi tạo và phương thức này (và các phương thức khác) chạy khi được gọi từ chuỗi chính/ban đầu. Khi tôi nhận được một giá trị cho envRes nó giữ một -2 khi trong một tiểu chủ đề.

Trả lời

15

Vui lòng tham khảo documentation đến chương Attaching to the VM.

Bạn cần gọi số AttachCurrentThread() cho từng chuỗi gốc ít nhất một lần trước khi bạn có thể sử dụng bất kỳ chức năng JNI nào.
Chủ đề được tạo bằng Java đã được đính kèm.
Vì vậy, tôi là ví dụ của bạn bất cứ khi nào cuộc gọi GetEnv không thành công, hãy gọi AttachCurrentThread() và bạn sẽ ổn. Hoặc chắc chắn rằng khi bạn tạo một tiểu chủ đề bạn đính kèm nó vào máy ảo.

+0

đó là nó - giám sát rất đơn giản trên phần của tôi lol. Chỉ cần hoán đổi thứ tự của hai cuộc gọi JNI và nó hoạt động hoàn hảo! Cảm ơn! – bbqchickenrobot

Các vấn đề liên quan