【質問】 Eclipseで作成したアプリで、NDKで作成したlibhello-jni.soを使いたい

8,217 views
Skip to first unread message

waka

unread,
Dec 22, 2011, 3:15:32 AM12/22/11
to 日本Androidの会
こんにちは。
wakaと申します。

Android NDK を使用したアプリを作ってみようと思ったのですが、いきなり躓いています。
私が試してみていることを以下に説明しますので、解決方法をご存知の方はコメントを
よろしくお願いします。

[開発環境]
OS : Ubuntu 10.04 (64bit)
NDK : android-ndk-r7
Eclipse : 3.5.2

(1) NDKのサンプルコード hello-jni をビルドして libhello-jni.so を作成
$ cd android-ndk-r7/samples/hello-jni
$ ../../ndk-build
-> hello-jni/libs/armeabi/libhello-jni.so が生成される

(2) 以前にEclipseで作成したテストアプリ(TestApp01)から libhello-jni.so に含まれる
 関数 stringFromJNI(String) を呼び出す


(1)は成功し、libhello-jni.so が生成されました。また同じく生成された HelloJni.apk を
Eclipseのプロジェクトとして実行し、エミュレータで Hello World が表示されるのを
確認できました。

この後(2)を実行したいのですが、方法が分かりません・・
このページ
http://www.ne.jp/asahi/hishidama/home/tech/java/jni.html
などを見ながら、呼び出す側のアプリのMainActivity.javaに

public native String stringFromJNI();

static{
System.loadLibrary("hello-jni");
}

を追加し、libhello-jni.soをEclipseのプロジェクトの[import]->[general]->[File System]

インポートしてみたのですが、エミュレータを実行すると上記の
System.loadLibrary("hello-jni");
でエラーになってしまいます。

ヘッダファイルが必要?、パスが通っていない? など、疑問は色々あるのですが、
当方の開発スキルが未熟なため解決方法が思いつきません。。

すみませんが、どなたか心当たりのある方はご回答をよろしくお願いします。




KISAKA Toshihiro

unread,
Dec 22, 2011, 7:59:56 AM12/22/11
to android-g...@googlegroups.com
こんばんは、木坂です。

NDK の sample の hello-jni での定義だと函数名が
Java_com_example_hellojni_HelloJni_stringFromJNI()
となっていますが、これを
Java_[loadLibrary している class の package 名の. を _
に置き換えたもの]_[loadLibrary している class 名]_stringFromJNI()
にしてやったりすると、どうでしょう。

あと、ライブラリーの追加は hello-jni の libs を eclipse の project ディレクトリー直下に copy
(あるいは symbolic link を張る等) して、 eclipse で F5 (refresh)
して認識させてやる方法でも大丈夫かもです。

KT
--
KISAKA Toshihiro

tueda

unread,
Dec 23, 2011, 2:39:07 AM12/23/11
to android-g...@googlegroups.com, waka
public native String stringFromJNI();

static{
    	System.loadLibrary("hello-jni");
}

を追加し、libhello-jni.soをEclipseのプロジェクトの[import]->[general]->[File System]
で
インポートしてみたのですが、エミュレータを実行すると上記の
System.loadLibrary("hello-jni");
でエラーになってしまいます。

ネイティブライブラリは${呼び出す側のプロジェクト}/libs/armeabi/に置かないとダメです。
Eclipseの設定は特に必要なく上記のディレクトリに置いておくと勝手にパッケージングしてくれます。
(これパス固定だと思っていますが私が知らないだけで変更する方法があるかもしれません。
誰か方法を知っていたら教えて下さい)

手前味噌でよければ私の昔のメモ書きとか参考になるかもしれません(1年前に書いたのでちょっと古い)。
http://tueda.wikkii.com/wiki/Android%E3%83%97%E3%83%AD%E3%82%B0%E3%83%A9%E3%83%9F%E3%83%B3%E3%82%B0-NDK-HelloWorld





小平稔高

