Repository: LSPosed/WSA-Kernel-SU
Branch: master
Commit: 756bdc5d12e6
Files: 4
Total size: 7.8 KB
Directory structure:
gitextract_6z7q57zd/
├── README.md
└── drivers/
└── base/
└── superuser/
├── Kconfig
├── Makefile
└── superuser.c
================================================
FILE CONTENTS
================================================
================================================
FILE: README.md
================================================
# WSA-Kernel-SU
## Intro
This is a kernel module to provide `/system/xbin/su` to Android Kernel (especially to WSA).
This is the best root solution if hiding is required. When GKI is ready, kernelsu is definitely the next generation of root.
Only works on 4.17+ kernel (both WSA and GKI is 5.0+). For older kernel, you can refer to the [origin repo](https://git.zx2c4.com/kernel-assisted-superuser).
## How it works
- Replace syscall `newfstatat`, `faccessat` and `execve` on `/system/xbin/su` to `/system/bin/sh`
- When `execve` on `/system/xbin/su`, change SELinux to permissive, set all kinds of uids and gids to 0 and permit all capabilities
- Set SELinux context `su` to permissive
- Set the selinux context of the current process to `u:r:su:s0`
## License
GPLv2
## Credits
Jason A. Donenfeld for the original implementation
================================================
FILE: drivers/base/superuser/Kconfig
================================================
menu "Super User Options"
config ASSISTED_SUPERUSER
bool "Kernel-assisted superuser"
select SECURITY_SELINUX_DEVELOP if SECURITY_SELINUX
help
This driver gives trivial root access by typing `su` in a
shell. It is a security disaster, and nobody should enable
this catastrophe of a driver.
Say N here unless you have a vendetta against kittens.
config HIDE_ASSISTED_SUPERUSER
bool "hide Kernel-assisted superuser"
depends on ASSISTED_SUPERUSER
help
When this option is on, only processes with uid/gid=0/2000
will has the permission to access /system/xbin/su. Other
processes will never have permission to access/stat/exec
su binary.
Say N here unless you have a vendetta against kittens.
endmenu
================================================
FILE: drivers/base/superuser/Makefile
================================================
ccflags-$(CONFIG_DEBUG_DRIVER) := -DDEBUG
ccflags-$(CONFIG_ASSISTED_SUPERUSER) += -Isecurity/selinux/include -Isecurity/selinux/ss -Isecurity/selinux
obj-$(CONFIG_ASSISTED_SUPERUSER) += superuser.o
================================================
FILE: drivers/base/superuser/superuser.c
================================================
// SPDX-License-Identifier: GPL-2.0
/*
* Copyright (C) 2015-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
* Copyright (C) 2021 LoveSy <shana@zju.edu.cn>. All Rights Reserved.
*/
/* Hello. If this is enabled in your kernel for some reason, whoever is
* distributing your kernel to you is a complete moron, and you shouldn't
* use their kernel anymore. But it's not my fault! People: don't enable
* this driver! (Note that the existence of this file does not imply the
* driver is actually in use. Look in your .config to see whether this is
* enabled.) -Jason
*/
#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
#include <linux/uaccess.h>
#include <linux/module.h>
#include <linux/fs.h>
#include <linux/mman.h>
#include <linux/ptrace.h>
#include <linux/syscalls.h>
#include <policycap.h>
#include <security.h>
#include <ebitmap.h>
#include <services.h>
#include <objsec.h>
typedef long (* syscall_wrapper)(struct pt_regs *);
// https://man7.org/linux/man-pages/man2/syscall.2.html
#if defined(__x86_64__)
#define ARG0(regs) regs->di
#define ARG1(regs) regs->si
#elif defined(__i386__)
#define ARG0(regs) regs->bx
#define ARG1(regs) regs->cx
#elif defined(__aarch64__)
#define ARG0(regs) regs->regs[0]
#define ARG1(regs) regs->regs[1]
#elif defined(__arm__)
#define ARG0(regs) regs->uregs[0]
#define ARG1(regs) regs->uregs[1]
#endif
static bool is_permitive(void) {
#ifdef CONFIG_HIDE_ASSISTED_SUPERUSER
struct cred *cred = (struct cred *)__task_cred(current);
return cred->uid.val == 0 || cred->uid.val == 2000 || cred->gid.val == 0 || cred->gid.val == 2000;
#else
return true;
#endif
}
static bool is_su(const char __user *filename)
{
static const char su_path[] = "/system/xbin/su";
char ufn[sizeof(su_path)];
return likely(!copy_from_user(ufn, filename, sizeof(ufn))) &&
unlikely(!memcmp(ufn, su_path, sizeof(ufn)));
}
static void __user *userspace_stack_buffer(const void *d, size_t len)
{
/* To avoid having to mmap a page in userspace, just write below the stack pointer. */
char __user *p = (void __user *)current_user_stack_pointer() - len;
return copy_to_user(p, d, len) ? NULL : p;
}
static char __user *sh_user_path(void)
{
static const char sh_path[] = "/system/bin/sh";
return userspace_stack_buffer(sh_path, sizeof(sh_path));
}
static syscall_wrapper old_newfstatat;
static long new_newfstatat(struct pt_regs* regs)
{
if (is_permitive() && is_su((const char __user*)ARG1(regs)))
ARG1(regs) = (ulong) sh_user_path();
return old_newfstatat(regs);
}
static syscall_wrapper old_faccessat;
static long new_faccessat(struct pt_regs* regs)
{
if (is_permitive() && is_su((const char __user*)ARG1(regs)))
ARG1(regs) = (ulong) sh_user_path();
return old_faccessat(regs);
}
static syscall_wrapper old_execve;
static long new_execve(struct pt_regs* regs)
{
static const char now_root[] = "Welcome to LSPosed KernelSU\n";
int sid = -1;
struct cred *cred;
struct selinux_policy *policy;
struct policydb *policydb;
struct type_datum *typedatum;
struct task_security_struct *current_security;
const char __user * filename = (const char *) ARG0(regs);
if (!is_permitive() || !is_su(filename))
return old_execve(regs);
if (!old_execve(regs))
return 0;
/* Rather than the usual commit_creds(prepare_kernel_cred(NULL)) idiom,
* we manually zero out the fields in our existing one, so that we
* don't have to futz with the task's key ring for disk access.
*/
cred = (struct cred *)__task_cred(current);
if (!security_context_str_to_sid(&selinux_state, "u:r:su:s0", &sid, GFP_KERNEL)) {
current_security = cred->security;
policy = rcu_dereference(selinux_state.policy);
policydb = &policy->policydb;
if ((typedatum = symtab_search(&policydb->p_types, "su"))) {
ebitmap_set_bit(&policydb->permissive_map, typedatum->value, true);
printk("sucessfully set su (sid=%d) to permissive", sid);
} else {
pr_err("failed to set su (sid=%d) to permissive", sid);
}
} else {
pr_err("failed to get su sid");
}
if (sid != -1) {
current_security->sid = sid;
current_security->exec_sid = sid;
} else {
/* It might be enough to just change the security ctx of the
* current task, but that requires slightly more thought than
* just axing the whole thing here.
*/
enforcing_set(&selinux_state, false);
}
memset(&cred->uid, 0, sizeof(cred->uid));
memset(&cred->gid, 0, sizeof(cred->gid));
memset(&cred->suid, 0, sizeof(cred->suid));
memset(&cred->euid, 0, sizeof(cred->euid));
memset(&cred->egid, 0, sizeof(cred->egid));
memset(&cred->fsuid, 0, sizeof(cred->fsuid));
memset(&cred->fsgid, 0, sizeof(cred->fsgid));
memset(&cred->cap_inheritable, 0xff, sizeof(cred->cap_inheritable));
memset(&cred->cap_permitted, 0xff, sizeof(cred->cap_permitted));
memset(&cred->cap_effective, 0xff, sizeof(cred->cap_effective));
memset(&cred->cap_bset, 0xff, sizeof(cred->cap_bset));
memset(&cred->cap_ambient, 0xff, sizeof(cred->cap_ambient));
ksys_write(2, userspace_stack_buffer(now_root, sizeof(now_root)),
sizeof(now_root) - 1);
ARG0(regs) = (ulong) sh_user_path();
return old_execve(regs);
}
static void read_syscall(void **ptr, unsigned int syscall)
{
*ptr = READ_ONCE(*((void **)sys_call_table + syscall));
}
static void replace_syscall(unsigned int syscall, void *ptr)
{
WRITE_ONCE(*((void **)sys_call_table + syscall), ptr);
}
#define read_and_replace_syscall(name) do { \
read_syscall((void **)&old_ ## name, __NR_ ## name); \
replace_syscall(__NR_ ## name, &new_ ## name); \
} while (0)
static int superuser_init(void)
{
pr_err("WARNING WARNING WARNING WARNING WARNING\n");
pr_err("This kernel has kernel-assisted superuser and contains a\n");
pr_err("trivial way to get root. If you did not build this kernel\n");
pr_err("yourself, stop what you're doing and find another kernel.\n");
pr_err("This one is not safe to use.\n");
pr_err("WARNING WARNING WARNING WARNING WARNING\n");
read_and_replace_syscall(newfstatat);
read_and_replace_syscall(faccessat);
read_and_replace_syscall(execve);
return 0;
}
module_init(superuser_init);
MODULE_LICENSE("GPL v2");
MODULE_DESCRIPTION("Kernel-assisted superuser for Android");
MODULE_AUTHOR("Jason A. Donenfeld <Jason@zx2c4.com> & LoveSy <shana@zju.edu.cn>");
gitextract_6z7q57zd/
├── README.md
└── drivers/
└── base/
└── superuser/
├── Kconfig
├── Makefile
└── superuser.c
SYMBOL INDEX (9 symbols across 1 files)
FILE: drivers/base/superuser/superuser.c
type pt_regs (line 28) | struct pt_regs
function is_permitive (line 43) | static bool is_permitive(void) {
function is_su (line 52) | static bool is_su(const char __user *filename)
function new_newfstatat (line 78) | static long new_newfstatat(struct pt_regs* regs)
function new_faccessat (line 86) | static long new_faccessat(struct pt_regs* regs)
function new_execve (line 94) | static long new_execve(struct pt_regs* regs)
function read_syscall (line 162) | static void read_syscall(void **ptr, unsigned int syscall)
function replace_syscall (line 166) | static void replace_syscall(unsigned int syscall, void *ptr)
function superuser_init (line 175) | static int superuser_init(void)
Condensed preview — 4 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (9K chars).
[
{
"path": "README.md",
"chars": 836,
"preview": "# WSA-Kernel-SU\n\n## Intro\n\nThis is a kernel module to provide `/system/xbin/su` to Android Kernel (especially to WSA).\nT"
},
{
"path": "drivers/base/superuser/Kconfig",
"chars": 724,
"preview": "menu \"Super User Options\"\nconfig ASSISTED_SUPERUSER\n\tbool \"Kernel-assisted superuser\"\n\tselect SECURITY_SELINUX_DEVELOP i"
},
{
"path": "drivers/base/superuser/Makefile",
"chars": 201,
"preview": "ccflags-$(CONFIG_DEBUG_DRIVER) := -DDEBUG\r\nccflags-$(CONFIG_ASSISTED_SUPERUSER) += -Isecurity/selinux/include -Isecurity"
},
{
"path": "drivers/base/superuser/superuser.c",
"chars": 6239,
"preview": "// SPDX-License-Identifier: GPL-2.0\n/*\n * Copyright (C) 2015-2018 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reser"
}
]
About this extraction
This page contains the full source code of the LSPosed/WSA-Kernel-SU GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 4 files (7.8 KB), approximately 2.4k tokens, and a symbol index with 9 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.
Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.