2012-04-27 5 views
1

これはNDKとAndroid SDKに関連する質問です。 現在、私のCコードはJavaで定義されたメソッドを呼び出しています。このメソッドはcallFromNDK()と呼ばれます。jni - appクラッシュ

この方法では、mediaplayerのインスタンスを参照して、短いテストトーンを再生しています。 callFromNDK()getは2秒ごとに呼び出されます。テストトーン自体は1秒です。

私が見るものは (SIGSEGV)、コード1(SEGV_MAPERR)、時にはフォールトaddr fffffff4です。

mediaplayerインスタンスが使用されているコンテキストとは異なるコンテキストで作成されたため、これが起こっているのでしょうか?

04-27 10:42:13.228: I/DEBUG(8926): Build fingerprint: 'google/passion/passion:2.3.6/GRK39F/189904:user/release-keys' 
04-27 10:42:13.228: I/DEBUG(8926): pid: 10362, tid: 11222 >>> <package_name> <<< 
04-27 10:42:13.228: I/DEBUG(8926): signal 11 (SIGSEGV), code 1 (SEGV_MAPERR), fault addr fffffff4 
04-27 10:42:13.238: I/DEBUG(8926): r0 4214cdc0 r1 00000000 r2 00000000 r3 0000ce68 
04-27 10:42:13.238: I/DEBUG(8926): r4 44628398 r5 00000000 r6 4472fbd8 r7 0000000e 
04-27 10:42:13.238: I/DEBUG(8926): r8 80018000 r9 00000000 10 00000000 fp 800a5368 
04-27 10:42:13.238: I/DEBUG(8926): ip 00000000 sp 4472fb88 lr 8001d084 pc 8001d090 cpsr 60000010 
04-27 10:42:13.238: I/DEBUG(8926): d0 00650072006800b8 d1 00000044bed7f457 
04-27 10:42:13.238: I/DEBUG(8926): d2 0069006400650052 d3 004d0049002e0040 
04-27 10:42:13.238: I/DEBUG(8926): d4 0061006900640065 d5 00790061006c0050 
04-27 10:42:13.238: I/DEBUG(8926): d6 0065005300720065 d7 0063006900760072 
04-27 10:42:13.238: I/DEBUG(8926): d8 0000000000000000 d9 0000000042ba56de 
04-27 10:42:13.238: I/DEBUG(8926): d10 0000000000000000 d11 0000000000000000 
04-27 10:42:13.238: I/DEBUG(8926): d12 0000000000000000 d13 0000000000000000 
04-27 10:42:13.238: I/DEBUG(8926): d14 0000000000000000 d15 0000000000000000 
04-27 10:42:13.238: I/DEBUG(8926): d16 0000000000000001 d17 c053000000000000 
04-27 10:42:13.238: I/DEBUG(8926): d18 0000000000000000 d19 0000000000000000 
04-27 10:42:13.238: I/DEBUG(8926): d20 3ff0000000000000 d21 8000000000000000 
04-27 10:42:13.238: I/DEBUG(8926): d22 0000000000000000 d23 ff00000000000000 
04-27 10:42:13.238: I/DEBUG(8926): d24 ff00000000000000 d25 ff00000000000000 
04-27 10:42:13.238: I/DEBUG(8926): d26 0100010001000100 d27 0100010001000100 
04-27 10:42:13.238: I/DEBUG(8926): d28 0100010001000100 d29 3ff0000000000000 
04-27 10:42:13.238: I/DEBUG(8926): d30 0000000000000000 d31 3ff0000000000000 
04-27 10:42:13.238: I/DEBUG(8926): scr 60000012 
04-27 10:42:13.328: I/DEBUG(8926):   #00 pc 0001d090 /system/lib/libdvm.so 
04-27 10:42:13.328: I/DEBUG(8926):   #01 pc 000220e4 /system/lib/libdvm.so 
04-27 10:42:13.328: I/DEBUG(8926):   #02 pc 00020fdc /system/lib/libdvm.so 
04-27 10:42:13.328: I/DEBUG(8926):   #03 pc 0005fc40 /system/lib/libdvm.so 
04-27 10:42:13.328: I/DEBUG(8926):   #04 pc 0004cff8 /system/lib/libdvm.so 
04-27 10:42:13.328: I/DEBUG(8926):   #05 pc 00001590 /data/data/<package_name>/lib/libtest-jni.so 
04-27 10:42:13.328: I/DEBUG(8926):   #06 pc 000016ca /data/data/<package_name>/lib/libtest-jni.so 
04-27 10:42:13.328: I/DEBUG(8926):   #07 pc 000118e4 /system/lib/libc.so 
04-27 10:42:13.328: I/DEBUG(8926):   #08 pc 000114b0 /system/lib/libc.so 
04-27 10:42:13.328: I/DEBUG(8926): code around pc: 
04-27 10:42:13.328: I/DEBUG(8926): 8001d070 fa0108cc ea000017 e3a00001 e3a09000 
04-27 10:42:13.328: I/DEBUG(8926): 8001d080 ebffff72 e2450014 e5905000 e5909004 
04-27 10:42:13.328: I/DEBUG(8926): 8001d090 e515200c e5963018 e3520000 1592a000 
04-27 10:42:13.328: I/DEBUG(8926): 8001d0a0 e3a01000 0affff8a e1f970b6 e5862010 
04-27 10:42:13.328: I/DEBUG(8926): 8001d0b0 e59a1028 e5835028 e590a010 e1a04009 
04-27 10:42:13.328: I/DEBUG(8926): code around lr: 
04-27 10:42:13.328: I/DEBUG(8926): 8001d064 e088f30c e1a01000 e5960018 fa0108cc 
04-27 10:42:13.328: I/DEBUG(8926): 8001d074 ea000017 e3a00001 e3a09000 ebffff72 
04-27 10:42:13.328: I/DEBUG(8926): 8001d084 e2450014 e5905000 e5909004 e515200c 
04-27 10:42:13.328: I/DEBUG(8926): 8001d094 e5963018 e3520000 1592a000 e3a01000 
04-27 10:42:13.328: I/DEBUG(8926): 8001d0a4 0affff8a e1f970b6 e5862010 e59a1028 
04-27 10:42:13.328: I/DEBUG(8926): stack: 
04-27 10:42:13.328: I/DEBUG(8926):  4472fb48 4472fbe0 
04-27 10:42:13.328: I/DEBUG(8926):  4472fb4c 4214cce4 
04-27 10:42:13.328: I/DEBUG(8926):  4472fb50 0000ce60 
04-27 10:42:13.328: I/DEBUG(8926):  4472fb54 00000001 
04-27 10:42:13.328: I/DEBUG(8926):  4472fb58 4472fbe0 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb5c 80049697 /system/lib/libdvm.so 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb60 4214cce4 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb64 431fbec9 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb68 ad34675d /system/lib/libandroid_runtime.so 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb6c 4472fbe0 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb70 42f8e91e 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb74 4214cd00 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb78 4472fbd8 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb7c 40038360 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb80 df002777 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb84 e3a070ad 
04-27 10:42:13.338: I/DEBUG(8926): #00 4472fb88 4214e32c 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb8c 4472fbd8 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb90 00000001 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb94 002c2c40 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb98 0000ce68 
04-27 10:42:13.338: I/DEBUG(8926):  4472fb9c 000f45b8 
04-27 10:42:13.338: I/DEBUG(8926):  4472fba0 800aad38 
04-27 10:42:13.338: I/DEBUG(8926):  4472fba4 fffffe84 
04-27 10:42:13.338: I/DEBUG(8926):  4472fba8 800a5368 
04-27 10:42:13.338: I/DEBUG(8926):  4472fbac 800220e8 /system/lib/libdvm.so 
04-27 10:42:13.338: I/DEBUG(8926): #01 4472fbb0 4472fbd8 
04-27 10:42:13.338: I/DEBUG(8926):  4472fbb4 0000ce60 
04-27 10:42:13.338: I/DEBUG(8926):  4472fbb8 80022058 /system/lib/libdvm.so 
04-27 10:42:13.338: I/DEBUG(8926):  4472fbbc 423298c8 
04-27 10:42:13.338: I/DEBUG(8926):  4472fbc0 00000000 
04-27 10:42:13.338: I/DEBUG(8926):  4472fbc4 80020fe0 /system/lib/libdvm.so 

任意のアイデアが高く評価されています

ここでは、コードの関連作品[Javaファイル]

public class Canvastutorial extends Activity { 
    private static MediaPlayer mediaPlayer = null; 
    public void callFromNDK() { 
     if (mediaPlayer != null) { 
      mediaPlayer.start(); 
     } 
    } 

    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     mediaPlayer = MediaPlayer.create(getApplicationContext(), R.raw.audioclip); 
     mediaPlayer.setLooping(false); 
    } 

    @Override 
    protected void onDestroy() { 
     mediaPlayer.release(); 
     mediaPlayer = null; 
     System.gc(); 
     super.onDestroy(); 
    } 

    @Override 
    protected void onPause() { 
     stopAndPrepare(); 
     super.onPause(); 
    } 

    private void stopAndPrepare() { 
      mediaPlayer.stop(); 
      try { 
       mediaPlayer.prepare(); 
      } catch (IllegalStateException e) { 
       e.printStackTrace(); 
      } catch (IOException e) { 
       e.printStackTrace(); 
      } 
      mediaPlayer.seekTo(0); 
    } 
} 

だLogCatは、アプリがクラッシュするとき、以下の通りです。

ありがとうございました。

プロジェクトのネイティブ側:thread_function getは定期的(2秒間隔)に呼び出され、Javaコードで定義された関数を呼び出しています。

