Fix JSON parsing, less libs size and few code updates!

This commit is contained in:
chiteroman 2023-11-29 10:10:07 +01:00
parent 6282b326e3
commit 72f3882054
No known key found for this signature in database
GPG Key ID: 19171A27D600CC72
13 changed files with 1012 additions and 794 deletions

View File

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="deploymentTargetDropDown">
<value>
<entry key="app">
<State />
</entry>
</value>
</component>
</project>

View File

@ -1,18 +1,18 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<project version="4"> <project version="4">
<component name="GradleMigrationSettings" migrationVersion="1" />
<component name="GradleSettings"> <component name="GradleSettings">
<option name="linkedExternalProjectsSettings"> <option name="linkedExternalProjectsSettings">
<GradleProjectSettings> <GradleProjectSettings>
<option name="testRunner" value="GRADLE" />
<option name="distributionType" value="DEFAULT_WRAPPED" />
<option name="externalProjectPath" value="$PROJECT_DIR$" /> <option name="externalProjectPath" value="$PROJECT_DIR$" />
<option name="gradleJvm" value="jbr-17" /> <option name="gradleJvm" value="#GRADLE_LOCAL_JAVA_HOME" />
<option name="modules"> <option name="modules">
<set> <set>
<option value="$PROJECT_DIR$" /> <option value="$PROJECT_DIR$" />
<option value="$PROJECT_DIR$/app" /> <option value="$PROJECT_DIR$/app" />
</set> </set>
</option> </option>
<option name="resolveExternalAnnotations" value="false" />
</GradleProjectSettings> </GradleProjectSettings>
</option> </option>
</component> </component>

10
.idea/migrations.xml Normal file
View File

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectMigrations">
<option name="MigrateToGradleLocalJavaHome">
<set>
<option value="$PROJECT_DIR$" />
</set>
</option>
</component>
</project>

View File

@ -1,4 +1,3 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4"> <project version="4">
<component name="ExternalStorageConfigurationManager" enabled="true" /> <component name="ExternalStorageConfigurationManager" enabled="true" />
<component name="ProjectRootManager" version="2" languageLevel="JDK_17" default="true" project-jdk-name="jbr-17" project-jdk-type="JavaSDK"> <component name="ProjectRootManager" version="2" languageLevel="JDK_17" default="true" project-jdk-name="jbr-17" project-jdk-type="JavaSDK">

View File

@ -2,5 +2,6 @@
<project version="4"> <project version="4">
<component name="VcsDirectoryMappings"> <component name="VcsDirectoryMappings">
<mapping directory="" vcs="Git" /> <mapping directory="" vcs="Git" />
<mapping directory="$PROJECT_DIR$/app/src/main/cpp/libcxx" vcs="Git" />
</component> </component>
</project> </project>

View File

@ -1,4 +1,3 @@
APP_STL := none APP_STL := none
APP_CFLAGS := -Oz -fno-exceptions -fno-rtti -fvisibility=hidden -fvisibility-inlines-hidden APP_CFLAGS := -Oz -fno-exceptions -fno-rtti -fvisibility=hidden -fvisibility-inlines-hidden
APP_CPPFLAGS := -std=c++20 APP_CPPFLAGS := -std=c++20
APP_LDFLAGS := -Oz

File diff suppressed because it is too large Load Diff

View File

