plugin_framework, test macos

Signed-off-by: fufesou <shuanglongchen@yeah.net>
This commit is contained in:
fufesou
2023-05-11 22:54:22 +08:00
parent 7190d451d4
commit 8a70bddd76
4 changed files with 219 additions and 108 deletions

View File

@@ -660,17 +660,17 @@ pub fn check_super_user_permission() -> ResultType<bool> {
Ok(status.success() && status.code() == Some(0))
}
pub fn elevate(arg: Vec<&str>) -> ResultType<Option<Child>> {
pub fn elevate(args: Vec<&str>) -> ResultType<Option<Child>> {
let cmd = std::env::current_exe()?;
match cmd.to_str() {
Some(cmd) => {
let mut args = vec![cmd];
args.append(&mut arg.clone());
let mut args_with_exe = vec![cmd];
args_with_exe.append(&mut args.clone());
// -E required for opensuse
if is_opensuse() {
args.insert(0, "-E");
args_with_exe.insert(0, "-E");
}
let task = Command::new("pkexec").args(args).spawn()?;
let task = Command::new("pkexec").args(args_with_exe).spawn()?;
Ok(Some(task))
}
None => {

View File

@@ -42,31 +42,45 @@ extern "C" bool InputMonitoringAuthStatus(bool prompt) {
#endif
}
extern "C" bool Elevate(char* process, char** args) {
AuthorizationRef authRef;
OSStatus status;
status = AuthorizationCreate(NULL, kAuthorizationEmptyEnvironment,
kAuthorizationFlagDefaults, &authRef);
if (status != errAuthorizationSuccess) {
printf("Failed to create AuthorizationRef\n");
return false;
}
AuthorizationItem authItem = {kAuthorizationRightExecute, 0, NULL, 0};
AuthorizationRights authRights = {1, &authItem};
AuthorizationFlags flags = kAuthorizationFlagDefaults |
kAuthorizationFlagInteractionAllowed |
kAuthorizationFlagPreAuthorize |
kAuthorizationFlagExtendRights;
status = AuthorizationCopyRights(authRef, &authRights, kAuthorizationEmptyEnvironment, flags, NULL);
if (status != errAuthorizationSuccess) {
printf("Failed to authorize\n");
return false;
}
if (process != NULL) {
FILE *pipe = NULL;
status = AuthorizationExecuteWithPrivileges(authRef, process, kAuthorizationFlagDefaults, args, &pipe);
if (status != errAuthorizationSuccess) {
printf("Failed to run as root\n");
AuthorizationFree(authRef, kAuthorizationFlagDefaults);
return false;
}
}
AuthorizationFree(authRef, kAuthorizationFlagDefaults);
return true;
}
extern "C" bool MacCheckAdminAuthorization() {
AuthorizationRef authRef;
OSStatus status;
status = AuthorizationCreate(NULL, kAuthorizationEmptyEnvironment,
kAuthorizationFlagDefaults, &authRef);
if (status != errAuthorizationSuccess) {
printf("Failed to create AuthorizationRef\n");
return false;
}
AuthorizationItem authItem = {kAuthorizationRightExecute, 0, NULL, 0};
AuthorizationRights authRights = {1, &authItem};
AuthorizationFlags flags = kAuthorizationFlagDefaults |
kAuthorizationFlagInteractionAllowed |
kAuthorizationFlagPreAuthorize |
kAuthorizationFlagExtendRights;
status = AuthorizationCopyRights(authRef, &authRights, kAuthorizationEmptyEnvironment, flags, NULL);
if (status != errAuthorizationSuccess) {
printf("Failed to authorize\n");
return false;
}
AuthorizationFree(authRef, kAuthorizationFlagDefaults);
return true;
return Elevate(NULL, NULL);
}
extern "C" float BackingScaleFactor() {

View File

@@ -17,11 +17,15 @@ use core_graphics::{
display::{kCGNullWindowID, kCGWindowListOptionOnScreenOnly, CGWindowListCopyWindowInfo},
window::{kCGWindowName, kCGWindowOwnerPID},
};
use hbb_common::{allow_err, anyhow::anyhow, bail, log, message_proto::Resolution};
use hbb_common::{allow_err, anyhow::anyhow, bail, libc, log, message_proto::Resolution};
use include_dir::{include_dir, Dir};
use objc::{class, msg_send, sel, sel_impl};
use scrap::{libc::c_void, quartz::ffi::*};
use std::path::PathBuf;
use std::{
ffi::{c_char, CString},
mem::size_of,
path::PathBuf,
};
static PRIVILEGES_SCRIPTS_DIR: Dir =
include_dir!("$CARGO_MANIFEST_DIR/src/platform/privileges_scripts");
@@ -35,6 +39,7 @@ extern "C" {
fn AXIsProcessTrustedWithOptions(options: CFDictionaryRef) -> BOOL;
fn InputMonitoringAuthStatus(_: BOOL) -> BOOL;
fn MacCheckAdminAuthorization() -> BOOL;
fn Elevate(process: *const c_char, args: *const *const c_char) -> BOOL;
fn MacGetModeNum(display: u32, numModes: *mut u32) -> BOOL;
fn MacGetModes(
display: u32,
@@ -671,3 +676,30 @@ pub fn change_resolution(name: &str, width: usize, height: usize) -> ResultType<
pub fn check_super_user_permission() -> ResultType<bool> {
unsafe { Ok(MacCheckAdminAuthorization() == YES) }
}
pub fn elevate(args: Vec<&str>) -> ResultType<bool> {
let cmd = std::env::current_exe()?;
match cmd.to_str() {
Some(cmd) => {
let cmd = CString::new(cmd)?;
let mut cstring_args = Vec::new();
for arg in args.iter() {
cstring_args.push(CString::new(*arg)?);
}
unsafe {
let args_ptr: *mut *const c_char =
libc::malloc((cstring_args.len() + 1) * size_of::<*const c_char>()) as _;
for i in 0..cstring_args.len() {
*args_ptr.add(i) = cstring_args[i].as_ptr() as _;
}
*args_ptr.add(cstring_args.len()) = std::ptr::null() as _;
let r = Elevate(cmd.as_ptr() as _, args_ptr as _);
libc::free(args_ptr as _);
Ok(r == YES)
}
}
None => {
bail!("Failed to get current exe str");
}
}
}