feat: Optimize some codes (ksud) (#465)
* chore: make cargo clippy happy Signed-off-by: Tools-app <localhost.hutao@gmail.com> * chore: Optimize import - Format as a standard import Signed-off-by: Tools-app <localhost.hutao@gmail.com> --------- Signed-off-by: Tools-app <localhost.hutao@gmail.com>
This commit is contained in:
74
userspace/ksud/Cargo.lock
generated
74
userspace/ksud/Cargo.lock
generated
@@ -835,6 +835,43 @@ dependencies = [
|
|||||||
"libc",
|
"libc",
|
||||||
]
|
]
|
||||||
|
|
||||||
|
[[package]]
|
||||||
|
name = "ksud"
|
||||||
|
version = "0.1.0"
|
||||||
|
dependencies = [
|
||||||
|
"android-properties",
|
||||||
|
"android_logger",
|
||||||
|
"anyhow",
|
||||||
|
"chrono",
|
||||||
|
"clap",
|
||||||
|
"const_format",
|
||||||
|
"derive-new",
|
||||||
|
"encoding_rs",
|
||||||
|
"env_logger",
|
||||||
|
"extattr",
|
||||||
|
"fs4",
|
||||||
|
"getopts",
|
||||||
|
"humansize",
|
||||||
|
"is_executable",
|
||||||
|
"java-properties",
|
||||||
|
"jwalk",
|
||||||
|
"libc",
|
||||||
|
"log",
|
||||||
|
"nom",
|
||||||
|
"notify",
|
||||||
|
"procfs",
|
||||||
|
"regex-lite",
|
||||||
|
"rust-embed",
|
||||||
|
"rustix 0.38.34",
|
||||||
|
"serde_json",
|
||||||
|
"sha1",
|
||||||
|
"sha256",
|
||||||
|
"tempfile",
|
||||||
|
"which",
|
||||||
|
"zip",
|
||||||
|
"zip-extensions",
|
||||||
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "lazy_static"
|
name = "lazy_static"
|
||||||
version = "1.5.0"
|
version = "1.5.0"
|
||||||
@@ -1837,43 +1874,6 @@ dependencies = [
|
|||||||
"lzma-sys",
|
"lzma-sys",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
|
||||||
name = "zakozako"
|
|
||||||
version = "0.1.0"
|
|
||||||
dependencies = [
|
|
||||||
"android-properties",
|
|
||||||
"android_logger",
|
|
||||||
"anyhow",
|
|
||||||
"chrono",
|
|
||||||
"clap",
|
|
||||||
"const_format",
|
|
||||||
"derive-new",
|
|
||||||
"encoding_rs",
|
|
||||||
"env_logger",
|
|
||||||
"extattr",
|
|
||||||
"fs4",
|
|
||||||
"getopts",
|
|
||||||
"humansize",
|
|
||||||
"is_executable",
|
|
||||||
"java-properties",
|
|
||||||
"jwalk",
|
|
||||||
"libc",
|
|
||||||
"log",
|
|
||||||
"nom",
|
|
||||||
"notify",
|
|
||||||
"procfs",
|
|
||||||
"regex-lite",
|
|
||||||
"rust-embed",
|
|
||||||
"rustix 0.38.34",
|
|
||||||
"serde_json",
|
|
||||||
"sha1",
|
|
||||||
"sha256",
|
|
||||||
"tempfile",
|
|
||||||
"which",
|
|
||||||
"zip",
|
|
||||||
"zip-extensions",
|
|
||||||
]
|
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "zerocopy"
|
name = "zerocopy"
|
||||||
version = "0.8.25"
|
version = "0.8.25"
|
||||||
|
|||||||
@@ -1,8 +1,4 @@
|
|||||||
use std::env;
|
use std::{env, fs::File, io::Write, path::Path, process::Command};
|
||||||
use std::fs::File;
|
|
||||||
use std::io::Write;
|
|
||||||
use std::path::Path;
|
|
||||||
use std::process::Command;
|
|
||||||
|
|
||||||
fn get_git_version() -> Result<(u32, String), std::io::Error> {
|
fn get_git_version() -> Result<(u32, String), std::io::Error> {
|
||||||
let output = Command::new("git")
|
let output = Command::new("git")
|
||||||
@@ -14,7 +10,7 @@ fn get_git_version() -> Result<(u32, String), std::io::Error> {
|
|||||||
let version_code: u32 = version_code
|
let version_code: u32 = version_code
|
||||||
.trim()
|
.trim()
|
||||||
.parse()
|
.parse()
|
||||||
.map_err(|_| std::io::Error::new(std::io::ErrorKind::Other, "Failed to parse git count"))?;
|
.map_err(|_| std::io::Error::other("Failed to parse git count"))?;
|
||||||
let version_code = 10000 + 700 + version_code; // For historical reasons
|
let version_code = 10000 + 700 + version_code; // For historical reasons
|
||||||
|
|
||||||
let version_name = String::from_utf8(
|
let version_name = String::from_utf8(
|
||||||
@@ -23,7 +19,7 @@ fn get_git_version() -> Result<(u32, String), std::io::Error> {
|
|||||||
.output()?
|
.output()?
|
||||||
.stdout,
|
.stdout,
|
||||||
)
|
)
|
||||||
.map_err(|_| std::io::Error::other("Failed to read git describe stdout"))?;
|
.map_err(|_| std::io::Error::other("Failed to parse git count"))?;
|
||||||
let version_name = version_name.trim_start_matches('v').to_string();
|
let version_name = version_name.trim_start_matches('v').to_string();
|
||||||
Ok((version_code, version_name))
|
Ok((version_code, version_name))
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,22 +1,19 @@
|
|||||||
#[cfg(unix)]
|
#[cfg(unix)]
|
||||||
use std::os::unix::fs::PermissionsExt;
|
use std::{
|
||||||
use std::path::Path;
|
os::unix::fs::PermissionsExt,
|
||||||
use std::path::PathBuf;
|
path::{Path, PathBuf},
|
||||||
use std::process::Command;
|
process::{Command, Stdio},
|
||||||
use std::process::Stdio;
|
};
|
||||||
|
|
||||||
use anyhow::Context;
|
use anyhow::{Context, Result, anyhow, bail, ensure};
|
||||||
use anyhow::Result;
|
|
||||||
use anyhow::anyhow;
|
|
||||||
use anyhow::bail;
|
|
||||||
use anyhow::ensure;
|
|
||||||
use regex_lite::Regex;
|
use regex_lite::Regex;
|
||||||
use which::which;
|
use which::which;
|
||||||
|
|
||||||
use crate::defs;
|
use crate::{
|
||||||
use crate::defs::BACKUP_FILENAME;
|
assets,
|
||||||
use crate::defs::{KSU_BACKUP_DIR, KSU_BACKUP_FILE_PREFIX};
|
defs::{self, BACKUP_FILENAME, KSU_BACKUP_DIR, KSU_BACKUP_FILE_PREFIX},
|
||||||
use crate::{assets, utils};
|
utils,
|
||||||
|
};
|
||||||
|
|
||||||
#[cfg(target_os = "android")]
|
#[cfg(target_os = "android")]
|
||||||
fn ensure_gki_kernel() -> Result<()> {
|
fn ensure_gki_kernel() -> Result<()> {
|
||||||
@@ -118,11 +115,11 @@ fn parse_kmi_from_kernel(kernel: &PathBuf, workdir: &Path) -> Result<String> {
|
|||||||
let re =
|
let re =
|
||||||
Regex::new(r"(?:.* )?(\d+\.\d+)(?:\S+)?(android\d+)").context("Failed to compile regex")?;
|
Regex::new(r"(?:.* )?(\d+\.\d+)(?:\S+)?(android\d+)").context("Failed to compile regex")?;
|
||||||
for s in printable_strings {
|
for s in printable_strings {
|
||||||
if let Some(caps) = re.captures(s) {
|
if let Some(caps) = re.captures(s)
|
||||||
if let (Some(kernel_version), Some(android_version)) = (caps.get(1), caps.get(2)) {
|
&& let (Some(kernel_version), Some(android_version)) = (caps.get(1), caps.get(2))
|
||||||
let kmi = format!("{}-{}", android_version.as_str(), kernel_version.as_str());
|
{
|
||||||
return Ok(kmi);
|
let kmi = format!("{}-{}", android_version.as_str(), kernel_version.as_str());
|
||||||
}
|
return Ok(kmi);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
println!("- Failed to get KMI version");
|
println!("- Failed to get KMI version");
|
||||||
@@ -711,10 +708,8 @@ fn do_patch(
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(target_os = "android")]
|
#[cfg(target_os = "android")]
|
||||||
if need_backup {
|
if need_backup && let Err(e) = do_backup(&magiskboot, workdir, &bootimage) {
|
||||||
if let Err(e) = do_backup(&magiskboot, workdir, &bootimage) {
|
println!("- Backup stock image failed: {e}");
|
||||||
println!("- Backup stock image failed: {e}");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
println!("- Repacking boot image");
|
println!("- Repacking boot image");
|
||||||
@@ -951,16 +946,15 @@ fn find_boot_image(
|
|||||||
&& !is_replace_kernel
|
&& !is_replace_kernel
|
||||||
&& vendor_boot_exist
|
&& vendor_boot_exist
|
||||||
&& !skip_init
|
&& !skip_init
|
||||||
{
|
&& unpack_and_check_init(
|
||||||
if unpack_and_check_init(
|
|
||||||
magiskboot,
|
magiskboot,
|
||||||
workdir,
|
workdir,
|
||||||
&vendor_boot_partition,
|
&vendor_boot_partition,
|
||||||
"vendor_ramdisk/init_boot.cpio",
|
"vendor_ramdisk/init_boot.cpio",
|
||||||
)? {
|
)?
|
||||||
println!("- Using vendor_boot partition (vendor_ramdisk/init_boot.cpio).");
|
{
|
||||||
selected_partition = &vendor_boot_partition;
|
println!("- Using vendor_boot partition (vendor_ramdisk/init_boot.cpio).");
|
||||||
}
|
selected_partition = &vendor_boot_partition;
|
||||||
}
|
}
|
||||||
|
|
||||||
// try vendor_boot/vendor_ramdisk/ramdisk.cpio
|
// try vendor_boot/vendor_ramdisk/ramdisk.cpio
|
||||||
@@ -968,16 +962,15 @@ fn find_boot_image(
|
|||||||
&& !is_replace_kernel
|
&& !is_replace_kernel
|
||||||
&& vendor_boot_exist
|
&& vendor_boot_exist
|
||||||
&& !skip_init
|
&& !skip_init
|
||||||
{
|
&& unpack_and_check_init(
|
||||||
if unpack_and_check_init(
|
|
||||||
magiskboot,
|
magiskboot,
|
||||||
workdir,
|
workdir,
|
||||||
&vendor_boot_partition,
|
&vendor_boot_partition,
|
||||||
"vendor_ramdisk/ramdisk.cpio",
|
"vendor_ramdisk/ramdisk.cpio",
|
||||||
)? {
|
)?
|
||||||
println!("- Using vendor_boot partition (vendor_ramdisk/ramdisk.cpio).");
|
{
|
||||||
selected_partition = &vendor_boot_partition;
|
println!("- Using vendor_boot partition (vendor_ramdisk/ramdisk.cpio).");
|
||||||
}
|
selected_partition = &vendor_boot_partition;
|
||||||
}
|
}
|
||||||
|
|
||||||
if selected_partition == &boot_partition {
|
if selected_partition == &boot_partition {
|
||||||
|
|||||||
@@ -7,8 +7,9 @@ use android_logger::Config;
|
|||||||
#[cfg(target_os = "android")]
|
#[cfg(target_os = "android")]
|
||||||
use log::LevelFilter;
|
use log::LevelFilter;
|
||||||
|
|
||||||
use crate::defs::KSUD_VERBOSE_LOG_FILE;
|
use crate::{
|
||||||
use crate::{apk_sign, assets, debug, defs, init_event, ksucalls, module, utils};
|
apk_sign, assets, debug, defs, defs::KSUD_VERBOSE_LOG_FILE, init_event, ksucalls, module, utils,
|
||||||
|
};
|
||||||
|
|
||||||
/// KernelSU userspace cli
|
/// KernelSU userspace cli
|
||||||
#[derive(Parser, Debug)]
|
#[derive(Parser, Debug)]
|
||||||
@@ -288,10 +289,7 @@ mod kpm_cmd {
|
|||||||
#[derive(Subcommand, Debug)]
|
#[derive(Subcommand, Debug)]
|
||||||
pub enum Kpm {
|
pub enum Kpm {
|
||||||
/// Load a KPM module: load <path> [args]
|
/// Load a KPM module: load <path> [args]
|
||||||
Load {
|
Load { path: PathBuf, args: Option<String> },
|
||||||
path: PathBuf,
|
|
||||||
args: Option<String>,
|
|
||||||
},
|
|
||||||
/// Unload a KPM module: unload <name>
|
/// Unload a KPM module: unload <name>
|
||||||
Unload { name: String },
|
Unload { name: String },
|
||||||
/// Get number of loaded modules
|
/// Get number of loaded modules
|
||||||
@@ -420,7 +418,9 @@ pub fn run() -> Result<()> {
|
|||||||
Commands::Kpm { command } => {
|
Commands::Kpm { command } => {
|
||||||
use crate::cli::kpm_cmd::Kpm;
|
use crate::cli::kpm_cmd::Kpm;
|
||||||
match command {
|
match command {
|
||||||
Kpm::Load { path, args } => crate::kpm::kpm_load(path.to_str().unwrap(), args.as_deref()),
|
Kpm::Load { path, args } => {
|
||||||
|
crate::kpm::kpm_load(path.to_str().unwrap(), args.as_deref())
|
||||||
|
}
|
||||||
Kpm::Unload { name } => crate::kpm::kpm_unload(&name),
|
Kpm::Unload { name } => crate::kpm::kpm_unload(&name),
|
||||||
Kpm::Num => crate::kpm::kpm_num().map(|_| ()),
|
Kpm::Num => crate::kpm::kpm_num().map(|_| ()),
|
||||||
Kpm::List => crate::kpm::kpm_list(),
|
Kpm::List => crate::kpm::kpm_list(),
|
||||||
|
|||||||
@@ -1,12 +1,16 @@
|
|||||||
use crate::defs::{KSU_MOUNT_SOURCE, NO_MOUNT_PATH, NO_TMPFS_PATH};
|
#[cfg(target_arch = "aarch64")]
|
||||||
use crate::module::{handle_updated_modules, prune_modules};
|
use crate::kpm;
|
||||||
use crate::{assets, defs, ksucalls, restorecon, utils, uid_scanner};
|
use crate::{
|
||||||
|
assets, defs,
|
||||||
|
defs::{KSU_MOUNT_SOURCE, NO_MOUNT_PATH, NO_TMPFS_PATH},
|
||||||
|
ksucalls,
|
||||||
|
module::{handle_updated_modules, prune_modules},
|
||||||
|
restorecon, uid_scanner, utils,
|
||||||
|
};
|
||||||
use anyhow::{Context, Result};
|
use anyhow::{Context, Result};
|
||||||
use log::{info, warn};
|
use log::{info, warn};
|
||||||
use rustix::fs::{MountFlags, mount};
|
use rustix::fs::{MountFlags, mount};
|
||||||
use std::path::Path;
|
use std::path::Path;
|
||||||
#[cfg(target_arch = "aarch64")]
|
|
||||||
use crate::kpm;
|
|
||||||
|
|
||||||
pub fn on_post_data_fs() -> Result<()> {
|
pub fn on_post_data_fs() -> Result<()> {
|
||||||
ksucalls::report_post_fs_data();
|
ksucalls::report_post_fs_data();
|
||||||
@@ -118,23 +122,21 @@ pub fn on_post_data_fs() -> Result<()> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Disable Samsung Activation Verify
|
// Disable Samsung Activation Verify
|
||||||
if let Some(model) = utils::getprop("ro.product.model") {
|
if let Some(model) = utils::getprop("ro.product.model")
|
||||||
if model.starts_with("SM-") {
|
&& model.starts_with("SM-")
|
||||||
info!("Disable Samsung Activation for model {}", model);
|
{
|
||||||
if Path::new("/system/app/ActivationDevice_V2").exists() {
|
info!("Disable Samsung Activation for model {}", model);
|
||||||
if let Err(e) = std::fs::create_dir_all("/data/local/tmp/ActivationDevice_V2") {
|
if Path::new("/system/app/ActivationDevice_V2").exists() {
|
||||||
warn!("Failed to create directory: {}", e);
|
if let Err(e) = std::fs::create_dir_all("/data/local/tmp/ActivationDevice_V2") {
|
||||||
} else {
|
warn!("Failed to create directory: {}", e);
|
||||||
if let Err(e) = mount(
|
} else if let Err(e) = mount(
|
||||||
"/data/local/tmp/ActivationDevice_V2",
|
"/data/local/tmp/ActivationDevice_V2",
|
||||||
"/system/app/ActivationDevice_V2",
|
"/system/app/ActivationDevice_V2",
|
||||||
"none",
|
"none",
|
||||||
MountFlags::BIND,
|
MountFlags::BIND,
|
||||||
"",
|
"",
|
||||||
) {
|
) {
|
||||||
warn!("Failed to mount ActivationDevice_V2: {}", e);
|
warn!("Failed to mount ActivationDevice_V2: {}", e);
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,11 +1,11 @@
|
|||||||
use anyhow::{anyhow, bail, Result};
|
use anyhow::{Result, anyhow, bail};
|
||||||
use libc::{c_int, c_ulong, prctl};
|
use libc::{c_int, c_ulong, prctl};
|
||||||
use notify::{RecursiveMode, Watcher};
|
use notify::{RecursiveMode, Watcher};
|
||||||
use std::{
|
use std::{
|
||||||
ffi::{CStr, CString, OsStr},
|
ffi::{CStr, CString, OsStr},
|
||||||
path::{Path, PathBuf},
|
|
||||||
os::unix::fs::PermissionsExt,
|
|
||||||
fs,
|
fs,
|
||||||
|
os::unix::fs::PermissionsExt,
|
||||||
|
path::{Path, PathBuf},
|
||||||
ptr,
|
ptr,
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -13,13 +13,13 @@ pub const KPM_DIR: &str = "/data/adb/kpm";
|
|||||||
|
|
||||||
// SukiSU KPM prctl command space
|
// SukiSU KPM prctl command space
|
||||||
const KSU_OPTIONS: c_int = 0xdeadbeef_u32 as c_int;
|
const KSU_OPTIONS: c_int = 0xdeadbeef_u32 as c_int;
|
||||||
const SUKISU_KPM_LOAD: c_int = 28;
|
const SUKISU_KPM_LOAD: c_int = 28;
|
||||||
const SUKISU_KPM_UNLOAD: c_int = 29;
|
const SUKISU_KPM_UNLOAD: c_int = 29;
|
||||||
const SUKISU_KPM_NUM: c_int = 30;
|
const SUKISU_KPM_NUM: c_int = 30;
|
||||||
const SUKISU_KPM_LIST: c_int = 31;
|
const SUKISU_KPM_LIST: c_int = 31;
|
||||||
const SUKISU_KPM_INFO: c_int = 32;
|
const SUKISU_KPM_INFO: c_int = 32;
|
||||||
const SUKISU_KPM_CONTROL:c_int = 33;
|
const SUKISU_KPM_CONTROL: c_int = 33;
|
||||||
const SUKISU_KPM_VERSION:c_int = 34;
|
const SUKISU_KPM_VERSION: c_int = 34;
|
||||||
|
|
||||||
/// Convert raw kernel return code to `Result`.
|
/// Convert raw kernel return code to `Result`.
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
@@ -56,7 +56,13 @@ pub fn kpm_unload(name: &str) -> Result<()> {
|
|||||||
let name_c = CString::new(name)?;
|
let name_c = CString::new(name)?;
|
||||||
let mut rc = -1;
|
let mut rc = -1;
|
||||||
unsafe {
|
unsafe {
|
||||||
prctl(KSU_OPTIONS, SUKISU_KPM_UNLOAD, name_c.as_ptr() as c_ulong, 0, &mut rc as *mut _ as c_ulong);
|
prctl(
|
||||||
|
KSU_OPTIONS,
|
||||||
|
SUKISU_KPM_UNLOAD,
|
||||||
|
name_c.as_ptr() as c_ulong,
|
||||||
|
0,
|
||||||
|
&mut rc as *mut _ as c_ulong,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
check_out(rc)?;
|
check_out(rc)?;
|
||||||
Ok(())
|
Ok(())
|
||||||
@@ -65,7 +71,15 @@ pub fn kpm_unload(name: &str) -> Result<()> {
|
|||||||
/// Return loaded module count.
|
/// Return loaded module count.
|
||||||
pub fn kpm_num() -> Result<i32> {
|
pub fn kpm_num() -> Result<i32> {
|
||||||
let mut rc = -1;
|
let mut rc = -1;
|
||||||
unsafe { prctl(KSU_OPTIONS, SUKISU_KPM_NUM, 0, 0, &mut rc as *mut _ as c_ulong) };
|
unsafe {
|
||||||
|
prctl(
|
||||||
|
KSU_OPTIONS,
|
||||||
|
SUKISU_KPM_NUM,
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
&mut rc as *mut _ as c_ulong,
|
||||||
|
)
|
||||||
|
};
|
||||||
let n = check_out(rc)?;
|
let n = check_out(rc)?;
|
||||||
println!("{n}");
|
println!("{n}");
|
||||||
Ok(n)
|
Ok(n)
|
||||||
@@ -122,7 +136,7 @@ pub fn kpm_control(name: &str, args: &str) -> Result<i32> {
|
|||||||
&mut rc as *mut _ as c_ulong,
|
&mut rc as *mut _ as c_ulong,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
check_out(rc).map(|v| v as i32)
|
check_out(rc)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Print loader version string.
|
/// Print loader version string.
|
||||||
@@ -243,12 +257,11 @@ pub fn remove_all_kpms() -> Result<()> {
|
|||||||
}
|
}
|
||||||
for entry in fs::read_dir(dir)? {
|
for entry in fs::read_dir(dir)? {
|
||||||
let p = entry?.path();
|
let p = entry?.path();
|
||||||
if p.extension() == Some(OsStr::new("kpm")) {
|
if p.extension() == Some(OsStr::new("kpm"))
|
||||||
if let Some(name) = p.file_stem().and_then(|s| s.to_str()) {
|
&& let Some(name) = p.file_stem().and_then(|s| s.to_str())
|
||||||
if let Err(e) = unload_kpm(name) {
|
&& let Err(e) = unload_kpm(name)
|
||||||
log::error!("KPM: unload {name} failed: {e}");
|
{
|
||||||
}
|
log::error!("KPM: unload {name} failed: {e}");
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Ok(())
|
Ok(())
|
||||||
@@ -282,5 +295,9 @@ pub fn load_kpm_modules() -> Result<()> {
|
|||||||
/// Convert zero-padded kernel buffer to owned String.
|
/// Convert zero-padded kernel buffer to owned String.
|
||||||
fn buf2str(buf: &[u8]) -> String {
|
fn buf2str(buf: &[u8]) -> String {
|
||||||
// SAFETY: buffer is always NUL-terminated by kernel.
|
// SAFETY: buffer is always NUL-terminated by kernel.
|
||||||
unsafe { CStr::from_ptr(buf.as_ptr().cast()).to_string_lossy().into_owned() }
|
unsafe {
|
||||||
|
CStr::from_ptr(buf.as_ptr().cast())
|
||||||
|
.to_string_lossy()
|
||||||
|
.into_owned()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -1,22 +1,28 @@
|
|||||||
use crate::defs::{DISABLE_FILE_NAME, KSU_MOUNT_SOURCE, MODULE_DIR, SKIP_MOUNT_FILE_NAME};
|
use std::{
|
||||||
use crate::magic_mount::NodeFileType::{Directory, RegularFile, Symlink, Whiteout};
|
cmp::PartialEq,
|
||||||
use crate::restorecon::{lgetfilecon, lsetfilecon};
|
collections::{HashMap, hash_map::Entry},
|
||||||
use crate::utils::{ensure_dir_exists, get_work_dir};
|
fs::{self, DirEntry, FileType, create_dir, create_dir_all, read_dir, read_link},
|
||||||
|
os::unix::fs::{FileTypeExt, symlink},
|
||||||
|
path::{Path, PathBuf},
|
||||||
|
};
|
||||||
|
|
||||||
use anyhow::{Context, Result, bail};
|
use anyhow::{Context, Result, bail};
|
||||||
use extattr::lgetxattr;
|
use extattr::lgetxattr;
|
||||||
use rustix::fs::{
|
use rustix::{
|
||||||
Gid, MetadataExt, Mode, MountFlags, MountPropagationFlags, Uid, UnmountFlags, bind_mount,
|
fs::{
|
||||||
chmod, chown, mount, move_mount, remount, unmount,
|
Gid, MetadataExt, Mode, MountFlags, MountPropagationFlags, Uid, UnmountFlags, bind_mount,
|
||||||
|
chmod, chown, mount, move_mount, remount, unmount,
|
||||||
|
},
|
||||||
|
mount::mount_change,
|
||||||
|
path::Arg,
|
||||||
|
};
|
||||||
|
|
||||||
|
use crate::{
|
||||||
|
defs::{DISABLE_FILE_NAME, KSU_MOUNT_SOURCE, MODULE_DIR, SKIP_MOUNT_FILE_NAME},
|
||||||
|
magic_mount::NodeFileType::{Directory, RegularFile, Symlink, Whiteout},
|
||||||
|
restorecon::{lgetfilecon, lsetfilecon},
|
||||||
|
utils::{ensure_dir_exists, get_work_dir},
|
||||||
};
|
};
|
||||||
use rustix::mount::mount_change;
|
|
||||||
use rustix::path::Arg;
|
|
||||||
use std::cmp::PartialEq;
|
|
||||||
use std::collections::HashMap;
|
|
||||||
use std::collections::hash_map::Entry;
|
|
||||||
use std::fs;
|
|
||||||
use std::fs::{DirEntry, FileType, create_dir, create_dir_all, read_dir, read_link};
|
|
||||||
use std::os::unix::fs::{FileTypeExt, symlink};
|
|
||||||
use std::path::{Path, PathBuf};
|
|
||||||
|
|
||||||
const REPLACE_DIR_XATTR: &str = "trusted.overlay.opaque";
|
const REPLACE_DIR_XATTR: &str = "trusted.overlay.opaque";
|
||||||
|
|
||||||
@@ -98,12 +104,11 @@ impl Node {
|
|||||||
};
|
};
|
||||||
if let Some(file_type) = file_type {
|
if let Some(file_type) = file_type {
|
||||||
let mut replace = false;
|
let mut replace = false;
|
||||||
if file_type == Directory {
|
if file_type == Directory
|
||||||
if let Ok(v) = lgetxattr(&path, REPLACE_DIR_XATTR) {
|
&& let Ok(v) = lgetxattr(&path, REPLACE_DIR_XATTR)
|
||||||
if String::from_utf8_lossy(&v) == "y" {
|
&& String::from_utf8_lossy(&v) == "y"
|
||||||
replace = true;
|
{
|
||||||
}
|
replace = true;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return Some(Node {
|
return Some(Node {
|
||||||
name: name.to_string(),
|
name: name.to_string(),
|
||||||
|
|||||||
@@ -5,6 +5,8 @@ mod cli;
|
|||||||
mod debug;
|
mod debug;
|
||||||
mod defs;
|
mod defs;
|
||||||
mod init_event;
|
mod init_event;
|
||||||
|
#[cfg(target_arch = "aarch64")]
|
||||||
|
mod kpm;
|
||||||
mod ksucalls;
|
mod ksucalls;
|
||||||
#[cfg(target_os = "android")]
|
#[cfg(target_os = "android")]
|
||||||
mod magic_mount;
|
mod magic_mount;
|
||||||
@@ -13,10 +15,8 @@ mod profile;
|
|||||||
mod restorecon;
|
mod restorecon;
|
||||||
mod sepolicy;
|
mod sepolicy;
|
||||||
mod su;
|
mod su;
|
||||||
mod utils;
|
|
||||||
mod uid_scanner;
|
mod uid_scanner;
|
||||||
#[cfg(target_arch = "aarch64")]
|
mod utils;
|
||||||
mod kpm;
|
|
||||||
|
|
||||||
fn main() -> anyhow::Result<()> {
|
fn main() -> anyhow::Result<()> {
|
||||||
cli::run()
|
cli::run()
|
||||||
|
|||||||
@@ -1,18 +1,6 @@
|
|||||||
#[allow(clippy::wildcard_imports)]
|
|
||||||
use crate::utils::*;
|
|
||||||
use crate::{
|
|
||||||
assets, defs, ksucalls,
|
|
||||||
restorecon::{restore_syscon, setsyscon},
|
|
||||||
sepolicy,
|
|
||||||
};
|
|
||||||
|
|
||||||
use anyhow::{Context, Result, anyhow, bail, ensure};
|
|
||||||
use const_format::concatcp;
|
|
||||||
use is_executable::is_executable;
|
|
||||||
use java_properties::PropertiesIter;
|
|
||||||
use log::{info, warn};
|
|
||||||
|
|
||||||
use std::fs::{copy, rename};
|
use std::fs::{copy, rename};
|
||||||
|
#[cfg(unix)]
|
||||||
|
use std::os::unix::{prelude::PermissionsExt, process::CommandExt};
|
||||||
use std::{
|
use std::{
|
||||||
collections::HashMap,
|
collections::HashMap,
|
||||||
env::var as env_var,
|
env::var as env_var,
|
||||||
@@ -22,11 +10,23 @@ use std::{
|
|||||||
process::Command,
|
process::Command,
|
||||||
str::FromStr,
|
str::FromStr,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
use anyhow::{Context, Result, anyhow, bail, ensure};
|
||||||
|
use const_format::concatcp;
|
||||||
|
use is_executable::is_executable;
|
||||||
|
use java_properties::PropertiesIter;
|
||||||
|
use log::{info, warn};
|
||||||
use zip_extensions::zip_extract_file_to_memory;
|
use zip_extensions::zip_extract_file_to_memory;
|
||||||
|
|
||||||
use crate::defs::{MODULE_DIR, MODULE_UPDATE_DIR, UPDATE_FILE_NAME};
|
#[allow(clippy::wildcard_imports)]
|
||||||
#[cfg(unix)]
|
use crate::{
|
||||||
use std::os::unix::{prelude::PermissionsExt, process::CommandExt};
|
assets,
|
||||||
|
defs::{self, MODULE_DIR, MODULE_UPDATE_DIR, UPDATE_FILE_NAME},
|
||||||
|
ksucalls,
|
||||||
|
restorecon::{restore_syscon, setsyscon},
|
||||||
|
sepolicy,
|
||||||
|
utils::*,
|
||||||
|
};
|
||||||
|
|
||||||
const INSTALLER_CONTENT: &str = include_str!("./installer.sh");
|
const INSTALLER_CONTENT: &str = include_str!("./installer.sh");
|
||||||
const INSTALL_MODULE_SCRIPT: &str = concatcp!(
|
const INSTALL_MODULE_SCRIPT: &str = concatcp!(
|
||||||
@@ -256,10 +256,10 @@ pub fn prune_modules() -> Result<()> {
|
|||||||
info!("remove module: {}", module.display());
|
info!("remove module: {}", module.display());
|
||||||
|
|
||||||
let uninstaller = module.join("uninstall.sh");
|
let uninstaller = module.join("uninstall.sh");
|
||||||
if uninstaller.exists() {
|
if uninstaller.exists()
|
||||||
if let Err(e) = exec_script(uninstaller, true) {
|
&& let Err(e) = exec_script(uninstaller, true)
|
||||||
warn!("Failed to exec uninstaller: {}", e);
|
{
|
||||||
}
|
warn!("Failed to exec uninstaller: {}", e);
|
||||||
}
|
}
|
||||||
|
|
||||||
if let Err(e) = remove_dir_all(module) {
|
if let Err(e) = remove_dir_all(module) {
|
||||||
@@ -283,10 +283,10 @@ pub fn handle_updated_modules() -> Result<()> {
|
|||||||
|
|
||||||
if let Some(name) = module.file_name() {
|
if let Some(name) = module.file_name() {
|
||||||
let old_dir = modules_root.join(name);
|
let old_dir = modules_root.join(name);
|
||||||
if old_dir.exists() {
|
if old_dir.exists()
|
||||||
if let Err(e) = remove_dir_all(&old_dir) {
|
&& let Err(e) = remove_dir_all(&old_dir)
|
||||||
log::error!("Failed to remove old {}: {}", old_dir.display(), e);
|
{
|
||||||
}
|
log::error!("Failed to remove old {}: {}", old_dir.display(), e);
|
||||||
}
|
}
|
||||||
if let Err(e) = rename(module, &old_dir) {
|
if let Err(e) = rename(module, &old_dir) {
|
||||||
log::error!("Failed to move new module {}: {}", module.display(), e);
|
log::error!("Failed to move new module {}: {}", module.display(), e);
|
||||||
|
|||||||
@@ -1,8 +1,9 @@
|
|||||||
use crate::utils::ensure_dir_exists;
|
|
||||||
use crate::{defs, sepolicy};
|
|
||||||
use anyhow::{Context, Result};
|
|
||||||
use std::path::Path;
|
use std::path::Path;
|
||||||
|
|
||||||
|
use anyhow::{Context, Result};
|
||||||
|
|
||||||
|
use crate::{defs, sepolicy, utils::ensure_dir_exists};
|
||||||
|
|
||||||
pub fn set_sepolicy(pkg: String, policy: String) -> Result<()> {
|
pub fn set_sepolicy(pkg: String, policy: String) -> Result<()> {
|
||||||
ensure_dir_exists(defs::PROFILE_SELINUX_DIR)?;
|
ensure_dir_exists(defs::PROFILE_SELINUX_DIR)?;
|
||||||
let policy_file = Path::new(defs::PROFILE_SELINUX_DIR).join(pkg);
|
let policy_file = Path::new(defs::PROFILE_SELINUX_DIR).join(pkg);
|
||||||
|
|||||||
@@ -1,12 +1,13 @@
|
|||||||
use crate::defs;
|
|
||||||
use anyhow::Result;
|
|
||||||
use jwalk::{Parallelism::Serial, WalkDir};
|
|
||||||
use std::path::Path;
|
use std::path::Path;
|
||||||
|
|
||||||
|
use anyhow::Result;
|
||||||
#[cfg(any(target_os = "linux", target_os = "android"))]
|
#[cfg(any(target_os = "linux", target_os = "android"))]
|
||||||
use anyhow::{Context, Ok};
|
use anyhow::{Context, Ok};
|
||||||
#[cfg(any(target_os = "linux", target_os = "android"))]
|
#[cfg(any(target_os = "linux", target_os = "android"))]
|
||||||
use extattr::{Flags as XattrFlags, lsetxattr};
|
use extattr::{Flags as XattrFlags, lsetxattr};
|
||||||
|
use jwalk::{Parallelism::Serial, WalkDir};
|
||||||
|
|
||||||
|
use crate::defs;
|
||||||
|
|
||||||
pub const SYSTEM_CON: &str = "u:object_r:system_file:s0";
|
pub const SYSTEM_CON: &str = "u:object_r:system_file:s0";
|
||||||
pub const ADB_CON: &str = "u:object_r:adb_data_file:s0";
|
pub const ADB_CON: &str = "u:object_r:adb_data_file:s0";
|
||||||
@@ -63,12 +64,11 @@ pub fn restore_syscon<P: AsRef<Path>>(dir: P) -> Result<()> {
|
|||||||
|
|
||||||
fn restore_modules_con<P: AsRef<Path>>(dir: P) -> Result<()> {
|
fn restore_modules_con<P: AsRef<Path>>(dir: P) -> Result<()> {
|
||||||
for dir_entry in WalkDir::new(dir).parallelism(Serial) {
|
for dir_entry in WalkDir::new(dir).parallelism(Serial) {
|
||||||
if let Some(path) = dir_entry.ok().map(|dir_entry| dir_entry.path()) {
|
if let Some(path) = dir_entry.ok().map(|dir_entry| dir_entry.path())
|
||||||
if let Result::Ok(con) = lgetfilecon(&path) {
|
&& let Result::Ok(con) = lgetfilecon(&path)
|
||||||
if con == ADB_CON || con == UNLABEL_CON || con.is_empty() {
|
&& (con == ADB_CON || con == UNLABEL_CON || con.is_empty())
|
||||||
lsetfilecon(&path, SYSTEM_CON)?;
|
{
|
||||||
}
|
lsetfilecon(&path, SYSTEM_CON)?;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Ok(())
|
Ok(())
|
||||||
|
|||||||
@@ -1,3 +1,5 @@
|
|||||||
|
use std::{ffi, path::Path, vec};
|
||||||
|
|
||||||
use anyhow::{Result, bail};
|
use anyhow::{Result, bail};
|
||||||
use derive_new::new;
|
use derive_new::new;
|
||||||
use nom::{
|
use nom::{
|
||||||
@@ -7,7 +9,6 @@ use nom::{
|
|||||||
character::complete::{space0, space1},
|
character::complete::{space0, space1},
|
||||||
combinator::map,
|
combinator::map,
|
||||||
};
|
};
|
||||||
use std::{ffi, path::Path, vec};
|
|
||||||
|
|
||||||
type SeObject<'a> = Vec<&'a str>;
|
type SeObject<'a> = Vec<&'a str>;
|
||||||
|
|
||||||
|
|||||||
@@ -1,22 +1,20 @@
|
|||||||
use anyhow::{Ok, Result};
|
|
||||||
use getopts::Options;
|
|
||||||
use std::env;
|
|
||||||
#[cfg(unix)]
|
#[cfg(unix)]
|
||||||
use std::os::unix::process::CommandExt;
|
use std::os::unix::process::CommandExt;
|
||||||
use std::path::PathBuf;
|
use std::{env, ffi::CStr, path::PathBuf, process::Command};
|
||||||
use std::{ffi::CStr, process::Command};
|
|
||||||
|
|
||||||
use crate::{
|
|
||||||
defs,
|
|
||||||
utils::{self, umask},
|
|
||||||
};
|
|
||||||
|
|
||||||
|
use anyhow::{Ok, Result};
|
||||||
|
use getopts::Options;
|
||||||
#[cfg(any(target_os = "linux", target_os = "android"))]
|
#[cfg(any(target_os = "linux", target_os = "android"))]
|
||||||
use rustix::{
|
use rustix::{
|
||||||
process::getuid,
|
process::getuid,
|
||||||
thread::{Gid, Uid, set_thread_res_gid, set_thread_res_uid},
|
thread::{Gid, Uid, set_thread_res_gid, set_thread_res_uid},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
use crate::{
|
||||||
|
defs,
|
||||||
|
utils::{self, umask},
|
||||||
|
};
|
||||||
|
|
||||||
#[cfg(any(target_os = "linux", target_os = "android"))]
|
#[cfg(any(target_os = "linux", target_os = "android"))]
|
||||||
pub fn grant_root(global_mnt: bool) -> Result<()> {
|
pub fn grant_root(global_mnt: bool) -> Result<()> {
|
||||||
rustix::process::ksu_grant_root()?;
|
rustix::process::ksu_grant_root()?;
|
||||||
|
|||||||
@@ -1,16 +1,17 @@
|
|||||||
use anyhow::Result;
|
|
||||||
use log::{info, warn};
|
|
||||||
use std::{
|
use std::{
|
||||||
fs,
|
fs,
|
||||||
io::Write,
|
io::Write,
|
||||||
os::unix::{
|
os::unix::{
|
||||||
fs::{symlink, PermissionsExt},
|
fs::{PermissionsExt, symlink},
|
||||||
process::CommandExt,
|
process::CommandExt,
|
||||||
},
|
},
|
||||||
path::Path,
|
path::Path,
|
||||||
process::{Command, Stdio},
|
process::{Command, Stdio},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
use anyhow::Result;
|
||||||
|
use log::{info, warn};
|
||||||
|
|
||||||
pub fn start_uid_scanner_daemon() -> Result<()> {
|
pub fn start_uid_scanner_daemon() -> Result<()> {
|
||||||
const SCANNER_PATH: &str = "/data/adb/uid_scanner";
|
const SCANNER_PATH: &str = "/data/adb/uid_scanner";
|
||||||
const LINK_DIR: &str = "/data/adb/ksu/bin";
|
const LINK_DIR: &str = "/data/adb/ksu/bin";
|
||||||
|
|||||||
@@ -1,28 +1,25 @@
|
|||||||
use anyhow::{Context, Error, Ok, Result, bail};
|
#[cfg(unix)]
|
||||||
|
use std::os::unix::prelude::PermissionsExt;
|
||||||
use std::{
|
use std::{
|
||||||
fs::{self, File, OpenOptions, create_dir_all, remove_file, write},
|
fs::{self, File, OpenOptions, create_dir_all, remove_file, write},
|
||||||
|
fs::{Permissions, set_permissions},
|
||||||
io::{
|
io::{
|
||||||
ErrorKind::{AlreadyExists, NotFound},
|
ErrorKind::{AlreadyExists, NotFound},
|
||||||
Write,
|
Write,
|
||||||
},
|
},
|
||||||
path::Path,
|
path::{Path, PathBuf},
|
||||||
process::Command,
|
process::Command,
|
||||||
};
|
};
|
||||||
|
|
||||||
use crate::{assets, boot_patch, defs, ksucalls, module, restorecon};
|
use anyhow::{Context, Error, Ok, Result, bail};
|
||||||
#[allow(unused_imports)]
|
|
||||||
use std::fs::{Permissions, set_permissions};
|
|
||||||
#[cfg(unix)]
|
|
||||||
use std::os::unix::prelude::PermissionsExt;
|
|
||||||
|
|
||||||
use std::path::PathBuf;
|
|
||||||
|
|
||||||
#[cfg(any(target_os = "linux", target_os = "android"))]
|
#[cfg(any(target_os = "linux", target_os = "android"))]
|
||||||
use rustix::{
|
use rustix::{
|
||||||
process,
|
process,
|
||||||
thread::{LinkNameSpaceType, move_into_link_name_space},
|
thread::{LinkNameSpaceType, move_into_link_name_space},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
use crate::{assets, boot_patch, defs, ksucalls, module, restorecon};
|
||||||
|
|
||||||
pub fn ensure_clean_dir(dir: impl AsRef<Path>) -> Result<()> {
|
pub fn ensure_clean_dir(dir: impl AsRef<Path>) -> Result<()> {
|
||||||
let path = dir.as_ref();
|
let path = dir.as_ref();
|
||||||
log::debug!("ensure_clean_dir: {}", path.display());
|
log::debug!("ensure_clean_dir: {}", path.display());
|
||||||
@@ -74,11 +71,11 @@ pub fn ensure_binary<T: AsRef<Path>>(
|
|||||||
)
|
)
|
||||||
})?)?;
|
})?)?;
|
||||||
|
|
||||||
if let Err(e) = remove_file(path.as_ref()) {
|
if let Err(e) = remove_file(path.as_ref())
|
||||||
if e.kind() != NotFound {
|
&& e.kind() != NotFound
|
||||||
return Err(Error::from(e))
|
{
|
||||||
.with_context(|| format!("failed to unlink {}", path.as_ref().display()));
|
return Err(Error::from(e))
|
||||||
}
|
.with_context(|| format!("failed to unlink {}", path.as_ref().display()));
|
||||||
}
|
}
|
||||||
|
|
||||||
write(&path, contents)?;
|
write(&path, contents)?;
|
||||||
|
|||||||
Reference in New Issue
Block a user