Can strace debug an application being debugged by gdb? - android

Background
I'm debugging an Android application using gdb 8.3 under WSL (Windows Subsystem for Linux). When debugging my app gdb frequently catches SIGSEGV and other signals that terminate the application, in general at inconsistent points in the session. These signals do not occur when the app is run without gdb. I have good reason to believe that gdb is the source of the instabilities.
I therefore want to monitor the running gdb-app using strace, in the hope of exercising the app and seeing what system function generates the offending signal when it crashes.
The Problem
strace is unable to attach to the gdb-debugged Android application because it cannot attach to an already attached process.
Here is the gdbserver command to attach to the running process:
dreamlte:/data/local/tmp # ./gdbserver :9999 --attach 26060
Attached; pid = 26060
Listening on port 9999
Remote debugging from host 127.0.0.1
I start gdb, which attaches to the running application.
With gdb attached to the Android application, I attempt to attach strace to the application:
127|dreamlte:/data/local/tmp # ./strace -p 26060
attach: ptrace(PTRACE_ATTACH, ...): Operation not permitted
I understand the problem is that the application process cannot be attached to more than once.
Is there a way to attach strace to a running gdb-app combination?

I understand the problem is that the application process cannot be
attached to more than once.
Yes, this is the limitation of ptrace() system call, see ERRORS section in man ptrace:
EPERM The specified process cannot be traced. This could be because
the tracer has insufficient privileges (the required
capability is CAP_SYS_PTRACE); unprivileged processes cannot
trace processes that they cannot send signals to or those
running set-user-ID/set-group-ID programs, for obvious
reasons. Alternatively, the process may already be being
traced, or (on kernels before 2.6.26) be init(1) (PID 1).
I therefore want to monitor the running gdb-app using strace, in the
hope of exercising the app and seeing what system function generates
the offending signal when it crashes.
Instead, you can see backtrace when the app crashes. You will probably see some system function generating signal or something else you do not expect.

Related

Debugging a native application with GDB on Android

I have a native C++ app which is supposed to run on an Android device. The application crashes at the startup, most likely when calling a function from a linked library. I am trying to debug it with gdb, but I can't succeed.
I am starting gdbserver on the Android device on some arbitrarily picked port (2000):
shell#msm8996: gdbserver :2000 my_app
Process my_app created; pid = 3420
Listening on port 2000
Now I am trying to attach to this process on my Host system (Windows 7) with gdb that was provided in Android-NDK.
C:\> gdb
(gdb) attach 3420
Can't attach to process.
(gdb) target remote :2000
:2000: The system tried to join a drive to a directory on a joined drive.
What is the problem?
EDIT:
Prior to running gdb I forwarded the port 2000 using adb:
adb forward tcp:2000 tcp:2000
This at least helped me to establish some communication, but:
(gdb) target remote :2000
Remote debugging using :2000
warning: Architecture rejected target-supplied description
Remote 'g' packet reply is too long: 00000000000000000000000000000...
On the device side:
Listening on port 2000
Remote debugging from host 127.0.0.1
readchar: Got EOF
Remote side has terminated connection. GDBserver will reopen the connection.
Listening on port 2000
You are most probably using different architecture / version of gdb. When you start the gdb, it displays a line like (I am showing what my GDB shows):
This GDB was configured as "--host=x86_64-linux-gnu
--target=arm-Linux-android"
Check if this matches with your phone's architecture.
Downloading the correct GDB version may solve your problem.

Unable to find android NDK stack-trace

I am developing an app that crashes in NDK code with SIG_SEGV. This causes the app to hang for about 15 seconds, then Android will prompt me to force close it. This prints the java stack-trace to logcat, but I don't see any stack-trace for the NDK. I have redirected stdio with ADB but I still don't see a stack-trace. How can I print C++ stack trace to logcat or where is being printed too?
Using Android 2.3.4
NDK r8b
The "force close" dialog is posted by the crashing application. This sounds like a Dalvik crash rather than a native crash. If the process is receiving a SIGSEGV it should be notifying debuggerd and exiting, leaving a trace in the log. It might be helpful to include logcat output from the crash in your question.
At any rate, recent versions of Android include the native traces mixed in with the Dalvik stack dump when threads are in native code. If you have a rooted device running a recent version of Android, you can ask debuggerd to dump a trace of all threads with adb shell debuggerd -b <pid>.
You're on Android 2.3.x, though, so none of that helps you. Your best option is to send the process a fatal signal to get the debuggerd crash dump. The signal must be sent twice, e.g.:
adb shell kill -6 <pid> ; sleep 1 ; adb shell kill -6 <pid>
This requires a rooted device, as the "shell" user can't send signals to arbitrary processes. Depending on what exactly is going on, you should be able to do this while the "force close" dialog is still on screen... but if the thread managed to crash without taking the process down then there may not be a stack to get a trace from.
You can use the following code to get Log
__android_log_print(ANDROID_LOG_ERROR, "TRACKERS", "%s", Str);
and add the following library
#include <android/log.h>
There is a tool called CheckJNI and the tutorial to set it up is there.

Where to find android crash history

I've been experiencing a great deal of instability on my Verizon Galaxy S III, and I believe it's related to the WiFi driver, or at least something in the networking stack. I get daily full system crashes that cause soft reboots of the OS.
In order to trace to the root of the issue, I'd like to see historical crash data for the Android OS. Please note that I am NOT developing an app, and I do not want instruction on how to use LogCat to trace issues within an in-development app. I want to see the Android system crash logs, but I'm not sure where to look for them.
After ANR happens, you would find call stack of related process at /data/anr/traces.txt
After application crashes, you might find call stack of crashed application under /data/tombstones directory.
See Android: How to get kernel logs after kernel panic?
It looks like /data/dontpanic/ should contain some "apanic" files, but only if the kernel's apanic support is enabled, and it worked. (I haven't seen anything there in my case, but maybe you'll be luckier than I ...)
crash report can be found at default path: /data/anr/
some manufacture place in custom path like: /data/system/ckerror
use cmd: adb pull /data/anr "dest path"
example:
in windows cmd prompt:
adb pull /data/anr c:\trace
The document states that
Android stores trace information when it experiences an ANR. On older OS releases, there's >a single /data/anr/traces.txt file on the device.
On newer OS releases, there are multiple >/data/anr/anr_* files. You can access ANR traces from a device or emulator by using >Android Debug Bridge (adb) as root:
adb root
adb shell ls /data/anr
adb pull /data/anr/<filename>
Usually the every crash is stored in traces.txt file under /data/anr/ folder of internal storage. Try checking this file.
I found a file call crash.txt inside the directory /data/Logging which seems to contain brief stack-traces from the last several crashes that occurred on the device.

Where does Android store shutdown logs?

