¿Por qué el uso de la acción '-execdir' es inseguro para el directorio que está en la RUTA?


19

¿Por qué es inseguro usar la combinación de -execdiracción de encontrar mientras se usa -execno lo es?

Cuando ejecuto el siguiente comando, recibo el siguiente mensaje de aviso:

/path/to/currentDir/$ find . -type f -name 'partOfFileNames*' -execdir rm -- {} +

find: The current directory is included in the PATH environment variable, which is insecure 
in combination with the -execdir action of find.  Please remove the current directory 
from your $PATH (that is, remove "." or leading or trailing colons)

¿Qué puede causar que aparezca este aviso?

Respuestas:


22

Podría ejecutar el programa incorrecto. Alguien podría hacerte ejecutar su programa.

La -execdiracción ejecuta su comando desde el directorio que contiene los archivos encontrados. Cuando $PATHcontiene rutas relativas, como .o cualquier cosa que no comience/ , no -execdires seguro porque un directorio donde se encuentra un archivo (u otro directorio resuelto en relación con él) también podría contener un ejecutable con el mismo nombre que el que está intentando correr. Ese ejecutable potencialmente no confiable se ejecutaría en su lugar.

Esto podría ser explotado deliberadamente por otro usuario para que ejecute su programa, lo que podría causar daños o vulnerar la seguridad de los datos, en lugar del programa que está intentando ejecutar. O, con menos frecuencia, podría simplemente resultar en la ejecución inadvertida del programa incorrecto, incluso sin que nadie intente solucionar el problema.

Si todo en su PATHvariable de entorno es una ruta absoluta, no debería ocurrir este error, incluso si el directorio que está buscando y -execdiring del que se contenida en PATH. (He comprobado que esto funciona). Si cree que no tiene ningún directorio relativo $PATHpero aún recibe este error, actualice su pregunta con detalles que incluyan la salida de echo "$PATH".

Un ejemplo concreto

Como ejemplo de lo que podría salir mal, suponga:

  • Alice tiene .en ella $PATHporque quiere poder ejecutar programas en cualquier directorio que quiera cd, sin molestarse en anteponer sus nombres ./.
  • La enemiga frenemy de Alice ha compartido /home/eve/sharedcon Alice.
  • Alice quiere estadísticas (líneas, palabras, bytes) en los .carchivos que Eve ha compartido con ella.

Entonces Alice corre:

find ~eve/shared -name \*.c -execdir wc {} \;

Desafortunadamente para Alice, Eve creó su propio script, lo nombró wc, lo configuró como ejecutable ( chmod +x) y lo colocó clandestinamente en uno de los directorios debajo /home/eve/shared. El guión de Eve se ve así:

#!/bin/sh
/usr/bin/wc "$@"
do_evil    # Eve replaces this command with whatver evil she wishes to do

Entonces, cuando Alice usa findcon -execdirpara ejecutarse wcen los archivos que Eve ha compartido, y llega a los archivos en el mismo directorio que el wcscript personalizado de Eve, Eve wcejecuta, ¡con todos los privilegios de Alice!

(Siendo astuta, Eve ha hecho que su wcguión actúe como una envoltura para el sistema wc, por lo que Alice ni siquiera sabrá que algo salió mal, es decir, que do_evilse ejecutó. Sin embargo, son posibles variaciones más simples y también más sofisticadas. )

Cómo findpreviene esto.

findevita que ocurra este problema de seguridad al negarse a tomar la -execdiracción cuando $PATHcontiene un directorio relativo.