@ -1,7 +1,6 @@
#include <android/log.h> #include <android/log.h>
#include <sys/system_properties.h> #include <sys/system_properties.h>
#include <unistd.h> #include <unistd.h>
#include <fstream>
#include "zygisk.hpp" #include "zygisk.hpp"
#include "shadowhook.h" #include "shadowhook.h"
@ -28,15 +27,17 @@ static void modify_callback(void *cookie, const char *name, const char *value, u
std::string_view prop(name); std::string_view prop(name);
if (prop.ends_with("api_level")) { if (prop.ends_with("api_level")) {
if (FIRST_API_LEVEL == "nullptr") { if (FIRST_API_LEVEL.empty()) {
LOGD("FIRST_API_LEVEL is empty, ignoring it...");
} else if (FIRST_API_LEVEL == "nullptr") {
value = nullptr; value = nullptr;
} else { } else {
value = FIRST_API_LEVEL.c_str(); value = FIRST_API_LEVEL.c_str();
} }
LOGD("[%s] -> %s", name, value); LOGD("[%s] -> %s", name, value);
} else if (prop.ends_with("security_patch")) { } else if (prop.ends_with("security_patch")) {
if (SECURITY_PATCH == "nullptr") { if (SECURITY_PATCH.empty()) {
value = nullptr; LOGD("SECURITY_PATCH is empty, ignoring it...");
} else { } else {
value = SECURITY_PATCH.c_str(); value = SECURITY_PATCH.c_str();
} }
@ -80,12 +81,16 @@ public:
} }
void preAppSpecialize(zygisk::AppSpecializeArgs *args) override { void preAppSpecialize(zygisk::AppSpecializeArgs *args) override {
bool isGms = false, isGmsUnstable = false;
auto rawProcess = env->GetStringUTFChars(args->nice_name, nullptr); auto rawProcess = env->GetStringUTFChars(args->nice_name, nullptr);
if (rawProcess) {
std::string_view process(rawProcess); std::string_view process(rawProcess);
bool isGms = process.starts_with("com.google.android.gms"); isGms = process.starts_with("com.google.android.gms");
bool isGmsUnstable = process.compare("com.google.android.gms.unstable") == 0; isGmsUnstable = process.compare("com.google.android.gms.unstable") == 0;
}
env->ReleaseStringUTFChars(args->nice_name, rawProcess); env->ReleaseStringUTFChars(args->nice_name, rawProcess);
@ -101,13 +106,11 @@ public:
return; return;
} }
int dexSize = 0; long dexSize = 0, jsonSize = 0;
int jsonSize = 0;
int fd = api->connectCompanion(); int fd = api->connectCompanion();
read(fd, &dexSize, sizeof(int)); read(fd, &dexSize, sizeof(long));
read(fd, &jsonSize, sizeof(int)); read(fd, &jsonSize, sizeof(long));
if (dexSize < 1) { if (dexSize < 1) {
close(fd); close(fd);
@ -124,19 +127,25 @@ public:
} }
dexVector.resize(dexSize); dexVector.resize(dexSize);
jsonVector.resize(jsonSize);
read(fd, dexVector.data(), dexSize); read(fd, dexVector.data(), dexSize);
std::vector<char> jsonVector(jsonSize);
read(fd, jsonVector.data(), jsonSize); read(fd, jsonVector.data(), jsonSize);
close(fd); close(fd);
LOGD("Read from file descriptor file 'classes.dex' -> %d bytes", dexSize); LOGD("Read from file descriptor file 'classes.dex' -> %ld bytes", dexSize);
LOGD("Read from file descriptor file 'pif.json' -> %d bytes", jsonSize); LOGD("Read from file descriptor file 'pif.json' -> %ld bytes", jsonSize);
std::string data(jsonVector.cbegin(), jsonVector.cend());
json = nlohmann::json::parse(data, nullptr, false, true);
jsonVector.clear();
data.clear();
} }
void postAppSpecialize(const zygisk::AppSpecializeArgs *args) override { void postAppSpecialize(const zygisk::AppSpecializeArgs *args) override {
if (dexVector.empty() || jsonVector.empty()) return; if (dexVector.empty() || json.empty()) return;
readJson(); readJson();
@ -145,7 +154,7 @@ public:
inject(); inject();
dexVector.clear(); dexVector.clear();
jsonVector.clear(); json.clear();
} }
void preServerSpecialize(zygisk::ServerSpecializeArgs *args) override { void preServerSpecialize(zygisk::ServerSpecializeArgs *args) override {
@ -155,15 +164,13 @@ public:
private: private:
zygisk::Api *api = nullptr; zygisk::Api *api = nullptr;
JNIEnv *env = nullptr; JNIEnv *env = nullptr;
std::vector<char> dexVector, jsonVector; std::vector<char> dexVector;
nlohmann::json json;
void readJson() { void readJson() {
std::string data(jsonVector.cbegin(), jsonVector.cend());
nlohmann::json json = nlohmann::json::parse(data, nullptr, false, true);
if (json.contains("SECURITY_PATCH")) { if (json.contains("SECURITY_PATCH")) {
if (json["SECURITY_PATCH"].is_null()) { if (json["SECURITY_PATCH"].is_null()) {
SECURITY_PATCH = "nullptr"; LOGD("Key SECURITY_PATCH is null!");
} else if (json["SECURITY_PATCH"].is_string()) { } else if (json["SECURITY_PATCH"].is_string()) {
SECURITY_PATCH = json["SECURITY_PATCH"].get<std::string>(); SECURITY_PATCH = json["SECURITY_PATCH"].get<std::string>();
} else { } else {
@ -175,17 +182,17 @@ private:
if (json.contains("FIRST_API_LEVEL")) { if (json.contains("FIRST_API_LEVEL")) {
if (json["FIRST_API_LEVEL"].is_null()) { if (json["FIRST_API_LEVEL"].is_null()) {
LOGD("Key FIRST_API_LEVEL is null!");
FIRST_API_LEVEL = "nullptr"; FIRST_API_LEVEL = "nullptr";
} else if (json["FIRST_API_LEVEL"].is_string()) { } else if (json["FIRST_API_LEVEL"].is_string()) {
FIRST_API_LEVEL = json["FIRST_API_LEVEL"].get<std::string>(); FIRST_API_LEVEL = json["FIRST_API_LEVEL"].get<std::string>();
} else { } else {
LOGD("Error parsing FIRST_API_LEVEL!"); LOGD("Error parsing FIRST_API_LEVEL!");
} }
json.erase("FIRST_API_LEVEL");
} else { } else {
LOGD("Key FIRST_API_LEVEL doesn't exist in JSON file!"); LOGD("Key FIRST_API_LEVEL doesn't exist in JSON file!");
} }
json.clear();
} }
void inject() { void inject() {
@ -214,8 +221,7 @@ private:
LOGD("read json"); LOGD("read json");
auto readProps = env->GetStaticMethodID(entryClass, "readJson", auto readProps = env->GetStaticMethodID(entryClass, "readJson",
"(Ljava/lang/String;)V"); "(Ljava/lang/String;)V");
std::string data(jsonVector.cbegin(), jsonVector.cend()); auto javaStr = env->NewStringUTF(json.dump().c_str());
auto javaStr = env->NewStringUTF(data.c_str());
env->CallStaticVoidMethod(entryClass, readProps, javaStr); env->CallStaticVoidMethod(entryClass, readProps, javaStr);
LOGD("call init"); LOGD("call init");
@ -225,22 +231,43 @@ private:
}; };
static void companion(int fd) { static void companion(int fd) {
std::ifstream dex(DEX_FILE_PATH, std::ios::binary); long dexSize = 0, jsonSize = 0;
std::ifstream json(JSON_FILE_PATH); std::vector<char> dexVector, jsonVector;
std::vector<char> dexVector((std::istreambuf_iterator<char>(dex)), FILE *dex = fopen(DEX_FILE_PATH, "rb");
std::istreambuf_iterator<char>());
std::vector<char> jsonVector((std::istreambuf_iterator<char>(json)),
std::istreambuf_iterator<char>());
int dexSize = static_cast<int>(dexVector.size()); if (dex) {
int jsonSize = static_cast<int>(jsonVector.size()); fseek(dex, 0, SEEK_END);
dexSize = ftell(dex);
fseek(dex, 0, SEEK_SET);
write(fd, &dexSize, sizeof(int)); dexVector.resize(dexSize);
write(fd, &jsonSize, sizeof(int)); fread(dexVector.data(), 1, dexSize, dex);
fclose(dex);
}
FILE *json = fopen(JSON_FILE_PATH, "r");
if (json) {
fseek(json, 0, SEEK_END);
jsonSize = ftell(json);
fseek(json, 0, SEEK_SET);
jsonVector.resize(jsonSize);
fread(jsonVector.data(), 1, jsonSize, json);
fclose(json);
}
write(fd, &dexSize, sizeof(long));
write(fd, &jsonSize, sizeof(long));
write(fd, dexVector.data(), dexSize); write(fd, dexVector.data(), dexSize);
write(fd, jsonVector.data(), jsonSize); write(fd, jsonVector.data(), jsonSize);
dexVector.clear();
jsonVector.clear();
} }
REGISTER_ZYGISK_MODULE(PlayIntegrityFix) REGISTER_ZYGISK_MODULE(PlayIntegrityFix)

View File

@ -1,7 +1,7 @@
id=playintegrityfix id=playintegrityfix
name=Play Integrity Fix name=Play Integrity Fix
version=PROPS-v2.0 version=PROPS-v2.1
versionCode=2000 versionCode=2001
author=chiteroman author=chiteroman
description=Fix CTS profile (SafetyNet) and DEVICE verdict (Play Integrity). description=Fix CTS profile (SafetyNet) and DEVICE verdict (Play Integrity).
updateJson=https://raw.githubusercontent.com/chiteroman/PlayIntegrityFix/main/update.json updateJson=https://raw.githubusercontent.com/chiteroman/PlayIntegrityFix/main/update.json

View File

@ -38,7 +38,10 @@ resetprop_if_match ro.boot.mode recovery unknown
resetprop_if_match vendor.boot.mode recovery unknown resetprop_if_match vendor.boot.mode recovery unknown
# SELinux # SELinux
if [ -n "$(getprop ro.build.selinux)" ]; then
resetprop --delete ro.build.selinux resetprop --delete ro.build.selinux
fi
# use toybox to protect *stat* access time reading # use toybox to protect *stat* access time reading
if [ "$(toybox cat /sys/fs/selinux/enforce)" == "0" ]; then if [ "$(toybox cat /sys/fs/selinux/enforce)" == "0" ]; then
chmod 640 /sys/fs/selinux/enforce chmod 640 /sys/fs/selinux/enforce