Root detection (Android)
final result = await DeviceShield.checkRoot();Android only. On iOS the status is CheckStatus.notApplicable. Use
jailbreak detection there.
Signals
Section titled “Signals”| Signal | What it checks | Strength |
|---|---|---|
su_binary_path |
An su binary at one of 9 standard paths (/system/bin/su, /system/xbin/su, /sbin/su, /data/local/xbin/su, …) |
Strong |
su_executable |
which su finds an su on the PATH |
Strong |
magisk_artifacts |
Magisk directories: /sbin/.magisk, /cache/.magisk, /data/adb/magisk, /data/adb/modules |
Strong |
writable_system |
The app can create a file in /system or /system/bin (it deletes it immediately) |
Strong |
superuser_apps_installed |
One of 13 root-management apps is installed (Magisk, SuperSU, KingRoot, …) | Medium: installed isn’t the same as rooted |
root_cloaking_apps_installed |
One of 8 root-hiding apps is installed (RootCloak, Hide My Root, Substrate, …) | Medium |
busybox_present |
BusyBox at /system/xbin/busybox or /system/bin/busybox |
Weak: some ROMs ship it |
build_tags_test_keys |
Build.TAGS contains test-keys |
Weak: common on custom ROMs and emulators |
dangerous_system_props |
ro.debuggable=1 or ro.secure=0 |
Weak: fires on engineering builds and some emulator images |
Weak signals fire on many unmodified devices, for example custom ROMs and engineering builds, so they never decide the result. See Detection results for the rule.
Limitations
Section titled “Limitations”- Magisk hides itself by default. Magisk can repackage its app under a random name and hide root from chosen apps (DenyList, Shamiko). A device set up this way can pass every check.
- Package checks depend on the manifest. The app-installed signals rely on
<queries>entries merged from the plugin. See Android setup. - Starts three short-lived processes (
which suand twogetpropcalls), on a background thread.