[Soot-list] Problem Instrumenting Kotlin data class

Alessio Gambi alessio.gambi at uni-passau.de
Tue Mar 23 03:44:05 EDT 2021


Hi Marc,

maybe you are right, but the same pattern of code works fine with other apps.

Best

— Alessio 

> On 22. Mar 2021, at 18:29, Marc Miltenberger <marcmiltenberger at gmail.com> wrote:
> 
> Hello Dr. Gambi,
> 
> I see one issue in this line:
> $r0 := @caughtexception
> 
> This does not seem right since $r0 is of type com.orgzly.android.util.Encoding. This should actually be some sort of throwable.
> 
> Best regards,
> Marc Miltenberger
> 
> 
> 
> Am Mo., 22. März 2021 um 18:24 Uhr schrieb Alessio Gambi <alessio.gambi at uni-passau.de <mailto:alessio.gambi at uni-passau.de>>:
> Dear All,
> 
> I am facing a weird problem while instrumenting a Kotlin data class using soot [1].
> 
> The problem is that after instrumenting the class, the byte code verifier rejects the class.
> 
> The method causing this seems to be “copy” that contains those units:
> 
> r0 := @this: com.orgzly.android.util.Encoding
> $r1 := @parameter0: java.lang.String
> $r2 := @parameter1: java.lang.String
> $r3 := @parameter2: java.lang.String
> staticinvoke <kotlin.jvm.internal.Intrinsics: void checkNotNullParameter(java.lang.Object,java.lang.String)>($r1, "used")
> r0 = new com.orgzly.android.util.Encoding
> specialinvoke r0.<com.orgzly.android.util.Encoding: void <init>(java.lang.String,java.lang.String,java.lang.String)>($r1, $r2, $r3)
> return r0
> 
> The same method after the instrumentation looks like the one reported below (I simplified it), where the units marked with ** are the code injected via soot.
> 
> The instrumentations 
> 	- encapsulates all the parameters of method calls into generic arrays of objects
> 	- invokes a Monitor class to track method invocations (before/after) and captures return values
> 	- wraps the method with a generic try-catch-all where the catch block logs the captured exception before rethrowing it
> 
> Now the weirdness (IMHO) is that r0 is assigned first to @this and then to something different (r0 = new com.orgzly.android.util.Encoding).
> This is part of the original code (see above), but I am afraid it might break the instrumented code because we pass r0 as parameter to other invocations in the catch block,
> under the assumption it points to “this”, while in reality it points to another instance of the same type.
> Consequently, the bytecode verifier reports the first call using it  in the catch block (staticinvoke <Monitor: void onAppMethodCaptureException)  as invalid (with type conflict)
> 
> Maybe someone has experiences something similar and/or can suggest a work around? Assuming this is indeed the problem, the only option I see at the moment
>  is to assign the return of  r0 = new com.orgzly.android.util.Encoding to a fresh local variable (rX)
> 
> Any help is appreciated !
> 
> Best
> 
> — Dr. Alessio Gambi
> Chair for SE 2
> University of Passau
> 
> 
> —————
> [1] https://github.com/orgzly/orgzly-android/blob/master/app/src/main/java/com/orgzly/android/util/Encoding.kt <https://github.com/orgzly/orgzly-android/blob/master/app/src/main/java/com/orgzly/android/util/Encoding.kt>
> 
> INSTRUMENTED CODE:
>                  r0 := @this: com.orgzly.android.util.Encoding
>                  $r1 := @parameter0: java.lang.String
>                  $r2 := @parameter1: java.lang.String
>                  $r3 := @parameter2: java.lang.String
> **               $r5 = newarray (java.lang.Object)[3]
> **               $r5[0] = $r1
> **               $r5[1] = $r2
> **               $r5[2] = $r3
> **               staticinvoke <Monitor: void onAppMethodCall(java.lang.String,java.lang.Object,java.lang.String,java.lang.Object[])>("com.orgzly", r0, "<com.orgzly.android.util.Encoding: com.orgzly.android.util.Encoding copy(java.lang.String,java.lang.String,java.lang.String)>", $r5)
> **               $r6 = newarray (java.lang.Object)[2]
> **               $r6[0] = $r1
> **               $r6[1] = "used"
> **               staticinvoke <Monitor: void onLibMethodCall(java.lang.Object,java.lang.String,java.lang.String,java.lang.Object[])>(null, "<kotlin.jvm.internal.Intrinsics: void checkNotNullParameter(java.lang.Object,java.lang.String)>", "<com.orgzly.android.util.Encoding: com.orgzly.android.util.Encoding copy(java.lang.String,java.lang.String,java.lang.String)>", $r6)
>                  staticinvoke <kotlin.jvm.internal.Intrinsics: void checkNotNullParameter(java.lang.Object,java.lang.String)>($r1, "used")
> **               staticinvoke <Monitor: void onLibMethodReturnNormally(java.lang.Object,java.lang.String,java.lang.String,java.lang.Object)>(null, "<kotlin.jvm.internal.Intrinsics: void checkNotNullParameter(java.lang.Object,java.lang.String)>", "<com.orgzly.android.util.Encoding: com.orgzly.android.util.Encoding copy(java.lang.String,java.lang.String,java.lang.String)>", null)
> 
>                  r0 = new com.orgzly.android.util.Encoding
>                  specialinvoke r0.<com.orgzly.android.util.Encoding: void <init>(java.lang.String,java.lang.String,java.lang.String)>($r1, $r2, $r3)
> **               staticinvoke <Monitor: void onAppMethodReturnNormally(java.lang.Object,java.lang.String,java.lang.String,java.lang.Object)>(r0, "<com.orgzly.android.util.Encoding: com.orgzly.android.util.Encoding copy(java.lang.String,java.lang.String,java.lang.String)>", "<com.orgzly.android.util.Encoding: com.orgzly.android.util.Encoding copy(java.lang.String,java.lang.String,java.lang.String)>", r0)
>                  return r0
> 
> **               $r0 := @caughtexception
> **               $r7 = $r0
> **               staticinvoke <Monitor: void onAppMethodCaptureException(java.lang.Object,java.lang.String,java.lang.String,java.lang.Object)>(r0, "<com.orgzly.android.util.Encoding: com.orgzly.android.util.Encoding copy(java.lang.String,java.lang.String,java.lang.String)>", "<com.orgzly.android.util.Encoding: com.orgzly.android.util.Encoding copy(java.lang.String,java.lang.String,java.lang.String)>", $r0)
> **               $r4 = $r0
> **               staticinvoke <Monitor: void onAppMethodThrowException(java.lang.Object,java.lang.String,java.lang.String,java.lang.Object)>(r0, "<com.orgzly.android.util.Encoding: com.orgzly.android.util.Encoding copy(java.lang.String,java.lang.String,java.lang.String)>", "<com.orgzly.android.util.Encoding: com.orgzly.android.util.Encoding copy(java.lang.String,java.lang.String,java.lang.String)>", $r4)
> **               staticinvoke <Monitor: void onAppMethodReturnExceptionally(java.lang.Object,java.lang.String,java.lang.String,java.lang.Object)>(r0, "<com.orgzly.android.util.Encoding: com.orgzly.android.util.Encoding copy(java.lang.String,java.lang.String,java.lang.String)>", "<com.orgzly.android.util.Encoding: com.orgzly.android.util.Encoding copy(java.lang.String,java.lang.String,java.lang.String)>", $r4)
> **               throw $r4
> 
> 
> _______________________________________________
> Soot-list mailing list
> Soot-list at CS.McGill.CA <mailto:Soot-list at CS.McGill.CA>
> https://mailman.CS.McGill.CA/mailman/listinfo/soot-list <https://mailman.cs.mcgill.ca/mailman/listinfo/soot-list>

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://mailman.CS.McGill.CA/pipermail/soot-list/attachments/20210323/aad04007/attachment-0001.html>


More information about the Soot-list mailing list