Haben Sie die Bibliothek coffeecatch getestet?
Es ist ein JNI-Signal-Catcher, der ermöglicht, SIGSEGV (+) - Signale in die Java-Ausnahmen mit gemischten jni/Java-Backtrace zu drehen. Es funktioniert bis API-19, aber ich hatte noch keine Chance es auf API> 19 zu testen. Es stellt Programmadressen zur Verfügung, die an addr2line übergeben werden können, um die endgültigen Verweise auf eine Quelle zu erhalten.
-Code-Vorlage:
#include "coffeejni.h"
#include "coffeecatch.h"
void MyClass::foo(JNIEnv *env, int arg1, int arg2) {
....
int rc;
COFFEE_TRY_JNI(env, rc = crashInside(arg1, arg2));
....
}
Beispiel der Spur:
F/myapp (24535): "DESIGN ERROR": thread=t1
F/myapp (24535): java.lang.Error: signal 11 (Address not mapped to object) at address 0xdeadbaad [at libc.so:0x18282]
F/myapp (24535): at com.example.NativeSupport.nsc(Native Method)
F/myapp (24535): at com.example.NativeSupport.nsc_quiet(NativeSupport.java:328)
F/myapp (24535): at com.example.NativeSupport.loop(NativeSupport.java:287)
F/myapp (24535): at com.example.NativeSupport.access$2(NativeSupport.java:274)
F/myapp (24535): at com.example.NativeSupport$2.run(NativeSupport.java:124)
F/myapp (24535): at java.lang.Thread.run(Thread.java:856)
F/myapp (24535): Caused by: java.lang.Error: signal 11 (Address not mapped to object) at address 0xdeadbaad [at libc.so:0x18282]
F/myapp (24535): at system.lib.libc_so.0x18282(Native Method)
F/myapp (24535): at system.lib.libc_so.0xdc04(abort:0x4:0)
F/myapp (24535): at data.data.example.lib.libexample_so.0xf147(Native Method)
F/myapp (24535): at data.data.example.lib.libexample_so.0x12d1b(Native Method)
F/myapp (24535): at data.data.example.lib.libexample_so.0x1347b(Native Method)
F/myapp (24535): at data.data.example.lib.libexample_so.0x13969(Native Method)
F/myapp (24535): at data.data.example.lib.libexample_so.0x13ab3(Native Method)
F/myapp (24535): at data.data.example.lib.libexample_so.0x17a9b(Native Method)
F/myapp (24535): at system.lib.libdvm_so.0x1f4b0(dvmPlatformInvoke:0x70:0)
F/myapp (24535): at system.lib.libdvm_so.0x4dfa5(dvmCallJNIMethod(unsigned int const*, JValue*, Method const*, Thread*):0x164:0)
F/myapp (24535): at system.lib.libdvm_so.0x28920(Native Method)
F/myapp (24535): at system.lib.libdvm_so.0x2d0b0(dvmInterpret(Thread*, Method const*, JValue*):0xb4:0)
F/myapp (24535): at system.lib.libdvm_so.0x5f599(dvmCallMethodV(Thread*, Method const*, Object*, bool, JValue*, std::__va_list):0x110:0)
F/myapp (24535): at system.lib.libdvm_so.0x5f5c3(dvmCallMethod(Thread*, Method const*, Object*, JValue*, ...):0x14:0)
F/myapp (24535): at system.lib.libdvm_so.0x549eb(Native Method)
F/myapp (24535): at system.lib.libc_so.0x12dd0(__thread_entry:0x30:0)
F/myapp (24535): at system.lib.libc_so.0x12534(pthread_create:0xac:0)
Native (JNI) Teil der Stack-Trace war:
F/myapp (24535): at data.data.example.lib.libexample_so.0xf147(Native Method)
F/myapp (24535): at data.data.example.lib.libexample_so.0x12d1b(Native Method)
F/myapp (24535): at data.data.example.lib.libexample_so.0x1347b(Native Method)
F/myapp (24535): at data.data.example.lib.libexample_so.0x13969(Native Method)
F/myapp (24535): at data.data.example.lib.libexample_so.0x13ab3(Native Method)
F/myapp (24535): at data.data.example.lib.libexample_so.0x17a9b(Native Method)
Und endlich ein humanoid- lesbare Rückverfolgung:
cd android-ndk/toolchains/arm-linux-androideabi-4.8/prebuilt/linux-x86_64/bin
./arm-linux-androideabi-addr2line -e /home/joe/myproj/obj/local/armeabi-v7a/libexample.so 0xf147 0x12d1b 0x1347b 0x13969 0x13ab3 0x17a9b
Nur um es klarzustellen: Sie versuchen, einen In-App-Crash-Handler zu schreiben, der die Stack-Trace nach einem Fehler erfasst? Der Signal-Handler hat keinen eigenen Stapel, es sei denn, "sigaltstack" wurde verwendet, obwohl es möglich ist, dass der Stapel-Abwickler nicht weiß, wie er über den Signalstapelrahmen tritt. Was ist dein ultimatives Ziel? ACRA für den NDK? – fadden
@fadden: richtig, ich möchte eine Post-Mortem-Stack-Spur bekommen. Es würde erscheinen, da der Signalhandler seinen eigenen Stapel hat, er stammt von 'art :: handleFault' oder etwas ähnlichem (auf 5.0). Was ist ACRA? –
Ich hörte ein Gerücht, dass ART einen eigenen Signal-Handler zur Verfügung stellte, der an den vorherigen Handler angekettet war; Wenn das der Fall ist, werden Sie ein unterschiedliches Verhalten auf 5.0 gegenüber 4.x mit Dalvik sehen. Dies liegt über dem systeminstallierten Signalhandler, der den debuggerd-Systemhandler einspeist (der den Stack-Trace nach einem systemeigenen Absturz an die Protokolldatei ausgibt). Ich dachte nicht, dass die Android-pthread-Bibliothek 'sigaltstack' verwendet, aber ich habe mich noch nicht eingecheckt. Sie müssten SP aus dem Signalrahmen ausgraben und diesen als Ihren Abwicklungspunkt anstelle des aktuellen SP verwenden. – fadden