I know that the boot up log can be obtained by pulling out contents of kmsg or dmesg through ADB.
But I'm not aware of how to retrieve the shutdown logs in Android as there's no /var folder in Android (place where most desktop linux distros generally store their shutdown logs).
So how can I obtain the shutdown logs in Android?
Look in some locations such as these:
/proc/last_kmsg
/data/tombstones/
/data/dontpanic/
/data/system/dropbox/
(This list isn't strictly kernel logs, including framework and application logs too, which are also sometimes of interest)
One work around I found for collecting shutdown logs in Android is to run adb pull /proc/kmsg C:\Logs.txt on the host PC and then switch off the device. You will get the logs till the USB communication between the host and the device snaps! I know this is only one case out of the numerous shutdown scenarios but I haven't found satisfactory answers for other cases!
TL;DR:
Run command through adb that copies logcat and proc/kmsg to a file and keep it running even when adb disconnects with nohup, disown or setsid. Probably needs busybox, needs root and adb root, too.
setsid cat proc/kmsg > /sdcard/kmsg.txt &
and
logcat -v long -f /sdcard/logcat.txt (somehow only works without setsid)
Or add normal copy commands to some startup script.
/TL;DR
You can constantly copy proc/kmsg and logcat to a file on your android device or a microSD card to get the logs even after adb disconnects.
You need root access and adb root access for this to work. For the latter, use the setting in the developer options if you have a custom rom or the adbd insecure app.
After using adb shell to get your android shell, type su to get superuser access.
Then you not only need to put an ampersand (&) after the command but also make sure that the command keeps running after adb disconnects. That is done by nohup, disown or setsid (see here for usage).
If it doesn't work because you don't have these commands, you need to install busybox.
See my question here.
See here for how to get logcat and kernel logs and print it to some file or merge it.
See developer.android.com/tools/help/logcat.html for parameters for the logcat command.
In the end you could have a command like setsid cat proc/kmsg > /sdcard/kmsg.txt & for the kernel messages.
For logcat you could have one of the following commands: logcat -v long -f /sdcard/logcat.txt or logcat -v long > /sdcard/logcat.txt
I don't know why, but sometimes it didn't work with setsid and just didn't copy continuously but stopped shortly after executing the command. In these situations, it also showed up when entering jobs, which it didn't otherwise. Then it just worked without setsid, it stayed alive after disconnecting and reconnecting. I guess you must just try when the file does keep getting larger. If someone figured out why it is behaving like it is... let me know and I'll edit the answer.
Probably adding the commands to a startup script could be a solution for some, too.
Hope this helps.
fightcookie
Newer phones do NOT use any of these locations so if you're reading this article then as of now
The kernel crash logs are now in /sys/fs/pstore instead of /proc/last_kmsg
I was looking for the same thing, and finally, I found the answer!
In android 8 all logs are located in \data\log\android_logs\... including apps and kernel logs. Kernel logs are called kmsgcat-log_timestamp_.gz
edit: Although this is a very old thread, I think the answer might be helpful.

How to send key events to a headless emulator in an instrumentation test?

We are currently working on an instrumentation test suite which runs on our build server, but while the tests pass on a dev machine using a normal Android emulator, the builds fail on the build server since there we only run a headless emulator with the -no-window flag.
The failure occurs when trying to invoke the InstrumentationTestCase.sendKeys() method to programmatically open the options menu. The error is:
Permission denied: injecting key event from pid 646 uid 10026 to window Window{43d55100 paused=false} owned by uid 1000
We then found out that there's a INJECT_EVENTS permission, but setting it in the manifest had no effect. In fact in the log we saw this output:
Not granting permission android.permission.INJECT_EVENTS to package com.qype.radar (protectionLevel=2 flags=0x6644)
Does that mean this permission is useless?
We also tried to let the instrumentation test app and the app under test share the same Linux user ID using android:sharedUserId and run in the same process (android:process -- we weren't sure if that was already the case), but still no luck.
Does this mean it's currently impossible to run instrumentations which contain key events on a headless emulator, or are we missing something?
I run the emulator without -no-window on headless machines by first running an Xvnc instance (i.e. fake X server) then starting the emulator in that DISPLAY.
More accurately, I get the Xvnc and Android Emulator Jenkins plugins to do this for me.
Unfortunately, unlocking the screen is still a concern before injecting UI events, but this is (hackily) resolved by automatically running a command like this (similar to this other answer you've seen):
echo "event send EV_KEY:KEY_MENU:1 EV_KEY:KEY_MENU:0" | nc -q1 localhost 5554
Edit:
I discovered that this method is far more reliable:
adb shell input keyevent 82
Some info about keycode 82.
I had similar problem with my test on the Hudson server. In my case the problem I solved by suggestion from Android SDK:
http://developer.android.com/guide/topics/testing/testing_android.html#UITestTroubleshooting
Important was that I had to enable permissions for main application too.

Categories

Resources