Compare commits

..

11 Commits

Author SHA1 Message Date
Wang Han
121f9a8e90 Update su.rs 2025-05-17 16:28:11 +08:00
Wang Han
36446948ba Update Cargo.toml 2025-05-17 16:26:06 +08:00
Wang Han
8cf7b7ad20 Update Cargo.toml 2025-05-17 16:21:26 +08:00
Wang Han
05f032d13d Update Cargo.lock 2025-05-17 16:10:44 +08:00
Wang Han
8c12707e1e Update Cargo.toml 2025-05-17 14:36:44 +08:00
Wang Han
af8e984898 Update Cargo.toml 2025-05-17 14:35:49 +08:00
Wang Han
29565b7af1 Update Cargo.lock 2025-05-17 14:33:12 +08:00
Wang Han
50770b287d Update Cargo.lock 2025-05-17 14:21:06 +08:00
Wang Han
5efc1ee549 Update build.rs 2025-05-17 14:14:03 +08:00
Wang Han
de164dd18e Update build.rs 2025-05-17 14:12:13 +08:00
Wang Han
dd9bc4d995 Update Cargo.lock 2025-05-17 14:09:53 +08:00
50 changed files with 279 additions and 539 deletions

1
.github/FUNDING.yml vendored
View File

@@ -2,3 +2,4 @@
github: tiann
patreon: weishu
custom: https://vxposed.com/donate.html

View File

@@ -27,10 +27,6 @@ jobs:
os_patch_level: 2024-08
- sub_level: 226
os_patch_level: 2024-11
- sub_level: 233
os_patch_level: 2025-02
- sub_level: 236
os_patch_level: 2025-05
uses: ./.github/workflows/gki-kernel.yml
secrets: inherit
with:

View File

@@ -36,12 +36,6 @@ jobs:
- version: "5.10"
sub_level: 223
os_patch_level: 2024-11
- version: "5.10"
sub_level: 228
os_patch_level: 2025-01
- version: "5.10"
sub_level: 234
os_patch_level: 2025-03
- version: "5.15"
sub_level: 148
os_patch_level: 2024-05
@@ -57,15 +51,6 @@ jobs:
- version: "5.15"
sub_level: 167
os_patch_level: 2024-11
- version: "5.15"
sub_level: 178
os_patch_level: 2024-11
- version: "5.15"
sub_level: 170
os_patch_level: 2025-01
- version: "5.15"
sub_level: 178
os_patch_level: 2025-03
uses: ./.github/workflows/gki-kernel.yml
secrets: inherit
with:

View File

@@ -39,12 +39,6 @@ jobs:
- version: "5.15"
sub_level: 167
os_patch_level: 2024-11
- version: "5.15"
sub_level: 170
os_patch_level: 2025-01
- version: "5.15"
sub_level: 178
os_patch_level: 2025-03
- version: "6.1"
sub_level: 75
os_patch_level: 2024-05
@@ -69,15 +63,6 @@ jobs:
- version: "6.1"
sub_level: 115
os_patch_level: 2024-12
- version: "6.1"
sub_level: 118
os_patch_level: 2025-01
- version: "6.1"
sub_level: 128
os_patch_level: 2025-03
- version: "6.1"
sub_level: 134
os_patch_level: 2025-05
uses: ./.github/workflows/gki-kernel.yml
secrets: inherit
with:

View File

@@ -36,21 +36,6 @@ jobs:
- version: "6.6"
sub_level: 57
os_patch_level: 2024-12
- version: "6.6"
sub_level: 58
os_patch_level: 2025-01
- version: "6.6"
sub_level: 66
os_patch_level: 2025-02
- version: "6.6"
sub_level: 77
os_patch_level: 2025-03
- version: "6.6"
sub_level: 82
os_patch_level: 2025-04
- version: "6.6"
sub_level: 87
os_patch_level: 2025-05
uses: ./.github/workflows/gki-kernel.yml
secrets: inherit
with:

View File

@@ -15,8 +15,8 @@ jobs:
matrix:
include:
- version: "android12-5.10"
sub_level: 236
os_patch_level: 2025-05
sub_level: 233
os_patch_level: 2025-02
- version: "android13-5.10"
sub_level: 234
os_patch_level: 2025-03
@@ -27,11 +27,11 @@ jobs:
sub_level: 178
os_patch_level: 2025-03
- version: "android14-6.1"
sub_level: 134
os_patch_level: 2025-05
sub_level: 128
os_patch_level: 2025-03
- version: "android15-6.6"
sub_level: 87
os_patch_level: 2025-05
sub_level: 77
os_patch_level: 2025-03
uses: ./.github/workflows/gki-kernel.yml
with:
version: ${{ matrix.version }}

View File

