Chinese document click here
Use fake-linker in combination with Xposed
to provide Java
and Native
bidirectional shielding of Xposed
detection, and also provide additional file redirection, JNI
monitor, file access control, provide to other modules to dynamically add or modify the configuration in the process.
View FakeXposed principle analysis
Android version: Android 5.0
~ Android 11
+. Support instructions: x86
, x86_64
, arm
, arm64
.Api 25
Because the new version of NDK
is removed, you need to change the NDK
version to adapt and compile
- Required build environment: Any platform that supports
Android Studio
,Python 3.6+
(for script build) - Build configuration: Edit local.properties.sample sample configuration and rename it to
local.properties
or pass the configuration path-PconfigPath
togradle
- Clone sources:
git clone --recurse-submodules https://github.com/sanfengAndroid/FakeXposed.git
- Android Studio build: Import the source code into
Android Studio
, modify the configuration and compile - Command line build
- Install Python 3.6+ (Windows platform only: add
Python
to the environment variablePATH
, and runpip install colorama
) - Set
ANDROID_SDK_ROOT
to the system environment variable, and installAndroid NDK 22.0.7026061
, which can be done inAndroid Studio SDK Manager
- Run
python build.py -vrm all
to execute a completeRelease
build - Run
python build.py -vrm api 30
to compile onlyAndroid Api level 30
- For more options, please see the build.py script
- Install Python 3.6+ (Windows platform only: add
Download the latest Release version
- This application is the
Xposed
module, not limited to the originalXposed
,Taichi
,EdXposed
,VirtualXposed
, you need to enable the module in the specifiedXposed manager
.Normal status is as follows - Enable
Global Hook
and specifyApplication Hook
as needed, and the module will determine whether to enable an application separately. Long press to turn on/off - Configure different hook options for each application or globally, such as file blacklist, hidden
maps
rules, file redirection, access control, package visibility, etc. Android 7
The following data sharing usesXSharedPreferences
without additional permissions. If you haveroot
permissions on Android 7 and above, it is recommended to useroot
permissions to install configuration files to another path for other applications to access, otherwise you need to set This software hasself-start
permission, and usesContentProvider
to exchange data, which may significantly increase the start-up time
-
Get the
ClassLoader
of the moduleHook an unused method in the application
ClassLoader.defineClass
XposedHelpers.findAndHookMethod(ClassLoader.class, "defineClass", String.class, byte[].class, int.class, int.class, new XC_MethodHook() { @Override protected void beforeHookedMethod(MethodHookParam param) throws Throwable { String name = (String) param.args[0]; if (TextUtils.equals(name, BuildConfig.APPLICATION_ID)){ LogUtil.d(TAG, "define class get self class"); param.setResult(NativeHook.class); } } });
Obtain
NativeHook.class
by calling as follows. Note thatdefineClass
has several overloaded methods. Only the ones that match the above signature can be obtained, otherwise you will get an exceptionMethod method = ClassLoader.class.getDeclaredMethod("defineClass", String.class, byte[].class, int.class, int.class); method.setAccessible(true); Class<?> nativeHook = (Class<?>) method.invoke(getClassLoader(), BuildConfig.APPLICATION_ID, null, 0, 0);
Get the
NativeHook.class
to get the correspondingClassLoader
, and then call various functions through reflection to add or delete configurationsNote: The loading order of Xposed modules is not controllable, so it is best to enter the application execution timing (such as the application Application.onCreate method) and then obtain
NativeHook.class
, and then use reflection operation, the source package name iscom.sanfengandroid.fakeinterface The classes under
will not be confused -
Invoke interface
The data mainly involves
Java
andNative
data, all of which contains the complete configuration inJava
GlobalConfig, the core data is as followspublic class GlobalConfig { private static final String TAG = GlobalConfig.class.getSimpleName(); private static final Map<String, ?>[] maps; private static final Object EXIST = new Object(); private static final Map<String, String> classBlacklist = new HashMap<>(); private static final Map<String, String> stackClassBlacklist = new HashMap<>(); private static final Map<String, String> packageBlacklist = new HashMap<>(); private static final Map<Integer, Object> hookMethodModifierFilter = new HashMap<>(); private static final ObservableMap<String, String> propBlacklist = new ObservableMap<>(); private static final ObservableMap<String, EnvBean> envBlacklist = new ObservableMap<>(); private static final Map<String, String> globalPropertyBlacklist = new HashMap<>(); private static final Map<String, String> componentKeyBlacklist = new HashMap<>(); private static final Map<String, String> globalSettingsBlacklist = new HashMap<>(); private static final Map<String, ExecBean> runtimeBlackList = new HashMap<>(); private static final Map<String, String> fileBlacklist = new HashMap<>(); private static final Map<String, String> symbolBlacklist = new HashMap<>(); private static final Map<String, String> mapsBlacklist = new HashMap<>(); private static final Map<String, String> fileRedirectList = new HashMap<>(); private static final Map<String, String> fileAccessList = new HashMap<>(); }
-
Java Hook
data modification: directly reflect and modify the aboveMap
object to take effect -Native Hook
data modification: In addition to modifying the aboveMap
object, you need to call NativeInit.nativeSync, which will clear somenative
data (file blacklist, symbol blacklist, attribute replacement, etc.) and then re-synchronized tonative
, which means that some old data is still in effect (maps rule, file redirection, file access permission configuration), but It can be updatedcpp static void NativeHook_ClearAll(JNIEnv *env, jclass clazz) { file_blacklist.clear(); file_path_blacklist.clear(); symbol_blacklist.clear(); properties.clear(); }
There are some otherNative
interfaces that can be viewed by themselves. NativeHook Just call those public methods by reflection
Note: This application may have compatibility issues, please make a backup when the Hook system is in progress
The application has not undergone a lot of testing. If you have any questions, you can leave a message on github, blog or wechat public