2015-09-09 119 views
0

我能夠遵循jni教程就好了。但是當我改變方法名稱時,我遇到了麻煩。是否有一個我需要遵循的命名約定?本教程使用HelloJNI作爲模塊名稱和庫名稱。我用「useaaacom」。java原生接口方法和模塊名稱的命名約定是什麼?

我對此有很好的反饋,我正在取得進展。我有一個相關的問題;讓我知道我是否應該爲它創建另一個帖子。我喜歡在這個應用程序上構建,該應用程序在此處運行。我如何從設備驅動程序調用函數?我有頭文件,並將驅動程序加載到我的映像中。我的意思是,我需要在我的項目中有一個頭文件的副本嗎?該設備驅動程序由供應商實施,即不屬於AOSP的一部分。自從我下載了整個開源項目並構建它之後,我確實有一份它的副本。所以我問的是我需要什麼在我的apk中的應用程序來調用功能,這是屬於有源設備驅動程序的一部分?

讓我知道我是否應該更多的解釋的任何部分,或者我需要張貼的頭文件或....

我已經驗證了我可以打開一個設備驅動器,具有以下幾行代碼:

#include <stdio.h> 
#include <stdlib.h> 
#include <sys/types.h> 
#include <sys/stat.h> 
#include <fcntl.h> 
#include <unistd.h> 
int main(int argc, char **argv) 
{ 
/* Our file descriptor */ 
int fd; 
int rc = 0; 
char *rd_buf[16]; 
printf("%s: entered\n", argv[0]); 
/* Open the device */ 
fd = open("/dev/hello1", O_RDWR); 
if (fd == -1) { 
perror("open failed"); 
rc = fd; 
exit(-1); 
} 
printf("%s: open: successful\n", argv[0]); 
/* Issue a read */ 
rc = read(fd, rd_buf, 0); 
if (rc == -1) { 
perror("read failed"); 
close(fd); 
exit(-1); 
} 
printf("%s: read: returning %d bytes!\n", argv[0], rc); 
close(fd); 
return 0; 
} 

我想我需要上面的代碼添加到我的JNI夾在.C源文件的形式,並從該文件調用我的設備驅動程序頭文件中的函數?您可能已經注意到上面的代碼是針對名爲「hello1」的測試設備驅動程序。我要將名稱更改爲我的目標設備驅動程序。

+0

方法名稱必須與JNI函數名稱匹配。 – nneonneo

回答

8

Oracle's documentation

動態鏈接程序會解決基於他們的名字條目。本地方法名由下列組分級聯:

  • 前綴Java_
  • 一個錯位完全合格的類名
  • 下劃線(_)分離器
  • 一個錯位的方法名
  • 爲重載的本地方法,兩個下劃線(__),後面跟着破壞的參數簽名

所以,如果你具備以下條件:

package com.foo.bar; 

class Baz { 
    public native void Grill(int i); 
} 

然後相應的C函數應該是:

JNIEXPORT void JNICALL Java_com_foo_bar_Baz_Grill(JNIEnv *env, jobject thiz, jint i); 

如果您在Java方法名下劃線:

public native void A_Grill(int i); 

然後C函數將是:

JNIEXPORT void JNICALL Java_com_foo_bar_Baz_A_1Grill(JNIEnv *env, jobject thiz, jint i); 

_1轉義序列匹配A_Grill_

0

根據語言規則,您可以隨意在Java級別調用您的包和類以及方法,但是C級的命名約定完全由javah工具的輸出定義。

根據文件名規則和'System.load()/ loadLibrary()`的規則,您可以隨意調用共享庫。