mirror of
https://github.com/topjohnwu/Magisk.git
synced 2025-10-27 15:20:58 +00:00
Migrate setup_magisk_env to Rust
This commit is contained in:
@@ -18,7 +18,6 @@ use std::fmt::Display;
|
||||
use std::fs::File;
|
||||
use std::io::{BufRead, BufReader, Read, Seek, SeekFrom, Write};
|
||||
use std::mem::MaybeUninit;
|
||||
use std::ops::Deref;
|
||||
use std::os::fd::{AsFd, BorrowedFd};
|
||||
use std::os::unix::ffi::OsStrExt;
|
||||
use std::os::unix::io::{AsRawFd, OwnedFd, RawFd};
|
||||
@@ -307,17 +306,12 @@ impl Utf8CStr {
|
||||
|
||||
pub fn set_attr<'a>(&'a self, attr: &'a FileAttr) -> OsResult<'a, ()> {
|
||||
if !attr.is_symlink()
|
||||
&& let Err(e) = nix::sys::stat::fchmodat(
|
||||
AT_FDCWD,
|
||||
self,
|
||||
Mode::from_bits_truncate((attr.st.st_mode & 0o777).as_()),
|
||||
FchmodatFlags::FollowSymlink,
|
||||
)
|
||||
&& let Err(e) = self.follow_link().chmod((attr.st.st_mode & 0o777).as_())
|
||||
{
|
||||
// Double check if self is symlink before reporting error
|
||||
let self_attr = self.get_attr()?;
|
||||
if !self_attr.is_symlink() {
|
||||
return Err(OsError::new(e, "chmod", Some(self), None));
|
||||
return Err(e);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -521,13 +515,27 @@ impl Utf8CStr {
|
||||
|
||||
impl FsPathFollow {
|
||||
pub fn exists(&self) -> bool {
|
||||
nix::unistd::access(self.deref(), AccessFlags::F_OK).is_ok()
|
||||
nix::unistd::access(self.as_utf8_cstr(), AccessFlags::F_OK).is_ok()
|
||||
}
|
||||
|
||||
pub fn chmod(&self, mode: mode_t) -> OsResult<'_, ()> {
|
||||
nix::sys::stat::fchmodat(
|
||||
AT_FDCWD,
|
||||
self.as_utf8_cstr(),
|
||||
Mode::from_bits_truncate(mode),
|
||||
FchmodatFlags::FollowSymlink,
|
||||
)
|
||||
.check_os_err("chmod", Some(self), None)
|
||||
}
|
||||
|
||||
pub fn get_attr(&self) -> OsResult<'_, FileAttr> {
|
||||
#[allow(unused_mut)]
|
||||
let mut attr = FileAttr {
|
||||
st: nix::sys::stat::stat(self.deref()).into_os_result("lstat", Some(self), None)?,
|
||||
st: nix::sys::stat::stat(self.as_utf8_cstr()).into_os_result(
|
||||
"lstat",
|
||||
Some(self),
|
||||
None,
|
||||
)?,
|
||||
#[cfg(feature = "selinux")]
|
||||
con: cstr::buf::new(),
|
||||
};
|
||||
@@ -537,16 +545,10 @@ impl FsPathFollow {
|
||||
}
|
||||
|
||||
pub fn set_attr<'a>(&'a self, attr: &'a FileAttr) -> OsResult<'a, ()> {
|
||||
nix::sys::stat::fchmodat(
|
||||
AT_FDCWD,
|
||||
self.deref(),
|
||||
Mode::from_bits_truncate((attr.st.st_mode & 0o777).as_()),
|
||||
FchmodatFlags::FollowSymlink,
|
||||
)
|
||||
.check_os_err("chmod", Some(self), None)?;
|
||||
self.chmod((attr.st.st_mode & 0o777).as_())?;
|
||||
|
||||
nix::unistd::chown(
|
||||
self.deref(),
|
||||
self.as_utf8_cstr(),
|
||||
Some(Uid::from(attr.st.st_uid)),
|
||||
Some(Gid::from(attr.st.st_gid)),
|
||||
)
|
||||
|
||||
@@ -214,53 +214,6 @@ int connect_daemon(int req, bool create) {
|
||||
return fd;
|
||||
}
|
||||
|
||||
bool setup_magisk_env() {
|
||||
char buf[4096];
|
||||
|
||||
LOGI("* Initializing Magisk environment\n");
|
||||
|
||||
ssprintf(buf, sizeof(buf), "%s/0/%s/install", APP_DATA_DIR, JAVA_PACKAGE_NAME);
|
||||
// Alternative binaries paths
|
||||
const char *alt_bin[] = { "/cache/data_adb/magisk", "/data/magisk", buf };
|
||||
for (auto alt : alt_bin) {
|
||||
if (access(alt, F_OK) == 0) {
|
||||
rm_rf(DATABIN);
|
||||
cp_afc(alt, DATABIN);
|
||||
rm_rf(alt);
|
||||
}
|
||||
}
|
||||
rm_rf("/cache/data_adb");
|
||||
|
||||
// Directories in /data/adb
|
||||
chmod(SECURE_DIR, 0700);
|
||||
xmkdir(DATABIN, 0755);
|
||||
xmkdir(MODULEROOT, 0755);
|
||||
xmkdir(SECURE_DIR "/post-fs-data.d", 0755);
|
||||
xmkdir(SECURE_DIR "/service.d", 0755);
|
||||
restorecon();
|
||||
|
||||
if (access(DATABIN "/busybox", X_OK))
|
||||
return false;
|
||||
|
||||
ssprintf(buf, sizeof(buf), "%s/" BBPATH "/busybox", get_magisk_tmp());
|
||||
mkdir(dirname(buf), 0755);
|
||||
cp_afc(DATABIN "/busybox", buf);
|
||||
exec_command_async(buf, "--install", "-s", dirname(buf));
|
||||
|
||||
// magisk32 and magiskpolicy are not installed into ramdisk and has to be copied
|
||||
// from data to magisk tmp
|
||||
if (access(DATABIN "/magisk32", X_OK) == 0) {
|
||||
ssprintf(buf, sizeof(buf), "%s/magisk32", get_magisk_tmp());
|
||||
cp_afc(DATABIN "/magisk32", buf);
|
||||
}
|
||||
if (access(DATABIN "/magiskpolicy", X_OK) == 0) {
|
||||
ssprintf(buf, sizeof(buf), "%s/magiskpolicy", get_magisk_tmp());
|
||||
cp_afc(DATABIN "/magiskpolicy", buf);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void unlock_blocks() {
|
||||
int fd, dev, OFF = 0;
|
||||
|
||||
|
||||
@@ -1,19 +1,19 @@
|
||||
use crate::UCred;
|
||||
use crate::consts::{
|
||||
MAGISK_FULL_VER, MAGISK_PROC_CON, MAGISK_VER_CODE, MAGISK_VERSION, MAIN_CONFIG, ROOTMNT,
|
||||
ROOTOVL, SECURE_DIR,
|
||||
APP_PACKAGE_NAME, BBPATH, DATABIN, MAGISK_FULL_VER, MAGISK_PROC_CON, MAGISK_VER_CODE,
|
||||
MAGISK_VERSION, MAIN_CONFIG, MODULEROOT, ROOTMNT, ROOTOVL, SECURE_DIR,
|
||||
};
|
||||
use crate::db::Sqlite3;
|
||||
use crate::ffi::{
|
||||
DbEntryKey, ModuleInfo, RequestCode, check_key_combo, denylist_handler, exec_common_scripts,
|
||||
exec_module_scripts, get_magisk_tmp, initialize_denylist, scan_deny_apps, setup_magisk_env,
|
||||
exec_module_scripts, get_magisk_tmp, initialize_denylist, scan_deny_apps,
|
||||
};
|
||||
use crate::logging::{android_logging, magisk_logging, setup_logfile, start_log_daemon};
|
||||
use crate::module::{disable_modules, remove_modules};
|
||||
use crate::mount::{clean_mounts, setup_preinit_dir};
|
||||
use crate::package::ManagerInfo;
|
||||
use crate::resetprop::{get_prop, set_prop};
|
||||
use crate::selinux::restore_tmpcon;
|
||||
use crate::selinux::{restore_tmpcon, restorecon};
|
||||
use crate::socket::IpcWrite;
|
||||
use crate::su::SuInfo;
|
||||
use crate::zygisk::ZygiskState;
|
||||
@@ -32,7 +32,7 @@ use std::fmt::Write as FmtWrite;
|
||||
use std::fs::File;
|
||||
use std::io::{BufReader, Write};
|
||||
use std::os::fd::{AsFd, FromRawFd, IntoRawFd, OwnedFd};
|
||||
use std::process::{Command, exit};
|
||||
use std::process::{Command, Stdio, exit};
|
||||
use std::sync::atomic::{AtomicBool, Ordering};
|
||||
use std::sync::{Mutex, OnceLock};
|
||||
|
||||
@@ -106,6 +106,83 @@ impl MagiskD {
|
||||
}
|
||||
}
|
||||
|
||||
fn setup_magisk_env(&self) -> bool {
|
||||
info!("* Initializing Magisk environment");
|
||||
|
||||
let mut buf = cstr::buf::default();
|
||||
|
||||
let app_bin_dir = buf
|
||||
.append_path(self.app_data_dir())
|
||||
.append_path("0")
|
||||
.append_path(APP_PACKAGE_NAME)
|
||||
.append_path("install");
|
||||
|
||||
// Alternative binaries paths
|
||||
let alt_bin_dirs = &[
|
||||
cstr!("/cache/data_adb/magisk"),
|
||||
cstr!("/data/magisk"),
|
||||
app_bin_dir,
|
||||
];
|
||||
for dir in alt_bin_dirs {
|
||||
if dir.exists() {
|
||||
cstr!(DATABIN).remove_all().ok();
|
||||
dir.copy_to(cstr!(DATABIN)).ok();
|
||||
dir.remove_all().ok();
|
||||
}
|
||||
}
|
||||
cstr!("/cache/data_adb").remove_all().ok();
|
||||
|
||||
// Directories in /data/adb
|
||||
cstr!(SECURE_DIR).follow_link().chmod(0o700).log_ok();
|
||||
cstr!(DATABIN).mkdir(0o755).log_ok();
|
||||
cstr!(MODULEROOT).mkdir(0o755).log_ok();
|
||||
cstr!(concatcp!(SECURE_DIR, "/post-fs-data.d"))
|
||||
.mkdir(0o755)
|
||||
.log_ok();
|
||||
cstr!(concatcp!(SECURE_DIR, "/service.d"))
|
||||
.mkdir(0o755)
|
||||
.log_ok();
|
||||
restorecon();
|
||||
|
||||
let busybox = cstr!(concatcp!(DATABIN, "/busybox"));
|
||||
if !busybox.exists() {
|
||||
return false;
|
||||
}
|
||||
|
||||
let tmp_bb = buf.append_path(get_magisk_tmp()).append_path(BBPATH);
|
||||
tmp_bb.mkdirs(0o755).ok();
|
||||
tmp_bb.append_path("busybox");
|
||||
tmp_bb.follow_link().chmod(0o755).log_ok();
|
||||
busybox.copy_to(tmp_bb).ok();
|
||||
|
||||
// Install busybox applets
|
||||
Command::new(&tmp_bb)
|
||||
.arg("--install")
|
||||
.arg("-s")
|
||||
.arg(tmp_bb.parent_dir().unwrap())
|
||||
.stdout(Stdio::null())
|
||||
.stderr(Stdio::null())
|
||||
.status()
|
||||
.log_ok();
|
||||
|
||||
// magisk32 and magiskpolicy are not installed into ramdisk and has to be copied
|
||||
// from data to magisk tmp
|
||||
let magisk32 = cstr!(concatcp!(DATABIN, "/magisk32"));
|
||||
if magisk32.exists() {
|
||||
let tmp = buf.append_path(get_magisk_tmp()).append_path("magisk32");
|
||||
magisk32.copy_to(tmp).log_ok();
|
||||
}
|
||||
let magiskpolicy = cstr!(concatcp!(DATABIN, "/magiskpolicy"));
|
||||
if magiskpolicy.exists() {
|
||||
let tmp = buf
|
||||
.append_path(get_magisk_tmp())
|
||||
.append_path("magiskpolicy");
|
||||
magiskpolicy.copy_to(tmp).log_ok();
|
||||
}
|
||||
|
||||
true
|
||||
}
|
||||
|
||||
fn post_fs_data(&self) -> bool {
|
||||
setup_logfile();
|
||||
info!("** post-fs-data mode running");
|
||||
@@ -125,7 +202,7 @@ impl MagiskD {
|
||||
|
||||
self.prune_su_access();
|
||||
|
||||
if !setup_magisk_env() {
|
||||
if !self.setup_magisk_env() {
|
||||
error!("* Magisk environment incomplete, abort");
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -37,7 +37,6 @@ struct ModuleInfo;
|
||||
int connect_daemon(int req, bool create = false);
|
||||
const char *get_magisk_tmp();
|
||||
void unlock_blocks();
|
||||
bool setup_magisk_env();
|
||||
bool check_key_combo();
|
||||
|
||||
template<typename T> requires(std::is_trivially_copyable_v<T>)
|
||||
|
||||
@@ -137,7 +137,6 @@ pub mod ffi {
|
||||
fn get_magisk_tmp() -> Utf8CStrRef<'static>;
|
||||
#[cxx_name = "resolve_preinit_dir_rs"]
|
||||
fn resolve_preinit_dir(base_dir: Utf8CStrRef) -> String;
|
||||
fn setup_magisk_env() -> bool;
|
||||
fn check_key_combo() -> bool;
|
||||
#[cxx_name = "exec_script_rs"]
|
||||
fn exec_script(script: Utf8CStrRef);
|
||||
|
||||
@@ -25,6 +25,7 @@ pub const MAIN_CONFIG: &str = concatcp!(INTERNAL_DIR, "/config");
|
||||
pub const PREINITMIRR: &str = concatcp!(INTERNAL_DIR, "/preinit");
|
||||
pub const MODULEMNT: &str = concatcp!(INTERNAL_DIR, "/modules");
|
||||
pub const WORKERDIR: &str = concatcp!(INTERNAL_DIR, "/worker");
|
||||
pub const BBPATH: &str = concatcp!(INTERNAL_DIR, "/busybox");
|
||||
pub const DEVICEDIR: &str = concatcp!(INTERNAL_DIR, "/device");
|
||||
pub const PREINITDEV: &str = concatcp!(DEVICEDIR, "/preinit");
|
||||
pub const LOG_PIPE: &str = concatcp!(DEVICEDIR, "/log");
|
||||
|
||||
Reference in New Issue
Block a user