Droptext.cc

Static slot table + Frida/jnitrace harness

STATIC SLOT TABLE + TRACE HARNESS - dm1.OooOO0O / o0O00OOO.OooO
Analysis only. No code changed.

ENVIRONMENT LIMIT
This environment has no adb, Frida, jnitrace, emulator, NDK, or unidbg jars. I cannot run
the device trace or the dcvm engine here, and I will not fabricate a trace. The static table
below is from the existing spec (dispatch_64.json, handler_class.json, op_jni.json,
member_slots.tsv, isa_table.h) and the decode of the two programs.

The operands are descriptor slot offsets, not method IDs. The class/method name is resolved
at runtime by cacheInitial/getCacheClass; the static spec only gives the JNI call type.

dm1.OooOO0O - 187 bytes at 0x31ebe

slot op JNI call likely real name (confirm with trace)
slot+0xd8 0x9e GetObjectField Intent/ActivityInfo field
slot+0x08 0xd5 GetIntField Intent int field
slot+0xdf 0x8f SetBooleanField ActivityInfo/dm1 boolean
slot+0xdf 0xfa GetBooleanField same boolean
slot+0xd7 0xc8 SetObjectField object field
slot+0xd8 0xc8 SetObjectField object field
slot+0xd9 0xc8 SetObjectField object field
slot+0xd4 0xc8 SetObjectField object field
slot 0x62 0x04 JNI type-signature call runtime-resolved
slot 0x63 0x04 JNI type-signature call runtime-resolved
slot 0x25 0x34 alloc/call runtime-resolved
slot 0x52 0xad JNI call runtime-resolved
slot 0x72 0x04 JNI type-signature call runtime-resolved
slot 0x73 0x04 JNI type-signature call runtime-resolved
slot 0x5a 0x04 JNI type-signature call runtime-resolved
slot 0x41 0xad JNI call runtime-resolved

o0O00OOO.OooO - 130 bytes at 0x32636

slot op JNI call likely real name (confirm with trace)
slot+0x26f 0x9e GetObjectField dm1 field
slot+0xde 0x9e GetObjectField dm1 field
slot 0x5a4 0x04 JNI type-signature call runtime-resolved
slot 0x5a0 0x04 JNI type-signature call runtime-resolved
slot+0xe1 0xfa GetBooleanField boolean field
slot 0x1bd 0x04 JNI type-signature call runtime-resolved
slot 0x59e 0x04 JNI type-signature call runtime-resolved
slot 0x165 0xbe call/instanceof runtime-resolved
slot 0x1c4 0x04 JNI type-signature call runtime-resolved
slot+0x26f 0x9e GetObjectField dm1 field
slot+0x49 0xb2 IsSameObject identity check
slot+0xd6 0x9e GetObjectField dm1 field
slot+0xde 0x9e GetObjectField dm1 field
slot 0x27a 0xe2 JNI call runtime-resolved
slot 0x41 0xb6 JNI call runtime-resolved
slot 0x27a 0xe2 JNI call runtime-resolved
slot 0x42 0xb6 JNI call runtime-resolved
slot 0x494 0x94 JNI call runtime-resolved
slot+0x285 0x9e GetObjectField dm1 field
slot 0x20 0x04 JNI type-signature call runtime-resolved

member_slots.tsv only covers the 30 field slots; most slots above are type-descriptor slots
resolved by the 0x04/0xad/0xe2/0xb6/0x94 handlers.

EXPECTED CALL ORDER (from the decode)
1. dm1.OooOO0O reads Intent + ActivityInfo fields.
2. JNI calls (0x04/0xad/0x34) - the startActivity/Activity path.
3. o0O00OOO.OooO reads the dm1 field, does IsSameObject, reads fields.
4. JNI calls (0xe2/0xb6/0x94) - the Binder/attach path.
5. Proxy FIEL$A* is launched; the target's view is attached to its content view.

The exact transition points (startActivity -> attach -> setContentView/addView) are what the
trace must confirm.