@@ -108,7 +108,6 @@ static void setup_groups(struct root_profile *profile, struct cred *cred)
groups_sort(group_info);
set_groups(cred, group_info);
put_group_info(group_info);
}
static void disable_seccomp()
@@ -133,18 +132,18 @@ void escape_to_root(void)
{
struct cred *cred;
cred = prepare_creds();
if (!cred) {
pr_warn("prepare_creds failed!\n");
return;
}
rcu_read_lock();
do {
cred = (struct cred *)__task_cred((current));
BUG_ON(!cred);
} while (!get_cred_rcu(cred));
if (cred->euid.val == 0) {
pr_warn("Already root, don't escape!\n");
abort_creds(cred);
rcu_read_unlock();
return;
}
struct root_profile *profile = ksu_get_root_profile(cred->uid.val);
cred->uid.val = profile->uid;
@@ -175,7 +174,7 @@ void escape_to_root(void)
setup_groups(profile, cred);
commit_creds(cred);
rcu_read_unlock();
// Refer to kernel/seccomp.c: seccomp_set_mode_strict
// When disabling Seccomp, ensure that current->sighand->siglock is held during the operation.
@@ -242,7 +241,7 @@ static void nuke_ext4_sysfs() {
}
ext4_unregister_sysfs(sb);
path_put(&path);
path_put(&path);
}
int ksu_handle_prctl(int option, unsigned long arg2, unsigned long arg3,
@@ -413,17 +412,6 @@ int ksu_handle_prctl(int option, unsigned long arg2, unsigned long arg3,
return 0;
}
if (arg2 == CMD_GET_MANAGER_UID) {
uid_t manager_uid = ksu_get_manager_uid();
if (copy_to_user(arg3, &manager_uid, sizeof(manager_uid))) {
pr_err("get manager uid failed\n");
}
if (copy_to_user(result, &reply_ok, sizeof(reply_ok))) {
pr_err("prctl reply error, cmd: %lu\n", arg2);
}
return 0;
}
// all other cmds are for 'root manager'
if (!from_manager) {
return 0;
@@ -552,13 +540,11 @@ static void try_umount(const char *mnt, bool check_mnt, int flags)
if (path.dentry != path.mnt->mnt_root) {
// it is not root mountpoint, maybe umounted by others already.
path_put(&path);
return;
}
// we are only interest in some specific mounts
if (check_mnt && !should_umount(&path)) {
path_put(&path);
return;
}

View File

@@ -23,7 +23,6 @@
#define CMD_UID_SHOULD_UMOUNT 13
#define CMD_IS_SU_ENABLED 14
#define CMD_ENABLE_SU 15
#define CMD_GET_MANAGER_UID 16
#define EVENT_POST_FS_DATA 1
#define EVENT_BOOT_COMPLETED 2

View File

@@ -24,19 +24,14 @@ static struct policydb *get_policydb(void)
return db;
}
static DEFINE_MUTEX(ksu_rules);
void apply_kernelsu_rules()
{
struct policydb *db;
if (!getenforce()) {
pr_info("SELinux permissive or disabled, apply rules!\n");
}
mutex_lock(&ksu_rules);
db = get_policydb();
rcu_read_lock();
struct policydb *db = get_policydb();
ksu_permissive(db, KERNEL_SU_DOMAIN);
ksu_typeattribute(db, KERNEL_SU_DOMAIN, "mlstrustedsubject");
@@ -123,11 +118,11 @@ void apply_kernelsu_rules()
// Allow all binder transactions
ksu_allow(db, ALL, KERNEL_SU_DOMAIN, "binder", ALL);
// Allow system server kill su process
ksu_allow(db, "system_server", KERNEL_SU_DOMAIN, "process", "getpgid");
ksu_allow(db, "system_server", KERNEL_SU_DOMAIN, "process", "sigkill");
// Allow system server kill su process
ksu_allow(db, "system_server", KERNEL_SU_DOMAIN, "process", "getpgid");
ksu_allow(db, "system_server", KERNEL_SU_DOMAIN, "process", "sigkill");
mutex_unlock(&ksu_rules);
rcu_read_unlock();
}
#define MAX_SEPOL_LEN 128

View File

@@ -213,8 +213,7 @@ void search_manager(const char *path, int depth, struct list_head *uid_data)
int i, stop = 0;
struct list_head data_path_list;
INIT_LIST_HEAD(&data_path_list);
unsigned long data_app_magic = 0;
// Initialize APK cache list
struct apk_path_hash *pos, *n;
list_for_each_entry(pos, &apk_path_hash_list, list) {
@@ -245,24 +244,6 @@ void search_manager(const char *path, int depth, struct list_head *uid_data)
pr_err("Failed to open directory: %s, err: %ld\n", pos->dirpath, PTR_ERR(file));
goto skip_iterate;
}
// grab magic on first folder, which is /data/app
if (!data_app_magic) {
if (file->f_inode->i_sb->s_magic) {
data_app_magic = file->f_inode->i_sb->s_magic;
pr_info("%s: dir: %s got magic! 0x%lx\n", __func__, pos->dirpath, data_app_magic);
} else {
filp_close(file, NULL);
goto skip_iterate;
}
}
if (file->f_inode->i_sb->s_magic != data_app_magic) {
pr_info("%s: skip: %s magic: 0x%lx expected: 0x%lx\n", __func__, pos->dirpath,
file->f_inode->i_sb->s_magic, data_app_magic);
filp_close(file, NULL);
goto skip_iterate;
}
iterate_dir(file, &ctx.ctx);
filp_close(file, NULL);

View File

@@ -92,10 +92,6 @@ android {
}
}
ksp {
arg("compose-destinations.defaultTransitions", "none")
}
dependencies {
implementation(libs.androidx.activity.compose)
implementation(libs.androidx.navigation.compose)

View File

@@ -50,13 +50,12 @@ bool become_manager(const char* pkg) {
}
// cache the result to avoid unnecessary syscall
static bool is_lkm = false;
int get_version(void) {
static bool is_lkm;
int get_version() {
int32_t version = -1;
int32_t flags = 0;
ksuctl(CMD_GET_VERSION, &version, &flags);
if (!is_lkm && (flags & 0x1)) {
int32_t lkm = 0;
ksuctl(CMD_GET_VERSION, &version, &lkm);
if (!is_lkm && lkm != 0) {
is_lkm = true;
}
return version;
@@ -97,4 +96,4 @@ bool is_su_enabled() {
// if ksuctl failed, we assume su is enabled, and it cannot be disabled.
ksuctl(CMD_IS_SU_ENABLED, &enabled, nullptr);
return enabled;
}
}

View File

@@ -11,9 +11,6 @@ import androidx.compose.animation.ExitTransition
import androidx.compose.animation.core.tween
import androidx.compose.animation.fadeIn
import androidx.compose.animation.fadeOut
import androidx.compose.animation.scaleOut
import androidx.compose.animation.slideInHorizontally
import androidx.compose.animation.slideOutHorizontally
import androidx.compose.foundation.layout.WindowInsets
import androidx.compose.foundation.layout.WindowInsetsSides
import androidx.compose.foundation.layout.displayCutout
@@ -62,16 +59,13 @@ class MainActivity : ComponentActivity() {
super.onCreate(savedInstanceState)
val isManager = Natives.becomeManager(ksuApp.packageName)
if (isManager) install()
val isManager = Natives.becomeManager(ksuApp.packageName)
if (isManager) install()
setContent {
KernelSUTheme {
val navController = rememberNavController()
val snackBarHostState = remember { SnackbarHostState() }
val bottomBarRoutes = remember {
BottomBarDestination.entries.map { it.direction.route }.toSet()
}
Scaffold(
bottomBar = { BottomBar(navController) },
contentWindowInsets = WindowInsets(0, 0, 0, 0)
@@ -84,45 +78,10 @@ class MainActivity : ComponentActivity() {
navGraph = NavGraphs.root,
navController = navController,
defaultTransitions = object : NavHostAnimatedDestinationStyle() {
override val enterTransition: AnimatedContentTransitionScope<NavBackStackEntry>.() -> EnterTransition = {
// If the target is a detail page (not a bottom navigation page), slide in from the right
if (targetState.destination.route !in bottomBarRoutes) {
slideInHorizontally(initialOffsetX = { it })
} else {
// Otherwise (switching between bottom navigation pages), use fade in
fadeIn(animationSpec = tween(340))
}
}
override val exitTransition: AnimatedContentTransitionScope<NavBackStackEntry>.() -> ExitTransition = {
// If navigating from the home page (bottom navigation page) to a detail page, slide out to the left
if (initialState.destination.route in bottomBarRoutes && targetState.destination.route !in bottomBarRoutes) {
slideOutHorizontally(targetOffsetX = { -it / 4 }) + fadeOut()
} else {
// Otherwise (switching between bottom navigation pages), use fade out
fadeOut(animationSpec = tween(340))
}
}
override val popEnterTransition: AnimatedContentTransitionScope<NavBackStackEntry>.() -> EnterTransition = {
// If returning to the home page (bottom navigation page), slide in from the left
if (targetState.destination.route in bottomBarRoutes) {
slideInHorizontally(initialOffsetX = { -it / 4 }) + fadeIn()
} else {
// Otherwise (e.g., returning between multiple detail pages), use default fade in
fadeIn(animationSpec = tween(340))
}
}
override val popExitTransition: AnimatedContentTransitionScope<NavBackStackEntry>.() -> ExitTransition = {
// If returning from a detail page (not a bottom navigation page), scale down and fade out
if (initialState.destination.route !in bottomBarRoutes) {
scaleOut(targetScale = 0.9f) + fadeOut()
} else {
// Otherwise, use default fade out
fadeOut(animationSpec = tween(340))
}
}
override val enterTransition: AnimatedContentTransitionScope<NavBackStackEntry>.() -> EnterTransition
get() = { fadeIn(animationSpec = tween(340)) }
override val exitTransition: AnimatedContentTransitionScope<NavBackStackEntry>.() -> ExitTransition
get() = { fadeOut(animationSpec = tween(340)) }
}
)
}

View File

@@ -81,9 +81,9 @@ fun createRootShell(globalMnt: Boolean = false): Shell {
Log.w(TAG, "ksu failed: ", e)
try {
if (globalMnt) {
builder.build("su", "-mm")
} else {
builder.build("su")
} else {
builder.build("su", "-mm")
}
} catch (e: Throwable) {
Log.e(TAG, "su failed: ", e)

View File

@@ -129,10 +129,6 @@ class ModuleViewModel : ViewModel() {
}
}
private fun sanitizeVersionString(version: String): String {
return version.replace(Regex("[^a-zA-Z0-9.\\-_]"), "_")
}
fun checkUpdate(m: ModuleInfo): Triple<String, String, String> {
val empty = Triple("", "", "")
if (m.updateJson.isEmpty() || m.remove || m.update || !m.enabled) {
@@ -162,8 +158,7 @@ class ModuleViewModel : ViewModel() {
JSONObject(result)
}.getOrNull() ?: return empty
var version = updateJson.optString("version", "")
version = sanitizeVersionString(version)
val version = updateJson.optString("version", "")
val versionCode = updateJson.optInt("versionCode", 0)
val zipUrl = updateJson.optString("zipUrl", "")
val changelog = updateJson.optString("changelog", "")
@@ -173,4 +168,4 @@ class ModuleViewModel : ViewModel() {
return Triple(zipUrl, version, changelog)
}
}
}

View File

@@ -50,7 +50,7 @@
<string name="home_learn_kernelsu_url">https://kernelsu.org/guide/what-is-kernelsu.html</string>
<string name="home_click_to_learn_kernelsu">تعرف على كيفية تثبيت KernelSU واستخدام الإضافات</string>
<string name="home_support_title">إدعمنا</string>
<string name="home_support_content">KernelSU سيظل دائماً مجانياً ومفتوح المصدر. مع ذلك، يمكنك متى ما استطعت أن تظهر لنا أنك تهتم بالتبرع.</string>
<string name="home_support_content">KernelSU سيظل دائماً مجانياً ومفتوح المصدر. مع ذلك، يمكنك أن تظهر لنا أنك تهتم بالتبرع.</string>
<string name="about_source_code"><![CDATA[أنظر إلى مصدر البرمجة في %1$s<br/>إنضم إلى قناتنا في %2$s ]]></string>
<string name="profile_capabilities">القدرات</string>
<string name="module_update">تحديث</string>

View File

@@ -84,19 +84,4 @@
<string name="confirm">Təsdiq edin</string>
<string name="module_sort_action_first">Sıralama (ilk hərəkət)</string>
<string name="module_sort_enabled_first">Sıralama (Əvvəlcə aktivdir)</string>
<string name="module_changelog">Dəyişikliklər jurnalı</string>
<string name="settings_profile_template">Tətbiq Profil Şablonu</string>
<string name="settings_profile_template_summary">Tətbiq Profilinə aid yerli və onlayn şablonların idarə olunması</string>
<string name="app_profile_template_create">Şablon yarat</string>
<string name="app_profile_template_edit">Şablonu redaktə et</string>
<string name="app_profile_template_id">ID</string>
<string name="app_profile_template_id_invalid">Etibarsız şablon ID-si</string>
<string name="app_profile_template_name">Ad</string>
<string name="app_profile_template_description">ıqlama</string>
<string name="su_not_allowed">%s üçün Superistifadəçi girişi vermək mümkün olmadı.</string>
<string name="app_profile_template_save">Yadda saxla</string>
<string name="app_profile_template_delete">Sil</string>
<string name="app_profile_template_view">Şablonu göstər</string>
<string name="app_profile_template_readonly">Yalnız oxu</string>
<string name="app_profile_template_id_exist">Şablon ID-si artıq mövcuddur!</string>
</resources>

View File

@@ -42,7 +42,7 @@
<string name="hide_system_apps">Sakrijte sistemske aplikacije</string>
<string name="safe_mode">Sigurnosni mod</string>
<string name="reboot_to_apply">Ponovo pokrenite da bi proradilo</string>
<string name="module_magisk_conflict">"Moduli su nedostupni jer su u sukobu sa Magisk-om!"</string>
<string name="module_magisk_conflict">Module su isključene jer je u sukobu sa Magisk-om!</string>
<string name="home_learn_kernelsu_url">https://kernelsu.org/guide/what-is-kernelsu.html</string>
<string name="home_click_to_learn_kernelsu">Naučite kako da instalirate KernelSU i da koristite module</string>
<string name="home_support_title">Podržite Nas</string>
@@ -54,7 +54,7 @@
<string name="failed_to_update_sepolicy">Neuspješno ažuriranje SELinux pravila za: %s</string>
<string name="home_working">Radi</string>
<string name="home_working_version">Verzija: %d</string>
<string name="home_kernel">Kernel verzija</string>
<string name="home_kernel">Kernel</string>
<string name="selinux_status_permissive">Permisivno</string>
<string name="uninstall">Deinstalirajte</string>
<string name="selinux_status_unknown">Nepoznato</string>
@@ -73,14 +73,11 @@
<string name="selinux_status_disabled">Isključeno</string>
<string name="about">O</string>
<string name="module_uninstall_confirm">Jeste li sigurni da želite deinstalirati modulu %s\?</string>
<string name="module_overlay_fs_not_available">overlayFS je onemogućen od strane kernela, modul nije dostupan.</string>
<string name="module_overlay_fs_not_available">overlayfs nije dostupan, modula ne može raditi!</string>
<string name="home_support_content">KernelSU je, i uvijek če biti, besplatan, i otvorenog izvora. Možete nam međutim pokazati da vas je briga s time da napravite donaciju.</string>
<string name="profile_default">Zadano</string>
<string name="profile_template">Šablon</string>
<string name="profile_custom">Prilagođeno</string>
<string name="profile_name">Naziv profila</string>
<string name="save_log">Sačuvaj Dnevnike</string>
<string name="module_install_prompt_with_name">Modul će biti instaliran</string>
<string name="module_sort_action_first">Sortiraj</string>
<string name="confirm">Potvrdi</string>
</resources>

View File

@@ -3,9 +3,9 @@
<string name="home_working">Arbejder</string>
<string name="home_module_count">Moduler: %d</string>
<string name="home_unsupported">Ikke understøttet</string>
<string name="home_kernel">Kernel-version</string>
<string name="home_kernel">Kernel</string>
<string name="home_unsupported_reason">KernelSU understøtter kun GKI kernels</string>
<string name="home_manager_version">Manager version</string>
<string name="home_manager_version">Manager Version</string>
<string name="home_selinux_status">SELinux-status</string>
<string name="selinux_status_disabled">Deaktiveret</string>
<string name="selinux_status_permissive">Tilladende</string>
@@ -18,22 +18,22 @@
<string name="install">Installer</string>
<string name="reboot">Genstart</string>
<string name="settings">Indstillinger</string>
<string name="reboot_userspace">Blød renstart</string>
<string name="reboot_userspace">Blød Genstart</string>
<string name="reboot_download">Genstart til Download</string>
<string name="reboot_edl">Genstart til EDL</string>
<string name="about">Om</string>
<string name="module_uninstall_confirm">Er du sikker på, at du vil afinstallere modulet %s\?</string>
<string name="module_uninstall_success">%s afinstalleret</string>
<string name="module_uninstall_failed">Afinstallation af: %s fejlede</string>
<string name="module_overlay_fs_not_available">Moduler utilgængelige - OverlayFS deaktiveret i kern\'en!</string>
<string name="module_overlay_fs_not_available">overlayfs er ikke tilgængeligt, modulet kan ikke fungere!</string>
<string name="refresh">Opdater</string>
<string name="send_log">Send logs</string>
<string name="send_log">Send Log</string>
<string name="safe_mode">Sikker tilstand</string>
<string name="reboot_to_apply">Genstart for at tage effekt</string>
<string name="home_learn_kernelsu">Lær KernelSU</string>
<string name="home_learn_kernelsu_url">https://kernelsu.org/guide/what-is-kernelsu.html</string>
<string name="home_click_to_learn_kernelsu">Lær hvordan man installerer KernelSU og moduler</string>
<string name="about_source_code"><![CDATA[View source code at %1$s<br/>Join our %2$s channel]]></string>
<string name="about_source_code">Se source koden ved %1$s<br/>Deltage i vores %2$s kanal</string>
<string name="profile_default">Standard</string>
<string name="profile_template">Skabelon</string>
<string name="profile_namespace">Monter navnerum</string>
@@ -44,17 +44,17 @@
<string name="profile_selinux_context">SELinux-kontext</string>
<string name="profile_umount_modules">Afmonteret moduler</string>
<string name="settings_umount_modules_default">Afmontere moduler som standard</string>
<string name="profile_umount_modules_summary">Aktivering af denne indstilling gør det muligt for KernelSU at gendanne alle modificerede filer af dets modul på app-niveau.</string>
<string name="profile_umount_modules_summary">Aktivering af denne indstilling vil tillade KernelSU at gendanne hvilken som helst modificeret filer af modulet for denne applikation.</string>
<string name="module_update">Opdatering</string>
<string name="module_downloading">Downloader modulet: %s</string>
<string name="new_version_available">Ny version %s er tilgængelig, klik for at opgradere.</string>
<string name="new_version_available">Ny version: %s er tilgængelig, kilk for at downloade</string>
<string name="launch_app">Start</string>
<string name="force_stop_app">Tving stop</string>
<string name="failed_to_update_sepolicy">Opdatering af SELinux-regler mislykkedes for %s</string>
<string name="force_stop_app">Tving Stop</string>
<string name="failed_to_update_sepolicy">Opdatering af SELinux-regler for: %s fejlede</string>
<string name="module_start_downloading">Start download: %s</string>
<string name="home_click_to_install">Klik for at installere</string>
<string name="home_working_version">Version: %d</string>
<string name="home">Home</string>
<string name="home">Hjem</string>
<string name="home_not_installed">Ikke installeret</string>
<string name="home_superuser_count">Superbrugere: %d</string>
<string name="home_fingerprint">Fingeraftryk</string>
@@ -67,9 +67,9 @@
<string name="module_version">Version</string>
<string name="hide_system_apps">Gem system-apps</string>
<string name="show_system_apps">Vis system-apps</string>
<string name="module_magisk_conflict">Moduler er utilgængelige på grund af en konflikt med Magisk!</string>
<string name="module_magisk_conflict">Moduler er deaktiveret, fordi der er konflikt med Magiskes!</string>
<string name="home_support_title">Støt Os</string>
<string name="home_support_content">KernelSU er og vil altid være gratis og åben kildekode. Du kan dog vise din støtte ved at donere.</string>
<string name="home_support_content">KernelSU er, og vil altid være gratis og open source. Du kan stadig vise os din støtte ved at donere.</string>
<string name="profile_custom">Brugerdefineret</string>
<string name="profile_name">Profilnavn</string>
<string name="profile_namespace_individual">Individuel</string>
@@ -78,64 +78,6 @@
<string name="profile_selinux_domain">Domæne</string>
<string name="profile_selinux_rules">Regler</string>
<string name="restart_app">Genstart</string>
<string name="require_kernel_version">Den nuværende KernelSU-version %d er for lav til, at manageren fungerer korrekt. Opgrader venligst til version %d eller højere!</string>
<string name="save_log">Gem logs</string>
<string name="module_install_prompt_with_name">Følgende moduler installeres: %1$s</string>
<string name="module_sort_action_first">Sorter (Handling først)</string>
<string name="module_sort_enabled_first">Sorter (Aktiveret først)</string>
<string name="confirm">Bekræft</string>
<string name="su_not_allowed">Kunne ikke tildele superbruger-adgang til %s</string>
<string name="module_changelog">opdateringslog</string>
<string name="settings_profile_template">app-profilskabelon</string>
<string name="settings_profile_template_summary">Administrer lokale og online skabeloner til App-profil</string>
<string name="app_profile_template_create">Opret skabelon</string>
<string name="app_profile_template_edit">Rediger skabelon</string>
<string name="app_profile_template_id">ID</string>
<string name="app_profile_template_id_invalid">ugyldigt skabelon-id</string>
<string name="app_profile_template_name">Navn</string>
<string name="app_profile_template_description">beskrivelse</string>
<string name="app_profile_template_save">Gem</string>
<string name="app_profile_template_delete">Slet</string>
<string name="app_profile_template_view">visningsskabelon</string>
<string name="app_profile_template_readonly">Skrivebeskyttet</string>
<string name="app_profile_template_id_exist">Skabelon-ID findes allerede!</string>
<string name="app_profile_import_export">Import/Eksport</string>
<string name="app_profile_import_from_clipboard">Importér fra udklipsholder</string>
<string name="app_profile_export_to_clipboard">Eksporter til udklipsholder</string>
<string name="app_profile_template_export_empty">Kan ikke finde lokal skabelon til eksport!</string>
<string name="app_profile_template_import_success">Importér med succes</string>
<string name="app_profile_template_sync">Synkroniser online skabeloner</string>
<string name="app_profile_template_save_failed">Kunne ikke gemme skabelon</string>
<string name="app_profile_template_import_empty">Udklipsholderen er tom!</string>
<string name="module_changelog_failed">Hent changelog mislykkedes: %s</string>
<string name="settings_check_update">Check for opdateringer</string>
<string name="settings_check_update_summary">Automatisk tjek for opdateringer, når du åbner appen</string>
<string name="grant_root_failed">Kunne ikke tildelle root!</string>
<string name="action">Handling</string>
<string name="open">Åbn</string>
<string name="enable_web_debugging">Aktiver WebView-fejlsøgning</string>
<string name="enable_web_debugging_summary">Kan bruges til fejlfinde af WebUI. Aktiver kun når det er nødvendigt.</string>
<string name="direct_install">Direkte installation (Anbefalet)</string>
<string name="select_file">Vælg en fil</string>
<string name="install_inactive_slot">Installer på inaktiv slot (efter OTA-opdatering)</string>
<string name="install_inactive_slot_warning">Din enhed vil blive TVINGET til at starte fra det nuværende inaktive slot efter en genstart!\nBrug kun denne mulighed efter OTA-opdatering er fuldført.\nFortsæt?</string>
<string name="install_next">Næste</string>
<string name="select_file_tip">%1$s partitionsimage anbefales</string>
<string name="select_kmi">Vælg KMI</string>
<string name="shrink_sparse_image">Minimér sparse image</string>
<string name="shrink_sparse_image_message">Tilpas den sparse image, hvor modulet er placeret, til dens faktiske størrelse. Bemærk, at dette kan forårsage unormal funktion af modulet, så brug kun når nødvendigt (f.eks. til backup).</string>
<string name="settings_uninstall">Afinstaller</string>
<string name="settings_uninstall_temporary">Afinstaller midlertidigt</string>
<string name="settings_uninstall_permanent">Afinstaller midlertidigt</string>
<string name="settings_restore_stock_image">Gendan systemets standardbillede</string>
<string name="settings_uninstall_temporary_message">Afinstaller KernelSU midlertidigt; gendan til original tilstand efter næste genstart.</string>
<string name="settings_uninstall_permanent_message">Afinstaller KernelSU fuldstændigt og permanent (root-adgang og alle moduler).</string>
<string name="settings_restore_stock_image_message">Gendan systemets standardfabriksbillede (hvis en backup eksisterer), typisk anvendt før OTA-opdatering; hvis du skal afinstallere KernelSU, brug \'Afinstaller permanent\'.</string>
<string name="flashing">Flashing</string>
<string name="flash_success">Flash-succes</string>
<string name="flash_failed">Flash mislykkedes</string>
<string name="selected_lkm">Valgt LKM: %s</string>
<string name="log_saved">Logs gemt</string>
<string name="settings_disable_su">Deaktiver su-kompatibilitet</string>
<string name="settings_disable_su_summary">Deaktiver midlertidigt enhver apps mulighed for at opnå root-privilegier via su-kommandoen (Eksisterende root-processer påvirkes ikke).</string>
<string name="require_kernel_version">Den nuværende KernelSU version %d er for lav til manageren for at fungere ordentligt. Opgrader til version %d eller højere!</string>
<string name="save_log">Gem Logfiler</string>
</resources>

View File

@@ -133,6 +133,4 @@
<string name="shrink_sparse_image">Spärliches Bild minimieren</string>
<string name="action">Aktion</string>
<string name="log_saved">Protokolle gespeichert</string>
<string name="module_install_prompt_with_name">Folgende Module werden installiert: %1$s</string>
<string name="confirm">Bestätigen</string>
</resources>

View File

@@ -67,4 +67,4 @@
<string name="profile_namespace_inherited">Minana</string>
<string name="settings_umount_modules_default_summary">Ang pangkalahatang default na halaga para sa \"Umount modules\" sa Mga Profile ng App. Kung pinagana, aalisin nito ang lahat ng mga pagbabago sa modyul sa system para sa mga aplikasyon na walang hanay ng Profile.</string>
<string name="save_log">I-save ang mga Log</string>
</resources>
</resources>

View File

@@ -6,7 +6,7 @@
<string name="home_superuser_count">Super-utilisateurs : %d</string>
<string name="home_module_count">Modules: %d</string>
<string name="home_unsupported_reason">KernelSU ne prend désormais en charge que les noyaux GKI</string>
<string name="home_kernel">Version du noyau</string>
<string name="home_kernel">Noyau</string>
<string name="home_fingerprint">Empreinte digitale</string>
<string name="home_selinux_status">Mode SELinux</string>
<string name="selinux_status_disabled">Désactivé</string>
@@ -30,7 +30,7 @@
<string name="install">Installer</string>
<string name="settings">Paramètres</string>
<string name="reboot_bootloader">Redémarrer en mode bootloader</string>
<string name="reboot_userspace">Redémarrage logiciel</string>
<string name="reboot_userspace">Redémarrage progressif</string>
<string name="reboot_recovery">Redémarrer en mode de récupération</string>
<string name="reboot_edl">Redémarrer en mode EDL</string>
<string name="about">À propos</string>
@@ -103,7 +103,7 @@
<string name="app_profile_template_import_empty">Le presse-papiers est vide !</string>
<string name="app_profile_template_view">Voir le modèle</string>
<string name="settings_check_update_summary">Vérifier automatiquement les mises à jour à l\'ouverture de l\'application</string>
<string name="settings_check_update">Rechercher des mises à jour</string>
<string name="settings_check_update">Vérifier les mises à jour</string>
<string name="enable_web_debugging">Activer le débogage WebView</string>
<string name="enable_web_debugging_summary">Peut être utilisé pour déboguer WebUI. Activez uniquement cette option si nécessaire.</string>
<string name="grant_root_failed">Échec de l\'octroi des privilèges root!</string>

View File

@@ -10,10 +10,10 @@
<string name="home_unsupported">Tidak didukung</string>
<string name="home_unsupported_reason">KernelSU saat ini hanya mendukung kernel GKI</string>
<string name="home_kernel">Kernel</string>
<string name="home_manager_version">Versi manajer</string>
<string name="home_manager_version">Versi manager</string>
<string name="home_fingerprint">Identitas</string>
<string name="home_selinux_status">Status SELinux</string>
<string name="selinux_status_disabled">Dinonaktifkan</string>
<string name="selinux_status_disabled">Nonaktif</string>
<string name="selinux_status_enforcing">Enforcing</string>
<string name="selinux_status_permissive">Permisif</string>
<string name="selinux_status_unknown">Tidak diketahui</string>
@@ -26,7 +26,7 @@
<string name="module_install">Instal</string>
<string name="install">Instal</string>
<string name="reboot">Reboot</string>
<string name="settings">Setelan</string>
<string name="settings">Pengaturan</string>
<string name="reboot_userspace">Soft Reboot</string>
<string name="reboot_recovery">Reboot ke Recovery</string>
<string name="reboot_bootloader">Reboot ke Bootloader</string>
@@ -38,7 +38,7 @@
<string name="module_uninstall_failed">Gagal menghapus: %s</string>
<string name="module_version">Versi</string>
<string name="module_author">Oleh</string>
<string name="module_overlay_fs_not_available">Modul tidak tersedia karena kernel tidak mendukung OverlayFS!</string>
<string name="module_overlay_fs_not_available">Kernel tidak mendukung OverlayFS, modul tidak akan berfungsi.</string>
<string name="refresh">Muat ulang</string>
<string name="show_system_apps">Tampilkan aplikasi sistem</string>
<string name="hide_system_apps">Sembunyikan aplikasi sistem</string>
@@ -57,7 +57,7 @@
<string name="profile_template">Templat</string>
<string name="profile_custom">Khusus</string>
<string name="profile_name">Nama profil</string>
<string name="profile_namespace">Gunakan Namespace</string>
<string name="profile_namespace">Mount Namespace</string>
<string name="profile_namespace_inherited">Diwariskan</string>
<string name="profile_namespace_global">Universal</string>
<string name="profile_namespace_individual">Individual</string>
@@ -88,7 +88,7 @@
<string name="app_profile_import_from_clipboard">Impor dari papan klip</string>
<string name="module_changelog_failed">Gagal mengambil Changelog: %s</string>
<string name="app_profile_template_name">Nama</string>
<string name="app_profile_template_id_invalid">ID templat tidak valid</string>
<string name="app_profile_template_id_invalid">ID template tidak valid</string>
<string name="app_profile_template_sync">Sinkronkan templat daring</string>
<string name="app_profile_template_create">Buat templat</string>
<string name="app_profile_import_export">Impor/Ekspor</string>
@@ -104,7 +104,7 @@
<string name="app_profile_template_view">Lihat templat</string>
<string name="app_profile_template_readonly">readonly</string>
<string name="enable_web_debugging">Pengawakutuan WebView</string>
<string name="enable_web_debugging_summary">Dapat mengawakutu WebView, hanya aktifkan jika butuh.</string>
<string name="enable_web_debugging_summary">Dapat digunakan untuk men-debug WebUI. Harap aktifkan hanya bila diperlukan.</string>
<string name="select_file_tip">%1$s image partisi terekomendasi</string>
<string name="select_kmi">Pilih KMI</string>
<string name="install_next">Selanjutnya</string>
@@ -132,13 +132,8 @@
<string name="flashing">Pasang</string>
<string name="flash_failed">Pemasangan Gagal</string>
<string name="save_log">Simpan Log</string>
<string name="action">Aksi</string>
<string name="action">Action</string>
<string name="log_saved">Log disimpan</string>
<string name="module_sort_enabled_first">Urut (Diaktifkan terlebih dahulu)</string>
<string name="module_sort_action_first">Urut (Tindakan pertama)</string>
<string name="module_install_prompt_with_name">Modul yg akan diinstal: %1$s</string>
<string name="confirm">Oke</string>
<string name="su_not_allowed">Akses SU tidak dapat diberikan ke %s</string>
<string name="settings_disable_su">Nonaktifkan kompatibilats SU</string>
<string name="settings_disable_su_summary">Nonaktifkan sementara kemampuan aplikasi memperoleh hak akses root via perintah SU (tidak mempengaruhi proses root yg sudah ada).</string>
</resources>

View File

@@ -1,6 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="home">ទំព័រដើម</string>
<string name="home_not_installed">មិនទាន់បានដំឡើង</string>
<string name="home_click_to_install">ចុចដើម្បីដំឡើង</string>
</resources>

View File

@@ -1,2 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<resources></resources>

View File

@@ -9,7 +9,7 @@
<string name="home_module_count">Modules: %d</string>
<string name="home_unsupported">Niet ondersteund</string>
<string name="home_unsupported_reason">KernelSU ondersteunt alleen GKI kernels</string>
<string name="home_kernel">Kernel version</string>
<string name="home_kernel">Kernel</string>
<string name="home_manager_version">Manager versie</string>
<string name="home_fingerprint">Fingerprint</string>
<string name="home_selinux_status">SELinux status</string>
@@ -38,7 +38,7 @@
<string name="module_uninstall_failed">Mislukt om te verwijderen: %s</string>
<string name="module_version">Versie</string>
<string name="module_author">Auteur</string>
<string name="module_overlay_fs_not_available">Modules zijn niet beschikbaar omdat OverlayFS door de kernel is uitgeschakeld!</string>
<string name="module_overlay_fs_not_available">Modules zijn niet beschikbaar omdat OverlayFS door de kernel is uitgeschakeld.</string>
<string name="refresh">Vernieuwen</string>
<string name="show_system_apps">Toon systeem apps</string>
<string name="hide_system_apps">Verberg systeem apps</string>
@@ -81,7 +81,7 @@
<string name="failed_to_update_sepolicy">Kan SELinux-regels niet bijwerken voor %s</string>
<string name="require_kernel_version">De huidige KernelSU-versie %d is te laag voor de manager om goed te werken. Upgrade naar versie %d of hoger!</string>
<string name="module_changelog">wijzigings logboek</string>
<string name="settings_profile_template">App-profiel sjabloon</string>
<string name="settings_profile_template">App-profiel Sjabloon</string>
<string name="app_profile_template_create">Maken sjabloon</string>
<string name="app_profile_template_edit">Bewerkin sjabloon</string>
<string name="app_profile_template_id">ID</string>
@@ -101,7 +101,7 @@
<string name="app_profile_import_from_clipboard">Importeren vanaf klembord</string>
<string name="module_changelog_failed">Ophalen van wijzigingslogboek mislukt: %s</string>
<string name="app_profile_export_to_clipboard">Exporteren naar klembord</string>
<string name="settings_check_update">Controleer for updates</string>
<string name="settings_check_update">Controleer update</string>
<string name="enable_web_debugging">Schakel WebView-foutopsporing</string>
<string name="enable_web_debugging_summary">Kan worden gebruikt om WebUI te debuggen. Schakel dit alleen in als dat nodig is.</string>
<string name="app_profile_template_export_empty">Kan niet geen lokale sjabloon vinden om te exporteren!</string>
@@ -140,5 +140,5 @@
<string name="su_not_allowed">Kan geen Superuser-toegang verlenen aan %s</string>
<string name="settings_disable_su">su-compatibiliteit uitschakelen</string>
<string name="confirm">Bevestigen</string>
<string name="settings_disable_su_summary">Schakel tijdelijk de mogelijkheid uit voor een app om rootrechten te verkrijgen via de opdracht su (Bestaande rootprocessen worden hierdoor niet beïnvloed).</string>
<string name="settings_disable_su_summary">Schakel tijdelijk de mogelijkheid uit voor een app om rootrechten te verkrijgen via de opdracht su (bestaande rootprocessen worden hierdoor niet beïnvloed).</string>
</resources>

View File

@@ -10,7 +10,7 @@
<string name="home_module_count">Moduły: %d</string>
<string name="home_unsupported">Nieobsługiwany</string>
<string name="home_unsupported_reason">KernelSU obsługuje obecnie tylko jądra GKI</string>
<string name="home_kernel">Wersja jądra</string>
<string name="home_kernel">Jądro</string>
<string name="home_manager_version">Wersja menedżera</string>
<string name="home_fingerprint">Odcisk</string>
<string name="home_selinux_status">Status SELinux</string>

View File

@@ -9,7 +9,7 @@
<string name="home_module_count">Módulos: %d</string>
<string name="home_unsupported">Sem suporte</string>
<string name="home_unsupported_reason">KernelSU suporta apenas kernels GKI agora</string>
<string name="home_kernel">Versão do kernel</string>
<string name="home_kernel">Kernel</string>
<string name="home_manager_version">Versão do gerenciador</string>
<string name="home_fingerprint">Impressão digital</string>
<string name="home_selinux_status">Status do SELinux</string>
@@ -103,7 +103,7 @@
<string name="app_profile_template_delete">Excluir</string>
<string name="app_profile_template_import_empty">A área de transferência está vazia!</string>
<string name="app_profile_template_view">Ver modelo</string>
<string name="settings_check_update">Verificar por atualizações</string>
<string name="settings_check_update">Verificar por atualização</string>
<string name="settings_check_update_summary">Verifique automaticamente se há atualizações ao abrir o app</string>
<string name="grant_root_failed">Falha ao conceder acesso root!</string>
<string name="open">Abrir</string>
@@ -136,7 +136,7 @@
<string name="log_saved">Registros salvos</string>
<string name="module_sort_action_first">Ordenar (Ação primeiro)</string>
<string name="module_sort_enabled_first">Ordenar (Ativado primeiro)</string>
<string name="settings_disable_su_summary">Desative temporariamente a capacidade de qualquer app obter privilégios root por meio do comando su (Processos root existentes não serão afetados).</string>
<string name="settings_disable_su_summary">Desative temporariamente a capacidade de qualquer app obter privilégios root por meio do comando su (processos root existentes não serão afetados).</string>
<string name="settings_disable_su">Desativar compatibilidade su</string>
<string name="confirm">Confirmar</string>
<string name="su_not_allowed">Não foi possível conceder acesso de SuperUsuário a %s</string>

View File

@@ -10,7 +10,7 @@
<string name="home_module_count">Модули: %d</string>
<string name="home_unsupported">Не поддерживается</string>
<string name="home_unsupported_reason">KernelSU поддерживает только GKI ядра</string>
<string name="home_kernel">Версия ядра</string>
<string name="home_kernel">Ядро</string>
<string name="home_manager_version">Версия менеджера</string>
<string name="home_fingerprint">Подпись</string>
<string name="home_selinux_status">Состояние SELinux</string>
@@ -106,7 +106,7 @@
<string name="app_profile_template_delete">Удалить</string>
<string name="app_profile_template_import_empty">Буфер обмена пуст!</string>
<string name="app_profile_template_view">Просмотр шаблона</string>
<string name="settings_check_update">Проверять наличие обновлений</string>
<string name="settings_check_update">Проверка обновлений</string>
<string name="settings_check_update_summary">Автоматическая проверка обновлений при открытии приложения</string>
<string name="grant_root_failed">Не удалось выдать root!</string>
<string name="open">Открыть</string>
@@ -140,7 +140,7 @@
<string name="module_sort_action_first">Сортировать (Сначала с действием)</string>
<string name="module_sort_enabled_first">Сортировать (Сначала включённые)</string>
<string name="settings_disable_su">Отключить su совместимость</string>
<string name="settings_disable_su_summary">Временно отключить возможность получения root привилегий любым приложениям с помощью команды su (Существующие root процессы не будут затронуты).</string>
<string name="settings_disable_su_summary">Временно отключить возможность получения root привилегий любым приложениям с помощью команды su (существующие root процессы не будут затронуты).</string>
<string name="module_install_prompt_with_name">Будут установлены следующие модули: %1$s</string>
<string name="confirm">Подтвердить</string>
<string name="su_not_allowed">Не удалось предоставить права Суперпользователя к %s</string>

View File

@@ -13,7 +13,7 @@
<string name="reboot_recovery">รีบูตเข้าสู่โหมดกู้คืน</string>
<string name="reboot_userspace">ซอฟต์รีบูต</string>
<string name="home_unsupported_reason">ตอนนี้ KernelSU รองรับเคอร์เนลประเภท GKI เท่านั้น</string>
<string name="home_kernel">วอร์ชันเคอร์เนล</string>
<string name="home_kernel">เคอร์เนล</string>
<string name="selinux_status_disabled">ปิดใช้งาน</string>
<string name="home_fingerprint">ลายนิ้วมือ</string>
<string name="home_selinux_status">สถานะ SELinux</string>
@@ -135,9 +135,4 @@
<string name="log_saved">บันทึก Log แล้ว</string>
<string name="module_sort_action_first">เรียงลำดับ (แบบรันคำสั่งก่อน)</string>
<string name="module_sort_enabled_first">เรียงลำดับ (แบบเปิดใช้งานก่อน)</string>
<string name="settings_disable_su_summary">ปิดใช้งานความสามารถของแอปต่าง ๆ ในการรับสิทธิ์ root ชั่วคราวโดยใช้คำสั่ง su (กระบวนการ root ที่มีอยู่จะไม่ได้รับผลกระทบ)</string>
<string name="module_install_prompt_with_name">โมดูล %1$s จะถูกติดตั้ง</string>
<string name="confirm">ยืนยัน</string>
<string name="su_not_allowed">ไม่สามารถให้สิทธิ์ผู้ใช้ขั้นสูงกับ %s ได้</string>
<string name="settings_disable_su">ปิดใช้งานความเข้ากันได้ของ su</string>
</resources>

View File

@@ -135,11 +135,4 @@
<string name="save_log">Günlükleri Kaydet</string>
<string name="action">Aksiyon</string>
<string name="log_saved">Günlükler kaydedildi</string>
<string name="confirm">Onayla</string>
<string name="su_not_allowed">%s için Superuser erişimi verilemedi</string>
<string name="settings_disable_su_summary">Herhangi bir uygulamanın su komutu aracılığıyla kök ayrıcalıkları elde etme yeteneğini geçici olarak devre dışı bırakın (mevcut kök işlemleri etkilenmeyecektir).</string>
<string name="module_install_prompt_with_name">Aşağıdaki modüller yüklenecek: %1$s</string>
<string name="module_sort_action_first">Sırala (Action önce)</string>
<string name="module_sort_enabled_first">Sırala (Etkin olanlar önce)</string>
<string name="settings_disable_su">Su uyumluluğunu devre dışı bırak</string>
</resources>

View File

@@ -8,20 +8,20 @@
<string name="profile_groups">Nhóm</string>
<string name="failed_to_update_app_profile">Không thể cập nhật Hồ sơ ứng dụng cho %s</string>
<string name="settings_umount_modules_default">Ngắt mô-đun theo mặc định</string>
<string name="settings_umount_modules_default_summary">Giá trị mặc định chung cho \"Ngắt mô-đun\" trong Hồ sơ ứng dụng. Khi bật, mọi thay đổi từ mô-đun sẽ bị loại bỏ khỏi hệ thống đối với các ứng dụng chưa được gán hồ sơ riêng.</string>
<string name="profile_umount_modules_summary">Bật tùy chọn này sẽ cho phép KernelSU khôi phục bất kỳ tệp đã sửa đổi bởi các mô-đun cho ứng dụng này.</string>
<string name="settings_umount_modules_default_summary">Giá trị mặc định của \"Ngắt mô-đun\" trong Cấu hình ứng dụng. Nếu bật, KernelSU sẽ khôi phục mọi tệp hệ thống đã sửa đổi bởi mô-đun cho các ứng dụng chưa thiết lập Cấu hình.</string>
<string name="profile_umount_modules_summary">Bật tùy chọn này sẽ khôi phục mọi tệp đã sửa đổi bởi các mô-đun cho ứng dụng này.</string>
<string name="module_update">Cập nhật</string>
<string name="module_downloading">Đang tải xuống mô-đun: %s</string>
<string name="module_start_downloading">Bắt đầu tải xuống: %s</string>
<string name="new_version_available">Có phiên bản mới %s, nhấn vào đây để cập nhật.</string>
<string name="home_learn_kernelsu">Tìm hiểu thêm về KernelSU</string>
<string name="new_version_available">Phiên bản mới: %s đã có, bấm để nâng cấp</string>
<string name="home_learn_kernelsu">Tìm hiểu KernelSU</string>
<string name="home_click_to_learn_kernelsu">Tìm hiểu cách cài đặt KernelSU và sử dụng các mô-đun</string>
<string name="home_support_title">Hỗ trợ chúng tôi</string>
<string name="home_support_content">KernelSU sẽ luôn miễn phí, mã nguồn mở. Tuy nhiên, bạn có thể thể hiện sự quan tâm của mình bằng cách quyên góp.</string>
<string name="about_source_code"><![CDATA[View source code at %1$s<br/>Tham gia kênh %2$s của chúng tôi]]></string>
<string name="module_magisk_conflict">Module không hoạt động do xung đột với Magisk!</string>
<string name="home_support_content">KernelSU sẽ luôn luôn miễn phí mã nguồn mở. Tuy nhiên bạn có thể ủng hộ chúng tôi bằng một khoản đóng góp nhỏ.</string>
<string name="about_source_code"><![CDATA[Xem mã nguồn tại %1$s<br/>Tham gia kênh %2$s của chúng tôi]]></string>
<string name="module_magisk_conflict">Các mô-đun bị vô hiệu hóa vì chúng xung đột với Magisk!</string>
<string name="module_uninstall_confirm">Bạn có muốn gỡ cài đặt mô-đun %s không\?</string>
<string name="send_log">Gửi nhật ký</string>
<string name="send_log">Nhật ký báo cáo</string>
<string name="home">Trang chủ</string>
<string name="home_not_installed">Chưa cài đặt</string>
<string name="home_click_to_install">Nhấn để cài đặt</string>
@@ -29,15 +29,15 @@
<string name="home_working_version">Phiên bản: %d</string>
<string name="home_unsupported">Không được hỗ trợ</string>
<string name="home_unsupported_reason">KernelSU hiện tại chỉ hỗ trợ kernel GKI</string>
<string name="home_kernel">Phiên bản Kernel</string>
<string name="home_manager_version">Phiên bản trình quản lý</string>
<string name="home_kernel">Kernel</string>
<string name="home_manager_version">Phiên bản Manager</string>
<string name="home_fingerprint">Fingerprint</string>
<string name="home_selinux_status">Trạng thái SELinux</string>
<string name="selinux_status_disabled">Vô hiệu hóa</string>
<string name="selinux_status_enforcing">Thực thi</string>
<string name="selinux_status_permissive">Cho phép</string>
<string name="selinux_status_unknown">Không rõ</string>
<string name="superuser">Siêu người dùng</string>
<string name="superuser">SuperUser</string>
<string name="module_failed_to_enable">Không thể kích hoạt mô-đun: %s</string>
<string name="module_failed_to_disable">Không thể vô hiệu hóa mô-đun: %s</string>
<string name="module_empty">Chưa cài đặt mô-đun nào</string>
@@ -46,97 +46,90 @@
<string name="module_install">Cài đặt</string>
<string name="install">Cài đặt</string>
<string name="reboot">Khởi động lại</string>
<string name="settings">Cài đặt</string>
<string name="settings">Thiết đặt</string>
<string name="reboot_userspace">Khởi động mềm</string>
<string name="reboot_recovery">Khởi động vào Recovery</string>
<string name="reboot_bootloader">Khởi động vào Bootloader</string>
<string name="reboot_download">Khởi động vào Download</string>
<string name="reboot_edl">Khởi động vào EDL</string>
<string name="reboot_recovery">Khởi động lại vào Recovery</string>
<string name="reboot_bootloader">Khởi động lại vào Bootloader</string>
<string name="reboot_download">Khởi động lại vào Download Mode</string>
<string name="reboot_edl">Khởi động lại vào EDL</string>
<string name="about">Giới thiệu</string>
<string name="module_uninstall_success">Đã gỡ cài đặt %s</string>
<string name="module_uninstall_failed">Không thể gỡ cài đặt: %s</string>
<string name="module_uninstall_success">%s được gỡ cài đặt</string>
<string name="module_uninstall_failed">Lỗi khi gỡ cài đặt: %s</string>
<string name="module_version">Phiên bản</string>
<string name="module_author">Tác giả</string>
<string name="module_overlay_fs_not_available">Module không hoạt động vì OverlayFS đã bị kernel vô hiệu hóa!</string>
<string name="module_overlay_fs_not_available">overlayfs hiện không khả dụng, mô-đun không thể hoạt động!</string>
<string name="refresh">Làm mới</string>
<string name="show_system_apps">Hiển thị ứng dụng hệ thống</string>
<string name="hide_system_apps">Ẩn ứng dụng hệ thống</string>
<string name="safe_mode">Chế độ an toàn</string>
<string name="reboot_to_apply">Khởi động lại để áp dụng thay đổi</string>
<string name="home_learn_kernelsu_url">https://kernelsu.org/guide/what-is-kernelsu.html</string>
<string name="reboot_to_apply">Khởi động lại để có hiệu lực</string>
<string name="home_learn_kernelsu_url">https://kernelsu.org/vi_VN/guide/what-is-kernelsu.html</string>
<string name="home_superuser_count">Số superuser: %d</string>
<string name="home_module_count">Số mô-đun: %d</string>
<string name="profile_selinux_domain">Phạm vi</string>
<string name="profile_selinux_rules">Quy tắc</string>
<string name="profile_selinux_rules">Quy định</string>
<string name="launch_app">Khởi chạy</string>
<string name="restart_app">Khởi động lại</string>
<string name="profile_namespace">Gắn namespace</string>
<string name="profile_capabilities">Quyền</string>
<string name="failed_to_update_sepolicy">Không thể cập nhật quy tắc SELinux cho %s</string>
<string name="failed_to_update_sepolicy">Không thể cập nhật quy định SELinux cho: %s</string>
<string name="force_stop_app">Buộc dừng</string>
<string name="profile_namespace_inherited">Inherited</string>
<string name="profile_namespace_global">Global</string>
<string name="profile_namespace_individual">Individual</string>
<string name="profile_namespace_inherited">Thừa hưởng</string>
<string name="profile_namespace_global">Chung</string>
<string name="profile_namespace_individual">Riêng</string>
<string name="profile_selinux_context">Bối cảnh SELinux</string>
<string name="profile_umount_modules">Ngắt mô-đun</string>
<string name="require_kernel_version">Phiên bản KernelSU bạn đang dùng (%d) quá để trình quản lý hoạt động ổn định. Hãy cập nhật từ phiên bản %d trở lên!</string>
<string name="require_kernel_version">KernelSU phiên bản %d quá thấp để trình quản lý hoạt động, hãy cập nhật lên %d hoặc mới hơn!</string>
<string name="app_profile_template_import_success">Đã nhập thành công</string>
<string name="app_profile_export_to_clipboard">Xuất vào bảng nhớ tạm</string>
<string name="app_profile_template_export_empty">Không có mẫu nào để xuất!</string>
<string name="app_profile_template_id_exist">ID mẫu đã tồn tại!</string>
<string name="app_profile_export_to_clipboard">Xuất từ khay nhớ tạm</string>
<string name="app_profile_template_export_empty">Không thể tìm thấy mẫu cục bộ để xuất!</string>
<string name="app_profile_template_id_exist">id bản mẫu đã tồn tại!</string>
<string name="module_changelog">Nhật ký thay đổi</string>
<string name="app_profile_import_from_clipboard">Nhập từ bảng nhớ tạm</string>
<string name="app_profile_import_from_clipboard">Nhập từ khay nhớ tạm</string>
<string name="module_changelog_failed">Không nạp được nhật ký thay đổi: %s</string>
<string name="app_profile_template_name">Tên</string>
<string name="app_profile_template_id_invalid">ID mẫu không hợp lệ</string>
<string name="app_profile_template_sync">Đồng bộ mẫu trực tuyến</string>
<string name="app_profile_template_create">Tạo mẫu</string>
<string name="app_profile_template_id_invalid">Id mẫu không hợp lệ</string>
<string name="app_profile_template_sync">Đồng bộ hóa các mẫu trực tuyến</string>
<string name="app_profile_template_create">Tạo Bản Mẫu</string>
<string name="app_profile_import_export">Nhập/Xuất</string>
<string name="app_profile_template_save_failed">Không lưu được mẫu</string>
<string name="app_profile_template_edit">Sửa mẫu</string>
<string name="settings_profile_template">Mẫu hsơ ng dụng</string>
<string name="app_profile_template_edit">Sửa Bản Mẫu</string>
<string name="settings_profile_template">Mẫu HSơ ng Dụng</string>
<string name="app_profile_template_description">Mô tả</string>
<string name="app_profile_template_save">Lưu</string>
<string name="settings_profile_template_summary">Quản lý mẫu Hồ sơ Ứng dụng và trực tuyến</string>
<string name="settings_profile_template_summary">Quản lý mẫu Hồ sơ Ứng dụng cục bộ và trực tuyến</string>
<string name="app_profile_template_delete">Xóa</string>
<string name="app_profile_template_import_empty">Bảng nhớ tạm đang trống!</string>
<string name="app_profile_template_view">Xem mẫu</string>
<string name="app_profile_template_readonly">Chỉ đọc</string>
<string name="app_profile_template_id">ID</string>
<string name="app_profile_template_import_empty">Clipboard trống!</string>
<string name="app_profile_template_view">Xem Bản Mẫu</string>
<string name="app_profile_template_readonly">chỉ đọc</string>
<string name="app_profile_template_id">id</string>
<string name="enable_web_debugging">Bật gỡ lỗi WebView</string>
<string name="enable_web_debugging_summary">Có thể ng để gỡ lỗi WebUI. Vui lòng chỉ bật khi cần thiết.</string>
<string name="enable_web_debugging_summary">Có thể được sử dụng để gỡ lỗi WebUI, vui lòng chỉ bật khi cần.</string>
<string name="grant_root_failed">Không cấp được quyền root!</string>
<string name="settings_check_update">Kiểm tra cập nhật</string>
<string name="settings_check_update_summary">Tự động kiểm tra cập nhật khi mở ứng dụng</string>
<string name="open">Mở</string>
<string name="install_inactive_slot">Cài đặt vào phân vùng không hoạt động (Sau khi cập nhật OTA)</string>
<string name="install_inactive_slot_warning">Thiết bị của bạn sẽ **BẮT BUỘC** khởi động vào phân vùng không hoạt động hiện tại sau khi khởi động lại!\nChỉ dùng tùy chọn này khi cập nhật OTA đã hoàn tất.\nTiếp tục?</string>
<string name="install_inactive_slot">Cài đặt vào khe không hoạt động (Sau OTA)</string>
<string name="install_inactive_slot_warning">Thiết bị của bạn sẽ **BẮT BUỘC** khởi động vào khe không hoạt động hiện tại sau khi khởi động lại!
\nChỉ sử dụng tùy chọn này sau khi OTA hoàn tất.
\nTiếp tục?</string>
<string name="settings_uninstall_temporary_message">Tạm thời gỡ cài đặt KernelSU, khôi phục về trạng thái ban đầu sau lần khởi động lại tiếp theo.</string>
<string name="select_kmi">Chọn KMI</string>
<string name="install_next">Kế tiếp</string>
<string name="direct_install">Cài đặt trực tiếp (Khuyến nghị)</string>
<string name="direct_install">Cài đặt trực tiếp (Được khuyến nghị)</string>
<string name="select_file">Chọn một tệp</string>
<string name="settings_uninstall">Gỡ cài đặt</string>
<string name="settings_uninstall_temporary">Gỡ cài đặt tạm thời</string>
<string name="settings_uninstall_permanent">Gỡ cài đặt vĩnh viễn</string>
<string name="settings_restore_stock_image">Khôi phục hình ảnh gốc</string>
<string name="settings_uninstall_permanent_message">Gỡ hoàn toàn KernelSU khỏi thiết bị, bao gồm cả quyền root và tất cả mô-đun đã cài.</string>
<string name="settings_restore_stock_image_message">Khôi phục hình ảnh gốc nhà máy (nếu bạn đã sao lưu trước đó), thường thực hiện trước khi cập nhật OTA; còn nếu muốn gỡ cài đặt KernelSU thì hãy chọn “Gỡ cài đặt vĩnh viễn.</string>
<string name="settings_uninstall_permanent_message">Gỡ cài đặt KernelSU (Root và tất cả các mô-đun) hoàn toàn và vĩnh viễn.</string>
<string name="settings_restore_stock_image_message">Khôi phục hình ảnh gốc của nhà máy (nếu có bản sao lưu), thường được sử dụng trước OTA; nếu bạn cần gỡ cài đặt KernelSU, vui lòng sử dụng \"Gỡ cài đặt vĩnh viễn\".</string>
<string name="flashing">Đang cài</string>
<string name="flash_success">Cài thành công</string>
<string name="flash_failed">Cài thất bại</string>
<string name="selected_lkm">Đã chọn LKM: %s</string>
<string name="selected_lkm">Đã chọn lkm: %s</string>
<string name="select_file_tip">Nên sử dụng hình ảnh phân vùng %1$s</string>
<string name="shrink_sparse_image">Giảm kích thước hình ảnh sparse</string>
<string name="shrink_sparse_image_message">Thay đổi kích thước hình ảnh sparse chứa mô-đun về đúng kích thước thực của nó. Lưu ý điều này có thể khiến mô-đun hoạt động không ổn định, vui lòng chỉ sử dụng khi cần thiết (Chẳng hạn như khi sao lưu).</string>
<string name="shrink_sparse_image">Giảm thiểu hình ảnh thưa thớt</string>
<string name="shrink_sparse_image_message">Thay đổi kích thước hình ảnh thưa nơi đặt mô-đun theo kích thước thực tế của nó. Lưu ý điều này có thể khiến module hoạt động không bình thường nên vui lòng chỉ sử dụng khi cần thiết (chẳng hạn như để sao lưu)</string>
<string name="save_log">Lưu Nhật Ký</string>
<string name="module_sort_action_first">Sắp xếp (Hoạt động trước)</string>
<string name="module_install_prompt_with_name">Các mô-đun sau sẽ được cài đặt: %1$s</string>
<string name="confirm">Xác nhận</string>
<string name="module_sort_enabled_first">Sắp xếp (Đã bật trước)</string>
<string name="su_not_allowed">Không thể cấp quyền Superuser cho %s</string>
<string name="action">Hoạt động</string>
<string name="log_saved">Đã lưu nhật ký</string>
<string name="settings_disable_su_summary">Tạm thời ngăn các ứng dụng mới sử dụng quyền root qua lệnh su (các tiến trình đã được cấp quyền root sẽ không bị ảnh hưởng).</string>
<string name="settings_disable_su">Tắt khả năng tương thích với su</string>
</resources>

View File

@@ -8,7 +8,7 @@
<string name="home_superuser_count">授權:%d 個應用程式</string>
<string name="home_unsupported">未受支援</string>
<string name="home_unsupported_reason">KernelSU 目前僅支援 GKI 核心</string>
<string name="home_kernel">核心版本</string>
<string name="home_kernel">裝置核心</string>
<string name="home_manager_version">管理工具</string>
<string name="home_fingerprint">指紋資訊</string>
<string name="home_selinux_status">SELinux 狀態</string>
@@ -37,11 +37,11 @@
<string name="module_uninstall_failed">無法解除安裝:%s</string>
<string name="module_version">版本</string>
<string name="module_author">作者</string>
<string name="module_overlay_fs_not_available">OverlayFS 已遭核心停用,無法使用模組功能</string>
<string name="module_overlay_fs_not_available">OverlayFS 已遭核心停用,無法使用模組功能</string>
<string name="refresh">重新載入</string>
<string name="show_system_apps">顯示系統程式</string>
<string name="hide_system_apps">隱藏系統程式</string>
<string name="send_log">傳送日誌</string>
<string name="send_log">發送運作日誌</string>
<string name="safe_mode">安全模式</string>
<string name="reboot_to_apply">將在重新啟動時生效</string>
<string name="module_magisk_conflict">與 Magisk 發生衝突,無法使用模組功能!</string>
@@ -50,7 +50,7 @@
<string name="home_learn_kernelsu_url">https://kernelsu.org/zh_TW/guide/what-is-kernelsu.html</string>
<string name="home_click_to_learn_kernelsu">知曉安裝、使用 KernelSU 本體與其模組功能的方法</string>
<string name="home_support_title">協助發展</string>
<string name="home_support_content">KernelSU 一向以免費與開放原始碼自居,矢志不渝。若想協助我們,可以用小額捐款表達你對專案發展的大力支持。</string>
<string name="home_support_content">KernelSU 一向以免費製品與開放原始碼自居,矢志不渝。若想協助我們,請以小額捐款表達你對專案發展的大力支持。</string>
<string name="about_source_code"><![CDATA[前往 %1$s 檢閱原始碼<br/>前往 %2$s 加入頻道]]></string>
<string name="profile_umount_modules">解除掛載模組功能</string>
<string name="failed_to_update_app_profile">無法更新「%s」App Profile</string>
@@ -91,7 +91,7 @@
<string name="app_profile_template_export_empty">查無可供匯出的本地範本!</string>
<string name="app_profile_template_id_exist">編號已由其他範本領有!</string>
<string name="app_profile_import_from_clipboard">自剪貼簿匯入</string>
<string name="module_changelog_failed">無法取更新說明:%s</string>
<string name="module_changelog_failed">無法取更新說明:%s</string>
<string name="app_profile_template_name">名稱</string>
<string name="app_profile_template_sync">同步線上範本</string>
<string name="app_profile_template_readonly">唯讀</string>
@@ -128,14 +128,7 @@
<string name="settings_restore_stock_image_message">若裝置內含有備份檔案,遂以 OTA 更新前的原廠系統映像檔進行復原。若需要解除安裝 KernelSU請選擇「永久性解除安裝」。</string>
<string name="flash_failed">閃刷失敗</string>
<string name="selected_lkm">已選定 LKM%s</string>
<string name="save_log">儲存日誌</string>
<string name="save_log">儲存運作日誌</string>
<string name="action">執行</string>
<string name="log_saved">日誌已儲存</string>
<string name="module_sort_enabled_first">排序(啟用優先)</string>
<string name="module_sort_action_first">排序(執行優先)</string>
<string name="module_install_prompt_with_name">將安裝以下模組:%1$s</string>
<string name="confirm">確認</string>
<string name="settings_disable_su_summary">暫時禁用任何應用程式通過⁠ su 命令獲得 root 權限的能力(現有的 root 進程不會受到影響)。</string>
<string name="su_not_allowed">無法授予「%s」超級使用者存取</string>
<string name="settings_disable_su">停用 su 相容性</string>
<string name="log_saved">已儲存運作日誌</string>
</resources>

View File

@@ -10,7 +10,7 @@
<string name="home_module_count">Modules: %d</string>
<string name="home_unsupported">Unsupported</string>
<string name="home_unsupported_reason">KernelSU only supports GKI kernels now</string>
<string name="home_kernel">Kernel version</string>
<string name="home_kernel">Kernel</string>
<string name="home_manager_version">Manager version</string>
<string name="home_fingerprint">Fingerprint</string>
<string name="home_selinux_status">SELinux status</string>
@@ -32,7 +32,7 @@
<string name="install">Install</string>
<string name="reboot">Reboot</string>
<string name="settings">Settings</string>
<string name="reboot_userspace">Soft reboot</string>
<string name="reboot_userspace">Soft Reboot</string>
<string name="reboot_recovery">Reboot to Recovery</string>
<string name="reboot_bootloader">Reboot to Bootloader</string>
<string name="reboot_download">Reboot to Download</string>
@@ -55,7 +55,7 @@
<string name="home_learn_kernelsu_url">https://kernelsu.org/guide/what-is-kernelsu.html</string>
<string name="home_click_to_learn_kernelsu">Learn how to install KernelSU and use modules</string>
<string name="home_support_title">Support Us</string>
<string name="home_support_content">KernelSU is, and always will be, free, and open source. However, you can show us that you care by making a donation.</string>
<string name="home_support_content">KernelSU is, and always will be, free, and open source. You can however show us that you care by making a donation.</string>
<string name="about_source_code"><![CDATA[View source code at %1$s<br/>Join our %2$s channel]]></string>
<string name="profile" translatable="false">App Profile</string>
<string name="profile_default">Default</string>
@@ -87,7 +87,7 @@
<string name="failed_to_update_sepolicy">Failed to update SELinux rules for %s</string>
<string name="su_not_allowed">Couldn\'t grant Superuser access to %s</string>
<string name="module_changelog">Changelog</string>
<string name="settings_profile_template">App Profile template</string>
<string name="settings_profile_template">App Profile Template</string>
<string name="settings_profile_template_summary">Manage local and online template of App Profile</string>
<string name="app_profile_template_create">Create template</string>
<string name="app_profile_template_edit">Edit template</string>
@@ -109,7 +109,7 @@
<string name="app_profile_template_save_failed">Failed to save template</string>
<string name="app_profile_template_import_empty">Clipboard is empty!</string>
<string name="module_changelog_failed">Fetch changelog failed: %s</string>
<string name="settings_check_update">Check for updates</string>
<string name="settings_check_update">Check update</string>
<string name="settings_check_update_summary">Automatically check for updates when opening the app</string>
<string name="grant_root_failed">Failed to grant root!</string>
<string name="action">Action</string>
@@ -139,5 +139,5 @@
<string name="save_log">Save logs</string>
<string name="log_saved">Logs saved</string>
<string name="settings_disable_su">Disable su compatibility</string>
<string name="settings_disable_su_summary">Temporarily disable the ability of any app to gain root privileges via the su command (Existing root processes won\'t be affected).</string>
<string name="settings_disable_su_summary">Temporarily disable the ability of any app to gain root privileges via the su command (existing root processes won\'t be affected).</string>
</resources>

View File

@@ -1,9 +1,9 @@
[versions]
agp = "8.10.1"
agp = "8.10.0"
kotlin = "2.1.21"
ksp = "2.1.21-2.0.2"
compose-bom = "2025.06.00"
lifecycle = "2.9.1"
ksp = "2.1.20-2.0.1"
compose-bom = "2025.05.00"
lifecycle = "2.9.0"
navigation = "2.9.0"
activity-compose = "1.10.1"
kotlinx-coroutines = "1.10.2"
@@ -11,7 +11,7 @@ coil-compose = "2.7.0"
compose-destination = "2.2.0"
sheets-compose-dialogs = "1.3.0"
markdown = "4.6.2"
webkit = "1.14.0"
webkit = "1.13.0"
appiconloader-coil = "1.5.0"
parcelablelist = "2.0.1"
libsu = "6.0.0"
@@ -71,4 +71,4 @@ sheet-compose-dialogs-input = { group = "com.maxkeppeler.sheets-compose-dialogs"
markdown = { group = "io.noties.markwon", name = "core", version.ref = "markdown" }
lsposed-cxx = { module = "org.lsposed.libcxx:libcxx", version = "28.1.13356709" }
lsposed-cxx = { module = "org.lsposed.libcxx:libcxx", version = "27.0.12077973" }

View File

@@ -483,6 +483,17 @@ dependencies = [
"crypto-common",
]
[[package]]
name = "displaydoc"
version = "0.2.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "97369cbbc041bc366949bc74d34658d6cda5621039731c6310521892a3a20ae0"
dependencies = [
"proc-macro2",
"quote",
"syn",
]
[[package]]
name = "either"
version = "1.15.0"
@@ -584,7 +595,6 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7ced92e76e966ca2fd84c8f7aa01a4aea65b0eb6648d72f7c8f3e2764a67fece"
dependencies = [
"crc32fast",
"libz-rs-sys",
"miniz_oxide",
]
@@ -672,7 +682,7 @@ dependencies = [
"errno 0.2.8",
"libc",
"memmap",
"thiserror",
"thiserror 1.0.69",
"winapi",
]
@@ -873,15 +883,6 @@ version = "0.2.15"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f9fbbcab51052fe104eb5e5d351cf728d30a5be1fe14d9be8a3b097481fb97de"
[[package]]
name = "libz-rs-sys"
version = "0.5.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "172a788537a2221661b480fee8dc5f96c580eb34fa88764d3205dc356c7e4221"
dependencies = [
"zlib-rs",
]
[[package]]
name = "linux-raw-sys"
version = "0.4.15"
@@ -1310,7 +1311,16 @@ version = "1.0.69"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b6aaf5339b578ea85b50e080feb250a3e8ae8cfcdff9a461c9ec2904bc923f52"
dependencies = [
"thiserror-impl",
"thiserror-impl 1.0.69",
]
[[package]]
name = "thiserror"
version = "2.0.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d452f284b73e6d76dd36758a0c8684b1d5be31f92b89d07fd5822175732206fc"
dependencies = [
"thiserror-impl 2.0.11",
]
[[package]]
@@ -1324,6 +1334,17 @@ dependencies = [
"syn",
]
[[package]]
name = "thiserror-impl"
version = "2.0.11"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "26afc1baea8a989337eeb52b6e72a039780ce45c3edfcc9c5b9d112feeb173c2"
dependencies = [
"proc-macro2",
"quote",
"syn",
]
[[package]]
name = "time"
version = "0.3.41"
@@ -1704,10 +1725,12 @@ dependencies = [
"arbitrary",
"crc32fast",
"deflate64",
"displaydoc",
"flate2",
"indexmap",
"lzma-rs",
"memchr",
"thiserror 2.0.11",
"time",
"xz2",
"zopfli",
@@ -1722,12 +1745,6 @@ dependencies = [
"zip",
]
[[package]]
name = "zlib-rs"
version = "0.5.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "626bd9fa9734751fc50d6060752170984d7053f5a39061f524cda68023d4db8a"
[[package]]
name = "zopfli"
version = "0.8.2"

View File

@@ -14,7 +14,7 @@ fn get_git_version() -> Result<(u32, String), std::io::Error> {
let version_code: u32 = version_code
.trim()
.parse()
.map_err(|_| std::io::Error::other("Failed to parse git count"))?;
.map_err(|_| std::io::Error::new(std::io::ErrorKind::Other, "Failed to parse git count"))?;
let version_code = 10000 + 200 + version_code; // For historical reasons
let version_name = String::from_utf8(
@@ -23,7 +23,12 @@ fn get_git_version() -> Result<(u32, String), std::io::Error> {
.output()?
.stdout,
)
.map_err(|_| std::io::Error::other("Failed to read git describe stdout"))?;
.map_err(|_| {
std::io::Error::new(
std::io::ErrorKind::Other,
"Failed to read git describe stdout",
)
})?;
let version_name = version_name.trim_start_matches('v').to_string();
Ok((version_code, version_name))
}

View File

@@ -153,40 +153,38 @@ fn parse_kmi_from_boot(magiskboot: &Path, image: &PathBuf, workdir: &Path) -> Re
parse_kmi_from_kernel(&image_path, workdir)
}
fn do_cpio_cmd(magiskboot: &Path, workdir: &Path, cpio_path: &Path, cmd: &str) -> Result<()> {
fn do_cpio_cmd(magiskboot: &Path, workdir: &Path, cmd: &str) -> Result<()> {
let status = Command::new(magiskboot)
.current_dir(workdir)
.stdout(Stdio::null())
.stderr(Stdio::null())
.arg("cpio")
.arg(cpio_path)
.arg("ramdisk.cpio")
.arg(cmd)
.status()?;
ensure!(status.success(), "magiskboot cpio {} failed", cmd);
Ok(())
}
fn is_magisk_patched(magiskboot: &Path, workdir: &Path, cpio_path: &Path) -> Result<bool> {
fn is_magisk_patched(magiskboot: &Path, workdir: &Path) -> Result<bool> {
let status = Command::new(magiskboot)
.current_dir(workdir)
.stdout(Stdio::null())
.stderr(Stdio::null())
.arg("cpio")
.arg(cpio_path)
.arg("test")
.args(["cpio", "ramdisk.cpio", "test"])
.status()?;
// 0: stock, 1: magisk
Ok(status.code() == Some(1))
}
fn is_kernelsu_patched(magiskboot: &Path, workdir: &Path, cpio_path: &Path) -> Result<bool> {
fn is_kernelsu_patched(magiskboot: &Path, workdir: &Path) -> Result<bool> {
let status = Command::new(magiskboot)
.current_dir(workdir)
.stdout(Stdio::null())
.stderr(Stdio::null())
.arg("cpio")
.arg(cpio_path)
.arg("exists kernelsu.ko")
.args(["cpio", "ramdisk.cpio", "exists kernelsu.ko"])
.status()?;
Ok(status.success())
@@ -236,37 +234,18 @@ pub fn restore(
.status()?;
ensure!(status.success(), "magiskboot unpack failed");
let mut ramdisk = workdir.join("ramdisk.cpio");
if !ramdisk.exists() {
ramdisk = workdir.join("vendor_ramdisk").join("init_boot.cpio")
}
if !ramdisk.exists() {
ramdisk = workdir.join("vendor_ramdisk").join("ramdisk.cpio");
}
if !ramdisk.exists() {
bail!("No compatible ramdisk found.")
}
let ramdisk = ramdisk.as_path();
let is_kernelsu_patched = is_kernelsu_patched(&magiskboot, workdir, ramdisk)?;
let is_kernelsu_patched = is_kernelsu_patched(&magiskboot, workdir)?;
ensure!(is_kernelsu_patched, "boot image is not patched by KernelSU");
let mut new_boot = None;
let mut from_backup = false;
#[cfg(target_os = "android")]
if do_cpio_cmd(
&magiskboot,
workdir,
ramdisk,
&format!("exists {BACKUP_FILENAME}"),
)
.is_ok()
{
if do_cpio_cmd(&magiskboot, workdir, &format!("exists {BACKUP_FILENAME}")).is_ok() {
do_cpio_cmd(
&magiskboot,
workdir,
ramdisk,
&format!("extract {BACKUP_FILENAME} {BACKUP_FILENAME}"),
&format!("extract {0} {0}", BACKUP_FILENAME),
)?;
let sha = std::fs::read(workdir.join(BACKUP_FILENAME))?;
let sha = String::from_utf8(sha)?;
@@ -289,12 +268,15 @@ pub fn restore(
if new_boot.is_none() {
// remove kernelsu.ko
do_cpio_cmd(&magiskboot, workdir, ramdisk, "rm kernelsu.ko")?;
do_cpio_cmd(&magiskboot, workdir, "rm kernelsu.ko")?;
// if init.real exists, restore it
let status = do_cpio_cmd(&magiskboot, workdir, ramdisk, "exists init.real").is_ok();
let status = do_cpio_cmd(&magiskboot, workdir, "exists init.real").is_ok();
if status {
do_cpio_cmd(&magiskboot, workdir, ramdisk, "mv init.real init")?;
do_cpio_cmd(&magiskboot, workdir, "mv init.real init")?;
} else {
let ramdisk = workdir.join("ramdisk.cpio");
std::fs::remove_file(ramdisk)?;
}
println!("- Repacking boot image");
@@ -303,7 +285,7 @@ pub fn restore(
.stdout(Stdio::null())
.stderr(Stdio::null())
.arg("repack")
.arg(&bootimage)
.arg(bootimage.display().to_string())
.status()?;
ensure!(status.success(), "magiskboot repack failed");
new_boot = Some(workdir.join("new-boot.img"));
@@ -402,7 +384,7 @@ fn do_patch(
match get_current_kmi() {
Ok(value) => value,
Err(e) => {
println!("- {e}");
println!("- {}", e);
if let Some(image_path) = &image {
println!(
"- Trying to auto detect KMI version for {}",
@@ -427,7 +409,7 @@ fn do_patch(
let (bootimage, bootdevice) =
find_boot_image(&image, skip_init, ota, is_replace_kernel, workdir)?;
let bootimage = bootimage.as_path();
let bootimage = bootimage.display().to_string();
// try extract magiskboot/bootctl
let _ = assets::ensure_binaries(false);
@@ -456,54 +438,48 @@ fn do_patch(
assets::copy_assets_to_file("ksuinit", init_file).context("copy ksuinit failed")?;
}
// magiskboot unpack boot.img
// magiskboot cpio ramdisk.cpio 'cp init init.real'
// magiskboot cpio ramdisk.cpio 'add 0755 ksuinit init'
// magiskboot cpio ramdisk.cpio 'add 0755 <kmod> kernelsu.ko'
println!("- Unpacking boot image");
let status = Command::new(&magiskboot)
.current_dir(workdir)
.stdout(Stdio::null())
.stderr(Stdio::null())
.arg("unpack")
.arg(bootimage)
.arg(&bootimage)
.status()?;
ensure!(status.success(), "magiskboot unpack failed");
let mut ramdisk = workdir.join("ramdisk.cpio");
if !ramdisk.exists() {
ramdisk = workdir.join("vendor_ramdisk").join("init_boot.cpio")
}
if !ramdisk.exists() {
ramdisk = workdir.join("vendor_ramdisk").join("ramdisk.cpio");
}
if !ramdisk.exists() {
bail!("No compatible ramdisk found.");
}
let ramdisk = ramdisk.as_path();
let is_magisk_patched = is_magisk_patched(&magiskboot, workdir, ramdisk)?;
ensure!(!is_magisk_patched, "Cannot work with Magisk patched image");
let no_ramdisk = !workdir.join("ramdisk.cpio").exists();
let is_magisk_patched = is_magisk_patched(&magiskboot, workdir)?;
ensure!(
no_ramdisk || !is_magisk_patched,
"Cannot work with Magisk patched image"
);
println!("- Adding KernelSU LKM");
let is_kernelsu_patched = is_kernelsu_patched(&magiskboot, workdir, ramdisk)?;
let is_kernelsu_patched = is_kernelsu_patched(&magiskboot, workdir)?;
let mut need_backup = false;
if !is_kernelsu_patched {
// kernelsu.ko is not exist, backup init if necessary
let status = do_cpio_cmd(&magiskboot, workdir, ramdisk, "exists init");
let status = do_cpio_cmd(&magiskboot, workdir, "exists init");
if status.is_ok() {
do_cpio_cmd(&magiskboot, workdir, ramdisk, "mv init init.real")?;
do_cpio_cmd(&magiskboot, workdir, "mv init init.real")?;
}
need_backup = flash;
}
do_cpio_cmd(&magiskboot, workdir, ramdisk, "add 0755 init init")?;
do_cpio_cmd(
&magiskboot,
workdir,
ramdisk,
"add 0755 kernelsu.ko kernelsu.ko",
)?;
do_cpio_cmd(&magiskboot, workdir, "add 0755 init init")?;
do_cpio_cmd(&magiskboot, workdir, "add 0755 kernelsu.ko kernelsu.ko")?;
#[cfg(target_os = "android")]
if need_backup {
if let Err(e) = do_backup(&magiskboot, workdir, ramdisk, bootimage) {
if let Err(e) = do_backup(&magiskboot, workdir, &bootimage) {
println!("- Backup stock image failed: {e}");
}
}
@@ -515,7 +491,7 @@ fn do_patch(
.stdout(Stdio::null())
.stderr(Stdio::null())
.arg("repack")
.arg(bootimage)
.arg(&bootimage)
.status()?;
ensure!(status.success(), "magiskboot repack failed");
let new_boot = workdir.join("new-boot.img");
@@ -566,11 +542,11 @@ fn calculate_sha1(file_path: impl AsRef<Path>) -> Result<String> {
}
let result = hasher.finalize();
Ok(format!("{result:x}"))
Ok(format!("{:x}", result))
}
#[cfg(target_os = "android")]
fn do_backup(magiskboot: &Path, workdir: &Path, cpio_path: &Path, image: &Path) -> Result<()> {
fn do_backup(magiskboot: &Path, workdir: &Path, image: &str) -> Result<()> {
let sha1 = calculate_sha1(image)?;
let filename = format!("{KSU_BACKUP_FILE_PREFIX}{sha1}");
@@ -582,8 +558,7 @@ fn do_backup(magiskboot: &Path, workdir: &Path, cpio_path: &Path, image: &Path)
do_cpio_cmd(
magiskboot,
workdir,
cpio_path,
&format!("add 0755 {BACKUP_FILENAME} {BACKUP_FILENAME}"),
&format!("add 0755 {0} {0}", BACKUP_FILENAME),
)?;
println!("- Stock image has been backup to");
println!("- {target}");
@@ -593,7 +568,7 @@ fn do_backup(magiskboot: &Path, workdir: &Path, cpio_path: &Path, image: &Path)
#[cfg(target_os = "android")]
fn clean_backup(sha1: &str) -> Result<()> {
println!("- Clean up backup");
let backup_name = format!("{KSU_BACKUP_FILE_PREFIX}{sha1}");
let backup_name = format!("{}{}", KSU_BACKUP_FILE_PREFIX, sha1);
let dir = std::fs::read_dir(defs::KSU_BACKUP_DIR)?;
for entry in dir.flatten() {
let path = entry.path();
@@ -680,12 +655,8 @@ fn find_boot_image(
let init_boot_exist =
Path::new(&format!("/dev/block/by-name/init_boot{slot_suffix}")).exists();
let vendor_boot_exist =
Path::new(&format!("/dev/block/by-name/vendor_boot{slot_suffix}")).exists();
let boot_partition = if !is_replace_kernel && init_boot_exist && !skip_init {
format!("/dev/block/by-name/init_boot{slot_suffix}")
} else if !is_replace_kernel && vendor_boot_exist && !skip_init {
format!("/dev/block/by-name/vendor_boot{slot_suffix}")
} else {
format!("/dev/block/by-name/boot{slot_suffix}")
};

View File

@@ -374,13 +374,13 @@ pub fn run() -> Result<()> {
Commands::BootInfo { command } => match command {
BootInfo::CurrentKmi => {
let kmi = crate::boot_patch::get_current_kmi()?;
println!("{kmi}");
println!("{}", kmi);
// return here to avoid printing the error message
return Ok(());
}
BootInfo::SupportedKmi => {
let kmi = crate::assets::list_supported_kmi()?;
kmi.iter().for_each(|kmi| println!("{kmi}"));
kmi.iter().for_each(|kmi| println!("{}", kmi));
return Ok(());
}
},
@@ -392,7 +392,7 @@ pub fn run() -> Result<()> {
};
if let Err(e) = &result {
log::error!("Error: {e:?}");
log::error!("Error: {:?}", e);
}
result
}

View File

@@ -30,7 +30,7 @@ fn set_kernel_param(uid: u32) -> Result<()> {
fn get_pkg_uid(pkg: &str) -> Result<u32> {
// stat /data/data/<pkg>
let uid = rustix::fs::stat(format!("/data/data/{pkg}"))
.with_context(|| format!("stat /data/data/{pkg}"))?
.with_context(|| format!("stat /data/data/{}", pkg))?
.st_uid;
Ok(uid)
}

View File

@@ -83,13 +83,13 @@ pub fn mount_modules_systemlessly(module_dir: &str) -> Result<()> {
// mount /system first
if let Err(e) = mount_partition("system", &system_lowerdir) {
warn!("mount system failed: {e:#}");
warn!("mount system failed: {:#}", e);
}
// mount other partitions
for (k, v) in partition_lowerdir {
if let Err(e) = mount_partition(&k, &v) {
warn!("mount {k} failed: {e:#}");
warn!("mount {k} failed: {:#}", e);
}
}
@@ -120,7 +120,7 @@ pub fn on_post_data_fs() -> Result<()> {
} else {
// Then exec common post-fs-data scripts
if let Err(e) = crate::module::exec_common_scripts("post-fs-data.d", true) {
warn!("exec common post-fs-data scripts failed: {e}");
warn!("exec common post-fs-data scripts failed: {}", e);
}
}
@@ -168,17 +168,17 @@ pub fn on_post_data_fs() -> Result<()> {
if safe_mode {
warn!("safe mode, skip post-fs-data scripts and disable all modules!");
if let Err(e) = crate::module::disable_all_modules() {
warn!("disable all modules failed: {e}");
warn!("disable all modules failed: {}", e);
}
return Ok(());
}
if let Err(e) = prune_modules() {
warn!("prune modules failed: {e}");
warn!("prune modules failed: {}", e);
}
if let Err(e) = restorecon::restorecon() {
warn!("restorecon failed: {e}");
warn!("restorecon failed: {}", e);
}
// load sepolicy.rule
@@ -187,28 +187,28 @@ pub fn on_post_data_fs() -> Result<()> {
}
if let Err(e) = crate::profile::apply_sepolies() {
warn!("apply root profile sepolicy failed: {e}");
warn!("apply root profile sepolicy failed: {}", e);
}
// mount temp dir
if let Err(e) = mount::mount_tmpfs(defs::TEMP_DIR) {
warn!("do temp dir mount failed: {e}");
warn!("do temp dir mount failed: {}", e);
}
// exec modules post-fs-data scripts
// TODO: Add timeout
if let Err(e) = crate::module::exec_stage_script("post-fs-data", true) {
warn!("exec post-fs-data scripts failed: {e}");
warn!("exec post-fs-data scripts failed: {}", e);
}
// load system.prop
if let Err(e) = crate::module::load_system_prop() {
warn!("load system.prop failed: {e}");
warn!("load system.prop failed: {}", e);
}
// mount module systemlessly by overlay
if let Err(e) = mount_modules_systemlessly(module_dir) {
warn!("do systemless mount failed: {e}");
warn!("do systemless mount failed: {}", e);
}
run_stage("post-mount", true);
@@ -298,7 +298,7 @@ fn catch_bootlog(logname: &str, command: Vec<&str>) -> Result<()> {
};
if let Err(e) = result {
warn!("Failed to start logcat: {e:#}");
warn!("Failed to start logcat: {:#}", e);
}
Ok(())

View File

@@ -268,7 +268,7 @@ pub fn prune_modules() -> Result<()> {
let uninstaller = module.join("uninstall.sh");
if uninstaller.exists() {
if let Err(e) = exec_script(uninstaller, true) {
warn!("Failed to exec uninstaller: {e}");
warn!("Failed to exec uninstaller: {}", e);
}
}
@@ -341,7 +341,7 @@ fn _install_module(zip: &str) -> Result<()> {
module_prop.insert(k, v);
},
)?;
info!("module prop: {module_prop:?}");
info!("module prop: {:?}", module_prop);
let Some(module_id) = module_prop.get("id") else {
bail!("module id not found in module.prop!");
@@ -440,13 +440,13 @@ fn _install_module(zip: &str) -> Result<()> {
let _dontdrop = mount::AutoMountExt4::try_new(tmp_module_img, module_update_tmp_dir, true)?;
info!("mounted {tmp_module_img} to {module_update_tmp_dir}");
info!("mounted {} to {}", tmp_module_img, module_update_tmp_dir);
setsyscon(module_update_tmp_dir)?;
let module_dir = format!("{module_update_tmp_dir}/{module_id}");
ensure_clean_dir(&module_dir)?;
info!("module dir: {module_dir}");
info!("module dir: {}", module_dir);
// unzip the image and move it to modules_update/<id> dir
let file = File::open(zip)?;
@@ -584,7 +584,7 @@ pub fn uninstall_module(id: &str) -> Result<()> {
}
pub fn run_action(id: &str) -> Result<()> {
let action_script_path = format!("/data/adb/modules/{id}/action.sh");
let action_script_path = format!("/data/adb/modules/{}/action.sh", id);
exec_script(&action_script_path, true)
}
@@ -674,11 +674,11 @@ fn _list_modules(path: &str) -> Vec<HashMap<String, String>> {
if !module_prop_map.contains_key("id") || module_prop_map["id"].is_empty() {
match entry.file_name().to_str() {
Some(id) => {
info!("Use dir name as module id: {id}");
info!("Use dir name as module id: {}", id);
module_prop_map.insert("id".to_owned(), id.to_owned());
}
_ => {
info!("Failed to get module id: {module_prop:?}");
info!("Failed to get module id: {:?}", module_prop);
continue;
}
}

View File

@@ -135,7 +135,7 @@ pub fn mount_overlayfs(
})();
if let Err(e) = result {
warn!("fsopen mount failed: {e:#}, fallback to mount");
warn!("fsopen mount failed: {:#}, fallback to mount", e);
let mut data = format!("lowerdir={lowerdir_config}");
if let (Some(upperdir), Some(workdir)) = (upperdir, workdir) {
data = format!("{data},upperdir={upperdir},workdir={workdir}");
@@ -225,7 +225,7 @@ fn mount_overlay_child(
}
// merge modules and stock
if let Err(e) = mount_overlayfs(&lower_dirs, stock_root, None, None, mount_point) {
warn!("failed: {e:#}, fallback to bind mount");
warn!("failed: {:#}, fallback to bind mount", e);
bind_mount(stock_root, mount_point)?;
}
Ok(())
@@ -238,7 +238,7 @@ pub fn mount_overlay(
workdir: Option<PathBuf>,
upperdir: Option<PathBuf>,
) -> Result<()> {
info!("mount overlay for {root}");
info!("mount overlay for {}", root);
std::env::set_current_dir(root).with_context(|| format!("failed to chdir to {root}"))?;
let stock_root = ".";
@@ -269,7 +269,10 @@ pub fn mount_overlay(
continue;
}
if let Err(e) = mount_overlay_child(mount_point, &relative, module_roots, &stock_root) {
warn!("failed to mount overlay for child {mount_point}: {e:#}, revert");
warn!(
"failed to mount overlay for child {}: {:#}, revert",
mount_point, e
);
umount_dir(root).with_context(|| format!("failed to revert {root}"))?;
bail!(e);
}

View File

@@ -70,9 +70,9 @@ pub fn apply_sepolies() -> Result<()> {
};
let sepolicy = sepolicy.path();
if sepolicy::apply_file(&sepolicy).is_ok() {
log::info!("profile sepolicy applied: {sepolicy:?}");
log::info!("profile sepolicy applied: {:?}", sepolicy);
} else {
log::info!("profile sepolicy apply failed: {sepolicy:?}");
log::info!("profile sepolicy apply failed: {:?}", sepolicy);
}
}
Ok(())

View File

@@ -697,7 +697,7 @@ fn apply_one_rule<'a>(statement: &'a PolicyStatement<'a>, strict: bool) -> Resul
for policy in policies {
if !rustix::process::ksu_set_policy(&FfiPolicy::from(policy)) {
log::warn!("apply rule: {statement:?} failed.");
log::warn!("apply rule: {:?} failed.", statement);
if strict {
return Err(anyhow::anyhow!("apply rule {:?} failed.", statement));
}

View File

@@ -72,7 +72,6 @@ pub fn root_shell() -> Result<()> {
#[cfg(any(target_os = "linux", target_os = "android"))]
pub fn root_shell() -> Result<()> {
// we are root now, this was set in kernel!
use anyhow::anyhow;
let env_args: Vec<String> = env::args().collect();
let program = env_args[0].clone();

View File

@@ -108,12 +108,12 @@ pub fn is_safe_mode() -> bool {
|| getprop("ro.sys.safemode")
.filter(|prop| prop == "1")
.is_some();
log::info!("safemode: {safemode}");
log::info!("safemode: {}", safemode);
if safemode {
return true;
}
let safemode = ksucalls::check_kernel_safemode();
log::info!("kernel_safemode: {safemode}");
log::info!("kernel_safemode: {}", safemode);
safemode
}
@@ -303,7 +303,7 @@ fn copy_xattrs(src_path: impl AsRef<Path>, dest_path: impl AsRef<Path>) -> Resul
if let Err(e) =
extattr::lsetxattr(dest_path.as_ref(), &xattr, &value, extattr::Flags::empty())
{
log::warn!("Failed to set xattr: {e}");
log::warn!("Failed to set xattr: {}", e);
}
}
Ok(())
@@ -336,7 +336,7 @@ pub fn copy_module_files(source: impl AsRef<Path>, destination: impl AsRef<Path>
std::fs::remove_file(&dest_path).context("Failed to remove file")?;
}
let target = std::fs::read_link(entry.path()).context("Failed to read symlink")?;
log::info!("Symlink: {dest_path:?} -> {target:?}");
log::info!("Symlink: {:?} -> {:?}", dest_path, target);
std::os::unix::fs::symlink(target, &dest_path).context("Failed to create symlink")?;
copy_xattrs(&source_path, &dest_path)?;
} else if entry.file_type().is_dir() {

View File

@@ -9,7 +9,7 @@ export default defineConfig( {
head: [
['script', {
async: 'async',
src: 'https://pagead2.googlesyndication.com/pagead/js/adsbygoogle.js?client=ca-pub-2610070972052494',
src: 'https://pagead2.googlesyndication.com/pagead/js/adsbygoogle.js?client=ca-pub-4345548567024241',
crossorigin: 'anonymous',
}],
],

View File

@@ -1 +1 @@
google.com, pub-2610070972052494, DIRECT, f08c47fec0942fa0
google.com, pub-4345548567024241, DIRECT, f08c47fec0942fa0