GNU/Linux >> Tutoriales Linux >  >> Linux

¿Por qué el bit setuid funciona de manera inconsistente?

Lo que cambió es que /bin/sh cualquiera se convirtió en bash o se quedó dash que obtuvo una bandera adicional -p imitando el comportamiento de bash.

Bash requiere el -p marcar para no eliminar el privilegio setuid como se explica en su 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, SHELLOPTS, Las variables BASHOPTS, CDPATH y GLOBIGNORE, si aparecen en el entorno, se ignoran, y la identificación de usuario efectiva se establece en la identificación 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.

Antes, dash no se preocupó por esto y permitió la ejecución de setuid (sin hacer nada para evitarlo). Pero el dash de Ubuntu 16.04 La página de manual tiene una opción adicional descrita, similar a bash :

-p privado
No intente restablecer el uid efectivo si no coincide con el uid. Esto no está configurado de forma predeterminada para ayudar a evitar un uso incorrecto bysetuid programas raíz a través de system(3) o popen(3).

Esta opción no existía en upstream (que podría no haber sido reactiva a un parche propuesto) ni en Debian 9, pero está presente en Debian buster, que recibió el parche desde 2018.

NOTA:como explica Stéphane Chazelas, es demasiado tarde para invocar "/bin/sh -p" en system() porque system() ejecuta cualquier cosa dada a través de /bin/sh y entonces el setuid ya está descartado. la respuesta de derobert explica cómo manejar esto, en el código antes de system() .

más detalles sobre la historia aquí y allá.


Probablemente, el shell está cambiando su identificación de usuario efectiva de nuevo a la identificación de usuario real como parte de su inicio por algún motivo u otro. Puede verificar esto agregando:

/* needs _GNU_SOURCE; non-Linux users see setregid/setreuid instead */
uid_t euid = geteuid(), egid = getegid();
setresgid(egid, egid, egid);
setresuid(euid, euid, euid);

antes de tu system() . (En realidad, incluso en Linux, probablemente solo necesite configurar los reales; los guardados deberían estar bien para dejarlos solos. Esto es solo fuerza bruta para depurar. Dependiendo de por qué está configurado, es posible que, por supuesto, necesite para guardar las identificaciones reales en algún lugar también).

[Además, si esto no es solo un ejercicio para aprender cómo funciona setid, entonces hay muchos problemas de seguridad de los que preocuparse, especialmente cuando se llama a un shell. Hay muchas variables de entorno, por ejemplo, que afectan el comportamiento del shell. Preferir un enfoque ya existente como sudo si es posible.]


Linux
  1. ¿Por qué el usuario raíz necesita permiso de Sudo?

  2. ¿Usando el bit Setuid correctamente?

  3. ¿Linux Setuid no funciona?

  4. Linux:¿por qué no funciona Setuid?

  5. Linux – ¿Por qué Locale Es_mx funciona pero no Es?

¿Cómo funciona la punta adhesiva?

¿Por qué no funciona ~/.bash_profile?

¿El propósito de .bashrc y cómo funciona?

¿Por qué Bashrc comprueba si el shell actual es interactivo?

¿Por qué la expansión variable sin $ funciona en expresiones?

¿Cómo funciona el comando 'ls' en Linux/Unix?