From 8594bfc76635487289ac479a1ba7cc2f288626e7 Mon Sep 17 00:00:00 2001 From: LoveSy Date: Mon, 1 Mar 2021 00:43:23 +0800 Subject: [PATCH] [core] Remove key selector & optimize binary size (#233) * [core] Remove key selector & optimize binary size * More clean up * Remove useless flags --- core/build.gradle | 22 +- core/src/main/cpp/dynamic_list | 3 + core/src/main/cpp/main/CMakeLists.txt | 6 +- core/src/main/cpp/main/include/utils.h | 51 --- core/src/main/cpp/main/src/context.cpp | 4 +- core/src/main/cpp/main/src/context.h | 2 +- core/src/main/cpp/main/src/main.cpp | 6 +- core/src/main/cpp/main/src/rirud_socket.cpp | 8 +- core/src/main/cpp/main/src/rirud_socket.h | 2 +- core/template_override/customize.sh | 33 +- core/template_override/util_functions.sh | 2 +- core/template_override/zh_CN.sh | 2 - key-selector/.gitignore | 1 - key-selector/build.gradle | 97 ------ key-selector/src/main/AndroidManifest.xml | 25 -- key-selector/src/main/cpp/CMakeLists.txt | 25 -- key-selector/src/main/cpp/Languages.h | 72 ---- key-selector/src/main/cpp/key_selector.cpp | 361 -------------------- key-selector/src/main/cpp/key_selector.h | 65 ---- settings.gradle | 2 +- 20 files changed, 32 insertions(+), 757 deletions(-) create mode 100644 core/src/main/cpp/dynamic_list delete mode 100644 key-selector/.gitignore delete mode 100644 key-selector/build.gradle delete mode 100644 key-selector/src/main/AndroidManifest.xml delete mode 100644 key-selector/src/main/cpp/CMakeLists.txt delete mode 100644 key-selector/src/main/cpp/Languages.h delete mode 100644 key-selector/src/main/cpp/key_selector.cpp delete mode 100644 key-selector/src/main/cpp/key_selector.h diff --git a/core/build.gradle b/core/build.gradle index 4005a671..bcf2eff1 100644 --- a/core/build.gradle +++ b/core/build.gradle @@ -58,7 +58,6 @@ dependencies { implementation 'com.android.tools.build:apksig:4.1.2' implementation project(path: ':sandhook-hooklib') compileOnly project(':hiddenapi-stubs') - compileOnly project(':key-selector') compileOnly 'androidx.annotation:annotation:1.1.0' implementation project(':interface') implementation project(':hiddenapi-bridge') @@ -80,8 +79,8 @@ android { externalNativeBuild { cmake { abiFilters 'arm64-v8a', 'armeabi-v7a', 'x86', 'x86_64' - cppFlags "-std=c++17 -ffixed-x18 -Qunused-arguments -frtti -fomit-frame-pointer" - cFlags "-std=gnu99 -ffixed-x18 -Qunused-arguments -frtti -fomit-frame-pointer" + cppFlags "-std=c++17 -ffixed-x18 -Qunused-arguments -frtti -fomit-frame-pointer -fpie -fPIC" + cFlags "-std=gnu99 -ffixed-x18 -Qunused-arguments -frtti -fomit-frame-pointer -fpie -fPIC" arguments "-DRIRU_MODULE_API_VERSION=$moduleMaxRiruApiVersion", "-DRIRU_MODULE_VERSION=$rootProject.ext.versionCode", "-DRIRU_MODULE_VERSION_NAME:STRING=\"$rootProject.ext.versionName\"" @@ -113,8 +112,8 @@ android { externalNativeBuild { cmake { - cppFlags "-fvisibility=hidden -fvisibility-inlines-hidden -O2 -s -Wno-unused-value -fomit-frame-pointer" - cFlags "-fvisibility=hidden -fvisibility-inlines-hidden -O2 -s -Wno-unused-value -fomit-frame-pointer" + cppFlags "-fvisibility=hidden -fvisibility-inlines-hidden -Os -Wno-unused-value -fomit-frame-pointer -ffunction-sections -fdata-sections -Wl,--gc-sections -Wl,--strip-all -fno-unwind-tables" + cFlags "-fvisibility=hidden -fvisibility-inlines-hidden -Os -Wno-unused-value -fomit-frame-pointer -ffunction-sections -fdata-sections -Wl,--gc-sections -Wl,--strip-all -fno-unwind-tables" } } } @@ -143,7 +142,6 @@ afterEvaluate { def prepareMagiskFilesTask = task("prepareMagiskFiles${variantCapped}") { dependsOn "assemble${variantCapped}" - dependsOn tasks.getByPath(":key-selector:copyKeySelector${variantCapped}LibraryToMagiskTemplate") doFirst { copy { from "${projectDir}/tpl/module.prop.tpl" @@ -190,22 +188,26 @@ afterEvaluate { eol: FixCrLfFilter.CrLf.newInstance("lf")) } copy { - include "libriru_lspd.so" + include "riru_lspd" + rename('riru_lspd', 'libriru_lspd.so') from "$libPathRelease/armeabi-v7a" into "$zipPathMagiskReleasePath/system/lib" } copy { - include "libriru_lspd.so" + include "riru_lspd" + rename('riru_lspd', 'libriru_lspd.so') from "$libPathRelease/arm64-v8a" into "$zipPathMagiskReleasePath/system/lib64" } copy { - include "libriru_lspd.so" + include "riru_lspd" + rename('riru_lspd', 'libriru_lspd.so') from "$libPathRelease/x86" into "$zipPathMagiskReleasePath/system_x86/lib" } copy { - include "libriru_lspd.so" + include "riru_lspd" + rename('riru_lspd', 'libriru_lspd.so') from "$libPathRelease/x86_64" into "$zipPathMagiskReleasePath/system_x86/lib64" } diff --git a/core/src/main/cpp/dynamic_list b/core/src/main/cpp/dynamic_list new file mode 100644 index 00000000..5b4815d5 --- /dev/null +++ b/core/src/main/cpp/dynamic_list @@ -0,0 +1,3 @@ +{ +init; +}; \ No newline at end of file diff --git a/core/src/main/cpp/main/CMakeLists.txt b/core/src/main/cpp/main/CMakeLists.txt index ab3f0018..ef5ac3e3 100644 --- a/core/src/main/cpp/main/CMakeLists.txt +++ b/core/src/main/cpp/main/CMakeLists.txt @@ -20,12 +20,12 @@ cmake_minimum_required(VERSION 3.4.1) -set(CMAKE_ANDROID_STL_TYPE c++_static) - aux_source_directory(src SRC_LIST) aux_source_directory(src/jni SRC_JNI_LIST) include_directories(include src) -add_library(riru_lspd SHARED ${SRC_LIST} ${SRC_JNI_LIST}) +add_executable(riru_lspd ${SRC_LIST} ${SRC_JNI_LIST}) + +SET(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -Wl,--dynamic-list=${CMAKE_SOURCE_DIR}/dynamic_list") find_package(riru REQUIRED CONFIG) find_library(log-lib log) diff --git a/core/src/main/cpp/main/include/utils.h b/core/src/main/cpp/main/include/utils.h index 1804540a..bdd30cd8 100644 --- a/core/src/main/cpp/main/include/utils.h +++ b/core/src/main/cpp/main/include/utils.h @@ -35,55 +35,4 @@ namespace lspd { __system_property_get("ro.build.version.sdk", prop_value); return atoi(prop_value); } - - static inline std::string GetAndroidBrand() { - char prop_value[PROP_VALUE_MAX]; - __system_property_get("ro.product.brand", prop_value); - return prop_value; - } - - template - inline bool path_exists(const std::filesystem::path &path) { - try { - return std::filesystem::exists(path); - } catch (const std::filesystem::filesystem_error &e) { - if constexpr(!quite) { - LOGE("%s", e.what()); - } - return false; - } - } - - inline void - path_chown(const std::filesystem::path &path, uid_t uid, gid_t gid, bool recursively = false) { - if (chown(path.c_str(), uid, gid) != 0) { - throw std::filesystem::filesystem_error(strerror(errno), path, - {errno, std::system_category()}); - } - if (recursively) { - for (const auto &item : std::filesystem::recursive_directory_iterator(path)) { - if (chown(item.path().c_str(), uid, gid) != 0) { - throw std::filesystem::filesystem_error(strerror(errno), item.path(), - {errno, std::system_category()}); - } - } - } - } - - inline std::tuple path_own(const std::filesystem::path &path) { - struct stat sb; - stat(path.c_str(), &sb); - return {sb.st_uid, sb.st_gid}; - } - - inline void recursive_permissions(const std::filesystem::path &p, - std::filesystem::perms prms, - std::filesystem::perm_options opts = std::filesystem::perm_options::replace) { - std::filesystem::permissions(p, prms, opts); - if (std::filesystem::is_directory(p)) { - for(auto &item : std::filesystem::recursive_directory_iterator(p)) { - std::filesystem::permissions(item.path(), prms, opts); - } - } - } } diff --git a/core/src/main/cpp/main/src/context.cpp b/core/src/main/cpp/main/src/context.cpp index b0cbce81..287e6801 100644 --- a/core/src/main/cpp/main/src/context.cpp +++ b/core/src/main/cpp/main/src/context.cpp @@ -40,8 +40,6 @@ #include "rirud_socket.h" namespace lspd { - namespace fs = std::filesystem; - constexpr int FIRST_ISOLATED_UID = 99000; constexpr int LAST_ISOLATED_UID = 99999; constexpr int FIRST_APP_ZYGOTE_ISOLATED_UID = 90000; @@ -63,7 +61,7 @@ namespace lspd { } } - void Context::PreLoadDex(const fs::path &dex_path) { + void Context::PreLoadDex(const std::string &dex_path) { if (LIKELY(!dex.empty())) return; try { diff --git a/core/src/main/cpp/main/src/context.h b/core/src/main/cpp/main/src/context.h index 553d7194..a3908be0 100644 --- a/core/src/main/cpp/main/src/context.h +++ b/core/src/main/cpp/main/src/context.h @@ -64,7 +64,7 @@ namespace lspd { void OnNativeForkSystemServerPre(JNIEnv *env); - void PreLoadDex(const std::filesystem::path &dex_paths); + void PreLoadDex(const std::string &dex_paths); private: inline static std::unique_ptr instance_ = std::make_unique(); diff --git a/core/src/main/cpp/main/src/main.cpp b/core/src/main/cpp/main/src/main.cpp index 3e6a7603..0b4d3200 100644 --- a/core/src/main/cpp/main/src/main.cpp +++ b/core/src/main/cpp/main/src/main.cpp @@ -94,7 +94,7 @@ namespace lspd { int riru_api_version; -RIRU_EXPORT void *init(void *arg) { +RIRU_EXPORT __attribute__((noinline)) void *init(void *arg) { static int step = 0; step += 1; @@ -145,3 +145,7 @@ RIRU_EXPORT void *init(void *arg) { } } } + +int main(){ + init(nullptr); +} \ No newline at end of file diff --git a/core/src/main/cpp/main/src/rirud_socket.cpp b/core/src/main/cpp/main/src/rirud_socket.cpp index 68a39b68..00726a0d 100644 --- a/core/src/main/cpp/main/src/rirud_socket.cpp +++ b/core/src/main/cpp/main/src/rirud_socket.cpp @@ -25,8 +25,6 @@ #include #include -namespace fs = std::filesystem; - template<> void RirudSocket::Write(const std::string &str) { auto count = str.size(); @@ -79,10 +77,10 @@ RirudSocket::~RirudSocket() { close(fd_); } -std::string RirudSocket::ReadFile(const fs::path &path) { +std::string RirudSocket::ReadFile(const std::string &path) { Write(ACTION_READ_FILE); - Write(static_cast(path.string().size())); - Write(path.string()); + Write(static_cast(path.size())); + Write(path); int32_t rirud_errno; Read(rirud_errno); if(rirud_errno != 0) { diff --git a/core/src/main/cpp/main/src/rirud_socket.h b/core/src/main/cpp/main/src/rirud_socket.h index b01d04b9..378d0e74 100644 --- a/core/src/main/cpp/main/src/rirud_socket.h +++ b/core/src/main/cpp/main/src/rirud_socket.h @@ -35,7 +35,7 @@ public: RirudSocket(); - std::string ReadFile(const std::filesystem::path &path); + std::string ReadFile(const std::string &path); // DirIter ReadDir(const std::filesystem::path &path); // DirIter RecursiveReadDir(const std::filesystem::path &path); diff --git a/core/template_override/customize.sh b/core/template_override/customize.sh index 01813754..cced89e3 100644 --- a/core/template_override/customize.sh +++ b/core/template_override/customize.sh @@ -106,8 +106,6 @@ LANG_UTIL_ERR_ANDROID_UNSUPPORT_1="Unsupported Android version" LANG_UTIL_ERR_ANDROID_UNSUPPORT_2="(below Oreo)" LANG_UTIL_ERR_ANDROID_UNSUPPORT_3="Learn more from our GitHub Wiki" LANG_UTIL_ERR_PLATFORM_UNSUPPORT="Unsupported platform" -LANG_UTIL_ERR_VARIANT_SELECTION="Error occurred when selecting variant" -LANG_UTIL_ERR_VARIANT_UNSUPPORT="Unsupported variant" LANG_CUST_INST_MIGRATE_CONF="Migrating configuration" # Load lang @@ -141,20 +139,6 @@ check_android_version check_riru_version lspd_check_architecture -# determinate variant -if [ "${ARCH}" == "arm" ]; then - BIN_PATH="system/bin" -elif [ "${ARCH}" == "arm64" ]; then - BIN_PATH="system/bin64" -elif [ "${ARCH}" == "x86" ]; then - BIN_PATH="system_x86/bin" -elif [ "${ARCH}" == "x64" ]; then - BIN_PATH="system_x86/bin64" -else - # unreachable - abortC "${LANG_UTIL_ERR_PLATFORM_UNSUPPORT}" -fi - ui_print "- ${LANG_CUST_INST_EXT_FILES}" # extract module files @@ -230,22 +214,7 @@ fi echo "rm -rf /data/misc/$MISC_PATH" >> "${MODPATH}/uninstall.sh" || abortC "! ${LANG_CUST_ERR_CONF_UNINST}" echo "[[ -f /data/adb/lspd/new_install ]] || rm -rf /data/adb/lspd" >> "${MODPATH}/uninstall.sh" || abortC "! ${LANG_CUST_ERR_CONF_UNINST}" -extract "${ZIPFILE}" "${BIN_PATH}/key_selector" "${TMPDIR}" -SELECTOR_PATH="${TMPDIR}/${BIN_PATH}/key_selector" -chmod 755 "${SELECTOR_PATH}" -"${SELECTOR_PATH}" -VARIANT=$? -if [ $VARIANT -lt 16 ]; then - abortC "${LANG_UTIL_ERR_VARIANT_SELECTION}" -fi - -if [ $VARIANT == 17 ]; then # YAHFA - echo "1" > /data/adb/lspd/config/variant -elif [ $VARIANT == 18 ]; then # SandHook - echo "2" > /data/adb/lspd/config/variant -else - abortC "${LANG_UTIL_ERR_VARIANT_UNSUPPORT} ${VARIANT}" -fi +echo "1" > /data/adb/lspd/config/variant if [[ ! -e /data/adb/lspd/config/verbose_log ]]; then echo "0" > /data/adb/lspd/config/verbose_log diff --git a/core/template_override/util_functions.sh b/core/template_override/util_functions.sh index accf0d95..eaddb048 100644 --- a/core/template_override/util_functions.sh +++ b/core/template_override/util_functions.sh @@ -54,7 +54,7 @@ require_new_android() { ui_print "${POUNDS}" ui_print "! ${LANG_UTIL_ERR_ANDROID_UNSUPPORT_1} ${1} ${LANG_UTIL_ERR_ANDROID_UNSUPPORT_2}" ui_print "! ${LANG_UTIL_ERR_ANDROID_UNSUPPORT_3}" - [[ ${BOOTMODE} == true ]] && am start -a android.intent.action.VIEW -d https://github.com/ElderDrivers/LSPosed/wiki/Available-Android-versions + [[ ${BOOTMODE} == true ]] && am start -a android.intent.action.VIEW -d https://github.com/LSPosed/LSPosed/wiki/Available-Android-versions abortC "${POUNDS}" } diff --git a/core/template_override/zh_CN.sh b/core/template_override/zh_CN.sh index f815847c..e42c19d2 100644 --- a/core/template_override/zh_CN.sh +++ b/core/template_override/zh_CN.sh @@ -68,8 +68,6 @@ LANG_UTIL_ERR_ANDROID_UNSUPPORT_1="不支持的 Android 版本" LANG_UTIL_ERR_ANDROID_UNSUPPORT_2="(Oreo 以下版本)" LANG_UTIL_ERR_ANDROID_UNSUPPORT_3="从我们的 GitHub Wiki 中了解更多" LANG_UTIL_ERR_PLATFORM_UNSUPPORT="不支持的设备平台" -LANG_UTIL_ERR_VARIANT_SELECTION="选择变种时出现错误" -LANG_UTIL_ERR_VARIANT_UNSUPPORT="不支持的变种" LANG_UTIL_ERR_DUPINST_1="不允许重复安装" LANG_UTIL_ERR_DUPINST_2="删除" LANG_UTIL_ERR_DUPINST_3="并重启以继续安装" diff --git a/key-selector/.gitignore b/key-selector/.gitignore deleted file mode 100644 index 42afabfd..00000000 --- a/key-selector/.gitignore +++ /dev/null @@ -1 +0,0 @@ -/build \ No newline at end of file diff --git a/key-selector/build.gradle b/key-selector/build.gradle deleted file mode 100644 index b0da24e2..00000000 --- a/key-selector/build.gradle +++ /dev/null @@ -1,97 +0,0 @@ -/* - * This file is part of LSPosed. - * - * LSPosed is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * LSPosed is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with LSPosed. If not, see . - * - * Copyright (C) 2020 EdXposed Contributors - * Copyright (C) 2021 LSPosed Contributors - */ - -apply plugin: 'com.android.library' - -android { - compileSdkVersion androidCompileSdkVersion.toInteger() - - defaultConfig { - minSdkVersion androidMinSdkVersion.toInteger() - targetSdkVersion androidTargetSdkVersion.toInteger() - - externalNativeBuild { - cmake { - abiFilters 'arm64-v8a', 'armeabi-v7a', 'x86', 'x86_64' - cppFlags "-std=c++20" - cFlags "-std=gnu99" - } - } - } - - buildTypes { - debug { - externalNativeBuild { - cmake { - cppFlags "-O0" - cFlags "-O0" - } - } - } - release { - externalNativeBuild { - cmake { - cppFlags "-fvisibility=hidden -fvisibility-inlines-hidden -Os -s -Wno-unused-value" - cFlags "-fvisibility=hidden -fvisibility-inlines-hidden -Os -s -Wno-unused-value" - } - } - } - } - externalNativeBuild { - cmake { - path "src/main/cpp/CMakeLists.txt" - } - } -} - -afterEvaluate { - android.libraryVariants.all { variant -> - def variantNameCapped = variant.name.capitalize() - def variantNameLowered = variant.name.toLowerCase() - - task("copyKeySelector${variantNameCapped}LibraryToMagiskTemplate") { - dependsOn tasks.getByName("assemble${variantNameCapped}") - def libPathRelease = "${buildDir}/intermediates/cmake/${variantNameLowered}/obj" - doLast { - copy { - include "key_selector" - from "${libPathRelease}/armeabi-v7a" - into "${zipPathMagiskReleasePath}/system/bin" - } - copy { - include "key_selector" - from "${libPathRelease}/arm64-v8a" - into "${zipPathMagiskReleasePath}/system/bin64" - } - copy { - include "key_selector" - from "${libPathRelease}/x86" - into "${zipPathMagiskReleasePath}/system_x86/bin" - } - copy { - include "key_selector" - from "${libPathRelease}/x86_64" - into "${zipPathMagiskReleasePath}/system_x86/bin64" - } - } - } - - } -} \ No newline at end of file diff --git a/key-selector/src/main/AndroidManifest.xml b/key-selector/src/main/AndroidManifest.xml deleted file mode 100644 index 0ffb6adc..00000000 --- a/key-selector/src/main/AndroidManifest.xml +++ /dev/null @@ -1,25 +0,0 @@ - - - - - - \ No newline at end of file diff --git a/key-selector/src/main/cpp/CMakeLists.txt b/key-selector/src/main/cpp/CMakeLists.txt deleted file mode 100644 index c7f0fe4c..00000000 --- a/key-selector/src/main/cpp/CMakeLists.txt +++ /dev/null @@ -1,25 +0,0 @@ -## -## This file is part of LSPosed. -## -## LSPosed is free software: you can redistribute it and/or modify -## it under the terms of the GNU General Public License as published by -## the Free Software Foundation, either version 3 of the License, or -## (at your option) any later version. -## -## LSPosed is distributed in the hope that it will be useful, -## but WITHOUT ANY WARRANTY; without even the implied warranty of -## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -## GNU General Public License for more details. -## -## You should have received a copy of the GNU General Public License -## along with LSPosed. If not, see . -## -## Copyright (C) 2020 EdXposed Contributors -## Copyright (C) 2021 LSPosed Contributors -## - -cmake_minimum_required(VERSION 3.4.1) - -project(key_selector) - -add_executable(key_selector key_selector.cpp) diff --git a/key-selector/src/main/cpp/Languages.h b/key-selector/src/main/cpp/Languages.h deleted file mode 100644 index 3b320ff7..00000000 --- a/key-selector/src/main/cpp/Languages.h +++ /dev/null @@ -1,72 +0,0 @@ -/* - * This file is part of LSPosed. - * - * LSPosed is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * LSPosed is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with LSPosed. If not, see . - * - * Copyright (C) 2020 EdXposed Contributors - * Copyright (C) 2021 LSPosed Contributors - */ - -// -// Created by 双草酸酯 on 1/26/21. -// - -#ifndef LSPOSED_LANGUAGES_H -#define LSPOSED_LANGUAGES_H -#include - -class Languages { -public: - virtual const std::string desc_line_1() { - return "Select variant. Use Volume Down to move and Volume Up to confirm."; - } - virtual const std::string desc_line_2(const uint16_t seconds) { - const char base[] = "The program will select YAHFA for you in %hu seconds if you don't \nhave a physical volume button. "; - return u16fmt(base, seconds); - } - virtual const std::string timeout(const uint16_t seconds) { - const char base[] = "No operation after %hu seconds."; - return u16fmt(base, seconds); - }; - virtual const std::string deprecated() { - return "(Deprecated)"; - }; -protected: - std::string u16fmt(const char* base, std::uint16_t s){ - std::string out; - out.resize(strlen(base) + 20); - sprintf(out.data(), base, s); - return out; - } -}; - -class LanguageChinese: public Languages { -public: - const std::string desc_line_1() override { - return "请选择变种。使用音量减切换,音量加确定。"; - } - const std::string desc_line_2(const uint16_t seconds) override { - const char base[] = "如果您的设备没有音量键,本程序将会在 %hu 秒后自动选择 YAHFA 。"; - return u16fmt(base, seconds); - } - const std::string timeout(const uint16_t seconds) override { - const char base[] = "在 %hu 秒内没有任何操作。"; - return u16fmt(base, seconds); - } - virtual const std::string deprecated() override { - return "(已废弃)"; - }; -}; - -#endif //LSPOSED_LANGUAGES_H diff --git a/key-selector/src/main/cpp/key_selector.cpp b/key-selector/src/main/cpp/key_selector.cpp deleted file mode 100644 index b28f3ca9..00000000 --- a/key-selector/src/main/cpp/key_selector.cpp +++ /dev/null @@ -1,361 +0,0 @@ -/* - * This file is part of LSPosed. - * - * LSPosed is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * LSPosed is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with LSPosed. If not, see . - * - * Copyright (C) 2010 The Android Open Source Project - * Copyright (C) 2015-2016 The CyanogenMod Project - * Copyright (C) 2021 LSPosed Contributors - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "Languages.h" -#include "key_selector.h" - -// Global variables -static struct pollfd *ufds; -static char **device_names; -static int nfds; - -static int open_device(const char *device) -{ - int version; - int fd; - int clkid = CLOCK_MONOTONIC; - struct pollfd *new_ufds; - char **new_device_names; - char name[80]; - char location[80]; - char idstr[80]; - input_id id{}; - - fd = open(device, O_RDWR); - if (fd < 0) { - return -1; - } - - if (ioctl(fd, EVIOCGVERSION, &version)) { - return -1; - } - - if (ioctl(fd, EVIOCGID, &id)) { - return -1; - } - - name[sizeof(name) - 1] = '\0'; - location[sizeof(location) - 1] = '\0'; - idstr[sizeof(idstr) - 1] = '\0'; - - if (ioctl(fd, EVIOCGNAME(sizeof(name) - 1), &name) < 1) { - name[0] = '\0'; - } - - if (ioctl(fd, EVIOCGPHYS(sizeof(location) - 1), &location) < 1) { - location[0] = '\0'; - } - - if (ioctl(fd, EVIOCGUNIQ(sizeof(idstr) - 1), &idstr) < 1) { - idstr[0] = '\0'; - } - - if (ioctl(fd, EVIOCSCLOCKID, &clkid) != 0) { - // a non-fatal error - } - - new_ufds = static_cast(realloc(ufds, sizeof(ufds[0]) * (nfds + 1))); - if (new_ufds == nullptr) { - return -1; - } - - ufds = new_ufds; - new_device_names = static_cast(realloc(device_names, - sizeof(device_names[0]) * (nfds + 1))); - if (new_device_names == nullptr) { - return -1; - } - - device_names = new_device_names; - - ufds[nfds].fd = fd; - ufds[nfds].events = POLLIN; - device_names[nfds] = strdup(device); - nfds++; - - return 0; -} - -int close_device(const char *device) -{ - int i; - for (i = 1; i < nfds; i++) { - if (strcmp(device_names[i], device) == 0) { - int count = nfds - i - 1; - free(device_names[i]); - memmove(device_names + i, device_names + i + 1, - sizeof(device_names[0]) * count); - memmove(ufds + i, ufds + i + 1, sizeof(ufds[0]) * count); - nfds--; - return 0; - } - } - return -1; -} - -static int read_notify(const char *dirname, int nfd) -{ - int res; - char devname[PATH_MAX]; - char *filename; - char event_buf[512]; - uint32_t event_size; - int event_pos = 0; - struct inotify_event *event; - - res = read(nfd, event_buf, sizeof(event_buf)); - if (res < (int)sizeof(*event)) { - if (errno == EINTR) { - return 0; - } - return 1; - } - - strcpy(devname, dirname); - filename = devname + strlen(devname); - *filename++ = '/'; - - while (res >= (int)sizeof(*event)) { - event = (struct inotify_event *)(event_buf + event_pos); - if (event->len) { - strcpy(filename, event->name); - if (event->mask & IN_CREATE) { - open_device(devname); - } else { - close_device(devname); - } - } - event_size = sizeof(*event) + event->len; - res -= event_size; - event_pos += event_size; - } - return 0; -} - -static int scan_dir(const char *dirname) -{ - namespace fs = std::filesystem; - try { - for (auto &item: fs::directory_iterator(dirname)) { - open_device(item.path().c_str()); - } - } catch (const fs::filesystem_error &e) { - std::cerr << e.what(); - return -1; - } - return 0; -} - - -uint32_t get_event() { - int i; - int res; - input_event event{}; - const char *device_path = "/dev/input"; - unsigned char keys; - - keys = KEYCHECK_CHECK_VOLUMEDOWN | KEYCHECK_CHECK_VOLUMEUP; - nfds = 1; - ufds = static_cast(calloc(1, sizeof(ufds[0]))); - ufds[0].fd = inotify_init(); - ufds[0].events = POLLIN; - - res = inotify_add_watch(ufds[0].fd, device_path, IN_DELETE | IN_CREATE); - if (res < 0) { - std::cerr << "inotify_add_watch failed" << std::endl; - exit(1); - } - - res = scan_dir(device_path); - if (res < 0) { - std::cerr << "scan dev failed" << std::endl; - exit(1); - } - - while (true) { - poll(ufds, nfds, -1); - if (ufds[0].revents & POLLIN) { - read_notify(device_path, ufds[0].fd); - } - - for (i = 1; i < nfds; i++) { - if ((ufds[i].revents) && (ufds[i].revents & POLLIN)) { - res = read(ufds[i].fd, &event, sizeof(event)); - if (res < (int)sizeof(event)) { - return 1; - } - - // keypress only - if (event.value == 1) { - if (event.code == KEY_VOLUMEDOWN && - (keys & KEYCHECK_CHECK_VOLUMEDOWN) != 0) { - return KEYCHECK_PRESSED_VOLUMEDOWN; - } - else if (event.code == KEY_VOLUMEUP && - (keys & KEYCHECK_CHECK_VOLUMEUP) != 0) { - return KEYCHECK_PRESSED_VOLUMEUP; - } - } - } - } - } -} - -// for phone which has no button -uint16_t timeout = 10; -std::unique_ptr l = nullptr; - -int main() { - if (getuid() != 0) { - std::cerr << "Root required" << std::endl; - exit(1); - } - - // languages - char locale[256]; - __system_property_get("persist.sys.locale", locale); - if (locale[0] == 'z' && locale[1] == 'h') { - l = std::make_unique(); - } else { - l = std::make_unique(); - } - - // get current arch -#if defined(__arm__) - const Arch arch = ARM; -#elif defined(__aarch64__) - const Arch arch = ARM64; -#elif defined(__i386__) - const Arch arch = x86; -#elif defined(__x86_64__) - const Arch arch = x86_64; -#else -#error "Unsupported arch" -#endif - - std::unordered_map variants; - std::string sandhook_deprecated = "SandHook " + l->deprecated(); - for (const auto i: AllVariants) { - switch (i) { - case Variant::YAHFA: - variants[i] = { - .expression = "YAHFA", - .supported_arch = {ARM, ARM64, x86, x86_64} - }; - break; - case Variant::SandHook: - variants[i] = { - .expression = sandhook_deprecated.c_str(), - .supported_arch = {ARM, ARM64} - }; - break; - } - } - - Variant cursor = Variant::YAHFA; - - // Load current variant - std::filesystem::path lspd_folder("/data/adb/lspd/config"); - std::filesystem::create_directories(lspd_folder); - - const auto variant_file = lspd_folder / "variant"; - if (std::filesystem::exists(variant_file)) { - std::ifstream ifs(variant_file); - if (ifs.good()) { - std::string line; - std::getline(ifs, line); - char* end; - int i = std::strtol(line.c_str(), &end, 10); - switch (i) { - default: - case 1: - cursor = Variant::YAHFA; - break; - case 2: - cursor = Variant::SandHook; - break; - } - timeout = 5; - } - } - - alarm(timeout); - signal(SIGALRM, [](int){ - std::cout << l->timeout(timeout) << std::endl; - exit(static_cast(Variant::YAHFA)); - }); - - auto print_status = [&cursor, variants, arch](){ - //std::cout << "\33[2K\r"; // clear this line - std::stringstream ss; - for (const auto &i: variants) { - if (!i.second.supported_arch.contains(arch)) { - continue; - } - ss << "["; - ss << (cursor == i.first ? "√" : " "); - ss << "] "; - ss << i.second.expression; - ss << " "; - } - std::cout << ss.str() << std::endl; - }; - - std::cout << l->desc_line_1() << std::endl; - std::cout << l->desc_line_2(timeout) << std::endl; - print_status(); - while (int event = get_event()) { - bool leave = false; - //std::cout << event << " " << cursor << std::endl; - switch (event) { - case KEYCHECK_PRESSED_VOLUMEUP: - leave = true; - break; - case KEYCHECK_PRESSED_VOLUMEDOWN: - cursor++; - break; - default: - std::cout << "ERROR\n"; - } - if (leave) { - break; - } - print_status(); - } - - // std::cout << std::endl << cursor << std::endl; - return static_cast(cursor); -} \ No newline at end of file diff --git a/key-selector/src/main/cpp/key_selector.h b/key-selector/src/main/cpp/key_selector.h deleted file mode 100644 index db9a904e..00000000 --- a/key-selector/src/main/cpp/key_selector.h +++ /dev/null @@ -1,65 +0,0 @@ -/* - * This file is part of LSPosed. - * - * LSPosed is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * LSPosed is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with LSPosed. If not, see . - * - * Copyright (C) 2020 EdXposed Contributors - * Copyright (C) 2021 LSPosed Contributors - */ - -#ifndef __KEYCHECK_H__ -#define __KEYCHECK_H__ -#include -#include - -// Constants: pressed keys -#define KEYCHECK_CHECK_VOLUMEDOWN 0x01u -#define KEYCHECK_CHECK_VOLUMEUP 0x02u -#define KEYCHECK_PRESSED_VOLUMEDOWN 41u -#define KEYCHECK_PRESSED_VOLUMEUP 42u - -enum class Variant { - YAHFA = 0x11, - SandHook = 0x12, - End = SandHook, -}; -const auto AllVariants = { Variant::YAHFA, Variant::SandHook }; - -Variant& operator++( Variant &c ) { - using IntType = typename std::underlying_type::type; - c = static_cast( static_cast(c) + 1 ); - if ( c > Variant::End ) - c = Variant::YAHFA; - return c; -} - -Variant operator++( Variant &c, int ) { - Variant result = c; - ++c; - return result; -} - -enum Arch { - ARM, - ARM64, - x86, - x86_64 -}; - -struct VariantDetail { - const char* expression; - std::unordered_set supported_arch; -}; - -#endif // __KEYCHECK_H__ \ No newline at end of file diff --git a/settings.gradle b/settings.gradle index 9b4b0b2f..88c4e282 100644 --- a/settings.gradle +++ b/settings.gradle @@ -1,5 +1,5 @@ rootProject.name = "LSPosed" -include ':core', ':hiddenapi-stubs', ':sandhook-hooklib', ':sandhook-annotation', ':app', ':key-selector', ':service', ':interface', ':hiddenapi-bridge', ':manager-service' +include ':core', ':hiddenapi-stubs', ':sandhook-hooklib', ':sandhook-annotation', ':app', ':service', ':interface', ':hiddenapi-bridge', ':manager-service' def service_root = "service" project(':interface').projectDir = file("$service_root${File.separator}interface")