unread,
Dec 23, 2011, 2:53:44 AM12/23/11
to android-g...@googlegroups.com

2011/12/23 16:39 "tueda" <tu...@wolf.dog.cx>:

> public native String stringFromJNI();
>
> static{
> System.loadLibrary("hello-jni");
> }
>

> ...

ネイティブライブラリは${呼び出す側のプロジェクト}/libs/armeabi/に置かないとダメです。
Eclipseの設定は特に必要なく上記のディレクトリに置いておくと勝手にパッケージングしてくれます。
(これパス固定だと思っていますが私が知らないだけで変更する方法があるかもしれません。
誰か方法を知っていたら教えて下さい)

手前味噌でよければ私の昔のメモ書きとか参考になるかもしれません(1年前に書いたのでちょっと古い)。
http://tueda.wikkii.com/wiki/Android%E3%83%97%E3%83%AD%E3%82%B0%E3%83%A9%E3%83%9F%E3%83%B3%E3%82%B0-NDK-HelloWorld





--
このメールは Google グループのグループ「日本Androidの会」の登録者に送られています。
このグループに投稿するには、android-group-japan@googlegroups...

waka

unread,
Dec 26, 2011, 2:56:37 AM12/26/11
to 日本Androidの会
木坂さん、tuedaさん、小平さん

wakaです。
情報ありがとうございます。

ライブラリを /libs/armeabi/ に置いて refresh したところ、
 System.loadLibrary("hello-jni");
はエラーにならず実行されたようです。

その後
 String str = stringFromJNI();
で「stringFromJNI() が見つからない」というエラーになりましたが、
これはおそらくライブラリのビルドで使用したソースファイル内の関数名
jstring Java_com_example_hellojni_HelloJni_stringFromJNI(・・・)
に含まれるパッケージ名(com.example.hellojni)が、現在この関数を
予防としているパッケージの名称と異なるためだと思われます。

これについて1つ疑問があります。
あるアプリのために作成したライブラリを別のアプリで使用したいのですが、
そのためにはライブラリファイル(.so)を /libs/armeabi/ にコピーするだけでは実現できず
(普通はパッケージ名が異なるため)、
結局ソースファイルとヘッダファイルをプロジェクト直下の /jni/ にコピーしてビルドする
必要があるということでしょうか?
(つまり、別の人からライブラリファイルだけをもらっても、私はそれを使うことができない?)

お手数ですが、情報をお持ちでしたらご教授お願いします。

P.S.
tuedaさんがメモ書きで書かれているとおり、ちゃんと本を一冊買って勉強することにしました。
現在「Android NDK ネイティブプログラミング」という本を読んでいます。
JNIの文法はなかなかややこしいですね・・

tueda

unread,
Dec 27, 2011, 8:10:36 AM12/27/11
to android-g...@googlegroups.com, waka

>
> これについて1つ疑問があります。
> あるアプリのために作成したライブラリを別のアプリで使用したいのですが、
> そのためにはライブラリファイル(.so)を /libs/armeabi/ にコピーするだけでは実現できず
> (普通はパッケージ名が異なるため)、
> 結局ソースファイルとヘッダファイルをプロジェクト直下の /jni/ にコピーしてビルドする
> 必要があるということでしょうか?
> (つまり、別の人からライブラリファイルだけをもらっても、私はそれを使うことができない?)

そうなのでネイティブライブラリと一緒にそれを呼び出すjarファイルも一緒に
配布します。
AAA.jar と libAAA.so みたいな。
使う方はjarファイルとそれが使用するネイティブライブラリの置き場所を指定
すれば
(特にネイティブライブラリを意識することなく)普通のjarとして利用できます。


waka

unread,
Jan 5, 2012, 5:03:04 AM1/5/12
to 日本Androidの会
tuedaさん

wakaです。

なるほど、.そういう仕組みになっているのですか。
色々と勉強になりました。

ありがとうございました!
Reply all
Reply to author
Forward
0 new messages