FRIDA SCRIPT (save as hooks.js)

Java.perform(function () {
const log = (tag, args) => console.log(`[${tag}] ` + args.map(String).join(' | '));

const Activity = Java.use('android.app.Activity');
Activity.attach.overload('android.app.ActivityThread','android.os.IBinder','android.app.Activity','java.lang.String','android.app.Activity$NonConfigurationInstances','android.content.res.Configuration','android.os.IBinder','int','android.app.Instrumentation','android.os.Bundle')
.implementation = function () { log('Activity.attach', arguments); return this.attach.apply(this, arguments); };

const Instrumentation = Java.use('android.app.Instrumentation');
Instrumentation.newActivity.overload('java.lang.ClassLoader','java.lang.String','android.content.Intent','android.os.Bundle','boolean')
.implementation = function () { log('Instrumentation.newActivity', [arguments[1], arguments[2]]); return this.newActivity.apply(this, arguments); };

const Window = Java.use('android.view.Window');
Window.setContentView.overload('android.view.View').implementation = function (v) { log('Window.setContentView', [v]); return this.setContentView(v); };
Window.setContentView.overload('int').implementation = function (id) { log('Window.setContentView', [id]); return this.setContentView(id); };

const ViewGroup = Java.use('android.view.ViewGroup');
ViewGroup.addView.overload('android.view.View').implementation = function (v) { log('ViewGroup.addView', [v]); return this.addView(v); };
ViewGroup.addView.overload('android.view.View','android.view.ViewGroup$LayoutParams').implementation = function (v,p) { log('ViewGroup.addView', [v,p]); return this.addView(v,p); };

const Context = Java.use('android.content.Context');
Context.startActivity.overload('android.content.Intent').implementation = function (i) { log('Context.startActivity', [i]); return this.startActivity(i); };
Context.startActivity.overload('android.content.Intent','android.os.Bundle').implementation = function (i,b) { log('Context.startActivity', [i,b]); return this.startActivity(i,b); };

const BinderProxy = Java.use('android.os.BinderProxy');
BinderProxy.transact.overload('int','android.os.Parcel','android.os.Parcel','int')
.implementation = function (c,d,r,f) { log('BinderProxy.transact', [c,d,r,f]); return this.transact(c,d,r,f); };
});

CAPTURE COMMANDS

adb root
adb shell am start -n com.cmaster.cloner/.ui.HomeActivity
PID=$(adb shell pidof com.cmaster.cloner)
adb shell jnitrace -t 1 -p "$PID" -o /data/local/tmp/jnitrace.log
adb shell "frida-server -D &"
frida -U -f com.cmaster.cloner -l hooks.js -o /tmp/cmaster.log
# open one simple app in CMaster, wait for the UI, then Ctrl-D
adb pull /data/local/tmp/jnitrace.log /tmp/jnitrace.log

DCVM RUN (once you have the NDK + unidbg jars)

cd vmtest
java -cp "$(cat /tmp/opencode/dc-build/cp.txt):/tmp/opencode/dcp" EngineRun \
/tmp/opencode/dc-build/dcvm.so /var/tmp/dc-build/lab/lab.apk x \
~/vmlibs/arm64/libcm.so 31ebe bb ~/vmlibs/arm64/libcm.so \
../app/src/main/cpp/spec/dex_members.tsv

java -cp "$(cat /tmp/opencode/dc-build/cp.txt):/tmp/opencode/dcp" EngineRun \
/tmp/opencode/dc-build/dcvm.so /var/tmp/dc-build/lab/lab.apk x \
~/vmlibs/arm64/libcm.so 32636 82 ~/vmlibs/arm64/libcm.so \
../app/src/main/cpp/spec/dex_members.tsv

SEND BACK
/tmp/cmaster.log and /tmp/jnitrace.log. I will fill the slot -> real class.method -> arguments
table and mark every divergence in dcvm.


Kilo

Views: 6, posted on: 2026-11-11

More texts about dm1.OooOO0O / o0O00OOO.OooO trace plan: