Skip to content

Minified exception class name is not resolved into the original class name #711

Closed

Description

@ninniuz

If an app has no Proguard/R8 rule to keep Exception class names, then stacktraces on the website will miss the original class name.

it.ninniuz.myapplication.a: null
    at it.ninniuz.myapplication.MainActivity.onCreate(MainActivity.kt:22)
    at android.app.Activity.performCreate(Activity.java:7136)
    at android.app.Activity.performCreate(Activity.java:7127)
    at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1271)
    at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2893)
    at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3048)
    at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:78)
    at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:108)
    at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:68)
    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1808)
    at android.os.Handler.dispatchMessage(Handler.java:106)
    at android.os.Looper.loop(Looper.java:193)
    at android.app.ActivityThread.main(ActivityThread.java:6669)
    at java.lang.reflect.Method.invoke(Method.java)
    at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:493)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:858)

Excerpt from the JSON event:

"exception": {
  "values": [
    {
      "stacktrace": {},
      "type": "a",
      "module": "it.ninniuz.myapplication"
    }
  ]
}

Note that the proguard mapping file has got a reference to this class hence Sentry's symbolicmodule could be able to de-obfuscate this reference:


it.ninniuz.myapplication.CustomException -> it.ninniuz.myapplication.a:
    26:26:void <init>() -> <init>

I have tested de-obfuscating this class reference using the symbolic python module and this is indeed true.

It seems like Sentry backend service is not even trying to resolve <module>.<type> from exception.values items, but just stacktrace frames individually.

I have got a very simple project setup on sentry.io to reproduce the issue, if needed.

Activity

  1. ninniuz commented on May 13, 2019

    @ninniuz
    Author

    I suggest either resolving this directly in the Sentry backend or adding a Proguard rule into the sentry-android-gradle-plugin to keep Throwable class names:

    -keepnames class * extends java.lang.Throwable
    

    In case such rule is added, I would suggest also updating the Sentry documentation for those projects that are not using the Gradle plugin.

  2. bruno-garcia commented on Jun 4, 2019

    @bruno-garcia
    Member

    @ninniuz Thanks for raising this.

    Could you please share the org id in sentry.io with the repro?
    The python module for symbolic uses the same codebase that sentry's event processing does. So it should give the same results. This could be a regression somehow.

    Agree regarding the docs but if symbolic is able to demangle that when you used symbolic python package, this is likely just a fix on the server.

  3. ninniuz commented on Jun 4, 2019

    @ninniuz
    Author

    The org id is andrea-di-menna

  4. bruno-garcia commented on Jun 5, 2019

    @bruno-garcia
    Member

    I can see the mapping file is there and the exception type was not resolved so this looks like a bug indeed.
    I haven't tested with python module symbolic yet, it's strange that it would work there and not in Sentry since it's the same code at the end in both. We need to investigate this further.

  5. kidinov commented on Nov 6, 2019

    @kidinov

    Any update on this issue? It is very annoying and kills a lot of time on manually deobfuscation.

  6. bruno-garcia commented on Nov 6, 2019

    @bruno-garcia
    Member

    Currently, since the proguard mapping file reuses the mangled name and only in combination with a line number is possible to resolve it, we are not able to resolve the class name. We haven't had the time to look for a solution yet.

    In other words, we will look at this again soon. Right now we have two engineers full time working on a better Android support.

  7. bruno-garcia commented on Nov 6, 2019

    @bruno-garcia
    Member

    Ok here's the update:

    You need to define in your proguard rule to keep Exception names:

    -keep public class * extends java.lang.Exception

    On the new SDK this will be included automatically

  8. kidinov commented on Nov 7, 2019

    @kidinov

    Currently, since the proguard mapping file reuses the mangled name and only in combination with a line number is possible to resolve it, we are not able to resolve the class name. We haven't had the time to look for a solution yet.

    Do you know if Crashlytics and others use this approach with line numbers in order to determine exception class name? Because I think at least on Crashlytics this problem was solved like years ago.

    You need to define in your proguard rule to keep Exception names:
    -keep public class * extends java.lang.Exception

    It doesn't look like a solution to the problem but mostly a workaround that will hit an obfuscation quality, which probably not acceptable to many users.

  9. bruno-garcia commented on Nov 7, 2019

    @bruno-garcia
    Member

    This is a limitation of the proguard mapping file, and any crash reporting tool will hit it.

    This is what they have on their docs: https://docs.fabric.io/android/crashlytics/dex-and-proguard.html

    Crashlytics will still function without this rule, but your crash reports will not include proper file names or line numbers.
    
    If you are using custom exceptions, add this line so that custom exception types are skipped during obfuscation:
    
    -keep public class * extends java.lang.Exception
    

    The solution is simply to avoid mangling the exception names.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions