11

My application is causing a force close somewhere but instead of getting a FATAL EXCEPTION with the usual (and very informative) stack trace in my LogCat, I only receive only the following 4 lines:

06-27 07:08:54.546: D/dalvikvm(14351): GC_FOR_MALLOC freed 9923 objects / 657416 bytes in 21ms
06-27 07:08:54.769: W/dalvikvm(14351): threadid=20: thread exiting with uncaught exception (group=0x4001d7f0)
06-27 07:08:54.796: W/dalvikvm(14351): threadid=21: thread exiting with uncaught exception (group=0x4001d7f0)
06-27 07:08:54.796: I/Process(14351): Sending signal. PID: 14351 SIG: 9

This is in DEBUG mode with NO FILTERS applied on the LogCat!

  • What could be causing this behavior?
  • Is there a way to tell what's causing this exception?

Update: Thanks to @assylias below, I've been able to implement:

final UncaughtExceptionHandler subclass = Thread.currentThread().getUncaughtExceptionHandler();
Thread.setDefaultUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() {
    @Override
    public void uncaughtException(Thread paramThread, Throwable paramThrowable) {
    Log.getStackTraceString(paramThrowable);

    subclass.uncaughtException(paramThread, paramThrowable);
    }
});

Which produced these added lines:

06-27 08:24:47.105: D/dalvikvm(15475): GC_FOR_MALLOC freed 13865 objects / 1435952 bytes in 45ms
06-27 08:24:47.136: I/dalvikvm(15475): threadid=15: stack overflow on call to Ljava/lang/AbstractStringBuilder;.enlargeBuffer:VI
06-27 08:24:47.136: I/dalvikvm(15475):   method requires 28+20+20=68 bytes, fp is 0x45209338 (56 left)
06-27 08:24:47.140: I/dalvikvm(15475):   expanding stack end (0x45209300 to 0x45209000)
06-27 08:24:47.140: I/dalvikvm(15475): Shrank stack (to 0x45209300, curFrame is 0x4520937c)
06-27 08:24:47.159: I/dalvikvm(15475): threadid=16: stack overflow on call to Ljava/lang/AbstractStringBuilder;.enlargeBuffer:VI
06-27 08:24:47.159: I/dalvikvm(15475):   method requires 28+20+20=68 bytes, fp is 0x4520c338 (56 left)
06-27 08:24:47.167: I/dalvikvm(15475):   expanding stack end (0x4520c300 to 0x4520c000)
06-27 08:24:47.167: I/dalvikvm(15475): Shrank stack (to 0x4520c300, curFrame is 0x4520c37c)
06-27 08:24:47.175: I/dalvikvm(15475): threadid=17: stack overflow on call to Ljava/lang/AbstractStringBuilder;.enlargeBuffer:VI
06-27 08:24:47.175: I/dalvikvm(15475):   method requires 28+20+20=68 bytes, fp is 0x4520f338 (56 left)
06-27 08:24:47.175: I/dalvikvm(15475):   expanding stack end (0x4520f300 to 0x4520f000)
06-27 08:24:47.175: I/dalvikvm(15475): Shrank stack (to 0x4520f300, curFrame is 0x4520f37c)

This is certainly much more useful information, but now I'm struggling with the following:

  • The application doesn't force-close now, despite the call to subclass.uncaughtException(). Why?
  • What is the meaning of all those stack overflows? What could I be doing that's so taxing on my poor Android test device?
  • How can I tell which part in my code causes this?

Update: Log.getStackTraceString(paramThrowable); wasn't actually printing anything. The extra print that I received was from the bogus subclass.uncaughtException(paramThread, paramThrowable); The right way of logging the full stack trace is by using Log.e(TAG, "uncaughtException", throwable).

The only question remaining now is how do I re-throw the exception? Just do a throw paramThrowable?

Answering my last question: Eclipse won't let me throw without surrounding with try/catch, which led me to understand that what I want is not a re-throw but a killProcess(). Problem solved.

4
  • Perhaps using try catch for your code will help to identify. Commented Jun 27, 2012 at 11:36
  • @Mukund Where in my code? I'm already using numerous try/catch clauses all over the place. Commented Jun 27, 2012 at 11:37
  • Add a more general try catch as the answer below,surrounding the entire code in a .java file. Commented Jun 27, 2012 at 11:48
  • @EternalLearner unlike checked Exceptions, eclipse will let you throw an unchecked RuntimeException: just do throw new RuntimeException(paramThrowable); Commented May 14, 2014 at 21:40

3 Answers 3

19

You could set a default uncaught exception handler at the beginning of your app and log some data in there (example below is using a java logger but easy to transpose to Android):

private static void setDefaultUncaughtExceptionHandler() {
    try {
        Thread.setDefaultUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() {

            @Override
            public void uncaughtException(Thread t, Throwable e) {
                logger.error("Uncaught Exception detected in thread {}", t, e);
            }
        });
    } catch (SecurityException e) {
        logger.error("Could not set the Default Uncaught Exception Handler", e);
    }
}
Sign up to request clarification or add additional context in comments.

4 Comments

Thanks +1. I could swear that Android already provides a default uncaught exception handler but I may be mistaken. I will try your approach shortly.
@EternalLearner I am not familiar enough with Android to know if that is the case. See this answer to a different question for a similar approach applied to Android (but probably too complicated for your use!).
Your answer is going to be accepted because it clearly allowed me to make progress in my troubleshooting efforts. However, I'm still struggling with some issues. See my update above. +1.
Great example.Thanks a lot .This example help to me solve this issues "thread exiting with uncaught exception".
2

this is going to be tedious, but i would single step through until it breaks with the debugger. then you can add a more general catch

catch(Exception e){ }

All exceptions extend from Exception so that may help you further diagnose you're problem.

One more idea, perhaps you're app is running up the device memory. The JVM could be killing you're app without telling you because of a JVM shutdown on memory error.

2 Comments

Thanks +1 for turning my attention tothat GC_FOR_MALLOC message right before the exception messages. I didn't think it was relevant so I didn't post it. Now that you mentioned this possibility, I updated my question. I'll see whether your technique works for me.
Assylias' answer down below, is much better than mine. default exception handlers are a good idea if single stepping through a large app is going to take too long.
0

I know this is old but if anyone else wants to know about exiting as normal after dealing with the uncaught exception:

final Thread.UncaughtExceptionHandler androidDefaultUEH = Thread.getDefaultUncaughtExceptionHandler();

Thread.setDefaultUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() {
            @Override
            public void uncaughtException(final Thread thread, final Throwable ex) {
                // Handle exception however you want, then:
                androidDefaultUEH.uncaughtException(thread, ex);
            }
        });

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.