// Callbacks to Android 
JavaVM *j_vm; 
jobject *j_obj; 
JNIEnv *j_env; 
jclass j_cls; 
jmethodID android_call; 

int JNI_OnLoad(JavaVM* vm, void* reserved) { 
    j_vm = vm; 
    (*j_vm)->GetEnv(j_vm, (void**) &j_env, JNI_VERSION_1_6); 
    j_cls = (*j_env)->FindClass(j_env, "<package_name>/<class_name>"); 
    android_call = (*j_env)->GetMethodID(j_env, j_cls, "callFromNDK", "()V"); 
    j_obj = (*j_env)->NewGlobalRef(j_env, (*j_env)->NewObject(j_env, j_cls, android_call)); 
    return JNI_VERSION_1_6; 
} 

void JNI_OnUnload(JavaVM *vm, void *reserved) { 
    (*j_env)->DeleteGlobalRef(j_env, j_obj); 
} 

void *thread_function(void *ptr) { 
    int *which = (int *) ptr; 
    (*j_vm)->AttachCurrentThread(j_vm, &j_env, NULL); 
    int rc; 
    while (!stop_thread) { 
     rc = pthread_mutex_lock(&mtx); 
     rc = pthread_cond_wait(&cond, &mtx); 
     rc = pthread_mutex_unlock(&mtx); 
     if (!stop_thread) { 
      (*j_env)->CallVoidMethod(j_env, j_obj, android_call); 
     } 
    } 
    (*j_vm)->DetachCurrentThread(j_vm); 
    return NULL; 
} 
+0

何がthread_functionを呼び出していますか?それが特定の問題であっても、mediaPlayer.start()の周りにいくつかのロギングと例外処理を追加することができると思います - その時点で準備されていますよね? mediaplyerドキュメントの再読みに値する。 –

+0

thread_functionはスレッドを作成中に登録された関数ポインタです。これは、スレッドの実行が開始されたときに呼び出される関数です。もちろん、mediaPlayerインスタンスは作成され、nullではありません。アプリは約15〜20分実行され、クラッシュします。アプリがクラッシュするまでの時間は決定的ではありません。 mediaPlayer.start()の周りのデバッグログを持っているのは、問題がどこにないのか分からないからです。 @StarDustが指摘しているように、問題は自分のネイティブコードでなければなりません。ログステートメントを置く以外にネイティブコードをデバッグする方法に関するいくつかのガイドラインを教えてください。どうも。 –

+1

問題はあなたのコードにあるかもしれませんが、ダンプは実際のクラッシュがlibdvm.soにあることを示しています。したがって、DVMをクラッシュさせるためにコードが何をしているのか把握する必要があります。クラッシュの前に実行されたコードの最後の行にある状態を記録すると、特にmediaPlayerオブジェクトを誤って使用している場合に役立ちます。コード内の最後のポイントをより正確に特定するには、アドレスto lineツールまたはobjdumpを使用して、スタックダンプに記述されているlibtest-jni.soの2つのポイントを特定します。 GDBを設定することもできます... –

答えて

0

エミュレータで実行しようとしましたか? libdvmでクラッシュしたので、ネイティブクラッシュの直前に非常に便利なロギングを取得するでしょう。

問題次の行を次のようになります。

j_cls = (*j_env)->FindClass(j_env, "<package_name>/<class_name>"); 

それはあなたが実際の名前空間とクラス名で"<package_name>/<class_name>"を置き換えると仮定しても安全ですか?

+0

はい。 package_nameとclass_nameの詳細が正しく、完全修飾されていると仮定することは安全です。私はエミュレータで試していなかったので、プログラムではオーディオ入力が必要でした。しかしそれは良い提案です。私はオーディオ入力部分を分離し、エミュレータを使用して何が起こるかを見てみましょう。どうも。 –

0

私はこのコードで3つのエラーが表示されますが、CheckJNI(http://android-developers.blogspot.com/2011/07/debugging-android-jni-with-checkjni.html)で実行し、Dalvikはあなたが間違っていたことを教えてください。あなたが気づいた間違いの1つは、ジンジャーブレッドによって発見されません。そして、あなたはジンジャーブレッドでそれを取り除くでしょう。)

あなたは常に使用するべきですCheckJNIの開発とデバッグStackOverflowは、恐らくJNIという単語が含まれている質問を投稿する前に「はい、私はCheckJNIを試しました」というチェックボックスをチェックさせるべきです:

+0

はCheckJNIを認識していませんでした。ここでは初心者のJNIユーザーです。 CheckJNIを使​​ってすべてのコードがうまくいくかどうかを確認します。先端のためのthx。 –

関連する問題