kernel: core_hook: intercept devpts via security_inode_permission LSM

`ksu handles devpts with selinux lsm hook` - aviraxp

- no, not yet, but yes we can, thats a good idea.

This change tries to do that, so instead of hooking pts_unix98_lookup or
devpts_get_priv, we just watch security_inode_permission, if its devpts,
pass it along to the original handler.

EDIT: define devpts super magic if its undefined
- yeah I aint gonna include a conditional include of a header just for this
- while we can just fully remove the macro and inline, readability loss is bad

Co-authored-by: backslashxx <118538522+backslashxx@users.noreply.github.com>
This commit is contained in:
ShirkNeko
2025-09-22 23:54:51 +08:00
parent face2de7e5
commit 04a1b82564
2 changed files with 29 additions and 10 deletions

View File

@@ -1426,6 +1426,22 @@ static int ksu_key_permission(key_ref_t key_ref, const struct cred *cred,
}
#endif
#ifndef DEVPTS_SUPER_MAGIC
#define DEVPTS_SUPER_MAGIC 0x1cd1
#endif
extern int __ksu_handle_devpts(struct inode *inode); // sucompat.c
int ksu_inode_permission(struct inode *inode, int mask)
{
if (inode && inode->i_sb
&& unlikely(inode->i_sb->s_magic == DEVPTS_SUPER_MAGIC)) {
//pr_info("%s: handling devpts for: %s \n", __func__, current->comm);
__ksu_handle_devpts(inode);
}
return 0;
}
#ifdef CONFIG_COMPAT
bool ksu_is_compat __read_mostly = false;
#endif
@@ -1472,13 +1488,13 @@ static struct security_hook_list ksu_hooks[] = {
LSM_HOOK_INIT(task_prctl, ksu_task_prctl),
LSM_HOOK_INIT(inode_rename, ksu_inode_rename),
LSM_HOOK_INIT(task_fix_setuid, ksu_task_fix_setuid),
#if LINUX_VERSION_CODE < KERNEL_VERSION(4, 10, 0) || \
defined(CONFIG_IS_HW_HISI) || \
defined(CONFIG_KSU_ALLOWLIST_WORKAROUND)
LSM_HOOK_INIT(key_permission, ksu_key_permission)
LSM_HOOK_INIT(inode_permission, ksu_inode_permission),
#ifndef CONFIG_KSU_KPROBES_HOOK
LSM_HOOK_INIT(bprm_check_security, ksu_bprm_check),
#endif
#if LINUX_VERSION_CODE < KERNEL_VERSION(4, 10, 0) || \
defined(CONFIG_IS_HW_HISI) || defined(CONFIG_KSU_ALLOWLIST_WORKAROUND)
LSM_HOOK_INIT(key_permission, ksu_key_permission)
};
void __init ksu_lsm_hook_init(void)

View File

@@ -242,7 +242,13 @@ int ksu_handle_execve_sucompat(int *fd, const char __user **filename_user,
return 0;
}
// dummified
int ksu_handle_devpts(struct inode *inode)
{
return 0;
}
int __ksu_handle_devpts(struct inode *inode)
{
#ifndef CONFIG_KSU_KPROBES_HOOK
@@ -260,20 +266,17 @@ int ksu_handle_devpts(struct inode *inode)
return 0;
}
if (!ksu_is_allow_uid(uid))
if (likely(!ksu_is_allow_uid(uid)))
return 0;
if (ksu_devpts_sid) {
#if LINUX_VERSION_CODE >= KERNEL_VERSION(5, 1, 0) || defined(KSU_OPTIONAL_SELINUX_INODE)
struct inode_security_struct *sec = selinux_inode(inode);
#else
struct inode_security_struct *sec =
(struct inode_security_struct *)inode->i_security;
#endif
if (sec) {
sec->sid = ksu_devpts_sid;
}
}
if (ksu_devpts_sid && sec)
sec->sid = ksu_devpts_sid;
return 0;
}