find ofrece dos mensajes de diagnóstico según la situación específica.

  • Si .está adentro $PATH, entonces (como has visto) dice:

    find: The current directory is included in the PATH environment variable, which is insecure in combination with the -execdir action of find. Please remove the current directory from your $PATH (that is, remove "." or leading or trailing colons)

    Probablemente tiene un mensaje especial para el .caso, ya que es especialmente común.

  • Si .aparece una ruta relativa distinta de - dice, foo- $PATHy usted corre findcon -execdir, dice:

    find: The relative path `foo' is included in the PATH environment variable, which is insecure in combination with the -execdir action of find. Please remove that entry from $PATH

Es mejor no tener caminos relativos en $PATHabsoluto.

El riesgo de tener .u otras rutas relativas $PATHse incrementa especialmente cuando se usa una utilidad que cambia automáticamente el directorio, por findlo que no le permitirá usar -execdiren esta situación.

Pero tener caminos relativos, especialmente ., en su $PATHes inherentemente arriesgado y es mejor evitarlo de todos modos. Considere la situación ficticia en el ejemplo anterior. Supongamos que en lugar de correr find, Alice simplemente cdes para ~eve/shared/blahy se ejecuta wc *.c. Si blahcontiene el wcguión de Eve , do_evilcorre como Alice.


2
No sé si has escuchado esto antes que
serías

55
@heemayl todos aquellos que escriben cosas útiles en la red, ya son maestros :-)
Ciro Santilli 新疆 改造 中心 法轮功 六四 事件

5

Hay una información muy detallada aquí . Otra excelente referencia está aquí . Para citar de la primera referencia:

La opción -execdir es una opción más moderna introducida en GNU find es un intento de crear una versión más segura de -exec. Tiene la misma semántica que -exec con dos mejoras importantes:

Siempre proporciona una ruta absoluta al archivo (usar la ruta relativa a un archivo es realmente peligroso en el caso de -exec).

Además de proporcionar una ruta absoluta, también verifica la seguridad de la variable PATH (si el punto está presente en la variable PATH env, puede recoger el ejecutable del directorio incorrecto)

De la segunda referencia:

La acción '-execdir' se niega a hacer nada si el directorio actual está incluido en la variable de entorno $ PATH. Esto es necesario porque '-execdir' ejecuta programas en el mismo directorio en el que encuentra archivos; en general, dicho directorio podría ser escrito por usuarios no confiables. Por razones similares, '-execdir' no permite que aparezca '{}' en el nombre del comando que se ejecutará.


¿Puede extender su respuesta por qué "si el punto está presente en la variable PATH env, puede recoger el ejecutable del directorio incorrecto" ? el cual directorio incorrecto ? ¿Y por qué tenemos que hacer esto para hacerlo seguro ? Gracias
αғsнιη

Espero que el segundo enlace en mi publicación actualizada responda su pregunta
Ron

3

El principal problema es con el valor de la variable del sistema PATHque contiene carpetas relativas, por lo que, por razones de seguridad, el findcomando no le permitirá ejecutar archivos binarios, porque potencialmente puede ejecutar programas incorrectos.


Entonces, por ejemplo, si tiene su directorio actual en su RUTA según la advertencia que obtiene:

El directorio actual se incluye en la variable de entorno PATH.

y ejecutarás tu comando:

find . -type f -name 'partOfFileNames*' -execdir rm -- {} +

en caso de que tenga un script local ( rmcon indicadores ejecutables) que lo contenga rm -fr /, puede eliminar todos sus archivos, porque en lugar de ejecutar lo esperado /bin/rm, ejecutará rmdesde el directorio actual, por lo que probablemente no sea lo que deseaba.


Como nota al margen, este es un problema conocido en Travis CI ( GH # 2811 ) cuando falla con el error:

find: la ruta relativa `./node_modules/.bin 'se incluye en la variable de entorno PATH, que es insegura en combinación con la acción -execdir de find. Elimina esa entrada de $ PATH

Entonces, la solución es eliminar la entrada afectada de la variable PATH, por ejemplo

PATH=`echo $PATH | sed -e 's/:\.\/node_modules\/\.bin//'`

según lo propuesto por drogus . El progreso de este error se puede seguir en GH # 4862 .


Aquí está la solución alternativa de la versión Bash:

PATH=${PATH//:\.\/node_modules\/\.bin/}

Ejemplo de uso (paso filtrado PATHa comando específico):

env PATH=${PATH//:\.\/node_modules\/\.bin/} find . -type f

Aquí hay una sedque parece eliminar todo lo que findno le gusta: askubuntu.com/questions/621132/…
Ciro Santilli 新疆 改造 中心 法轮功 六四 事件

3

xargsy bash -c cdsolución

Esta bien me rindo:

find . -type f |
  xargs -I '{}' bash -c 'cd "$(dirname "{}")" && pwd && echo "$(basename "{}")"'

sed solución alterna

Un poco menos agradable que la solución anterior:

PATH="$(echo "$PATH" | sed -E 's/(^|:)[^\/][^:]*//g')" find . -execdir echo '{}' \;

Un caso de prueba:

[ "$(printf '/a/b::c/d:/e/f\n' | sed -E 's/(^|:)[^\/][^:]*//g')" = '/a/b:/e/f' ] || echo fail

Para renameconcreto, también se puede evitar con un poco de Perl expresiones regulares-fu: /programming/16541582/finding-multiple-files-recursively-and-renaming-in-linux/54163971#54163971

RTFS esperanza aplastante

Para aquellos que tienen la esperanza de que exista una forma de ignorar findla opinión de los demás, permítanme aclararlo con alguna fuente:

A partir de eso, vemos que parece que no hay forma de desactivar la comprobación de ruta.

La regla exacta que verifica es: falla si PATHestá vacío o no comienza /.

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.