¿Invocar un script con ld-linux.so?

¿Invocar un script con ld-linux.so?

Acabo de descargar un tararchivo que se supone incluye todo lo necesario para ejecutar un programa al que podemos llamar some_binary. Extraje su contenido y veo lo siguiente:

  • Un binario (llamémoslo some_binary)
  • Una libcarpeta con varias bibliotecas dinámicas (archivos .so) como/lib/ld-linux-x86-64.so
  • y un script de shell llamadosome_binary.sh

El guión tiene el siguiente contenido:

#!/bin/bash
`dirname "$0"`/lib/ld-linux-x86-64.so.2   `dirname "$0"`/some_binary "$@"

y ejecutarlo como ./some_binary.sh some argumentsparece funcionar ./some_binarycorrectamente. Por extraño que parezca, ejecuta el siguiente script:

#!/bin/bash
LD_LIBRARY_PATH=$CWD/LIB:$LD_LIBRARY_PATH
./some_binary "$@"

como ./my_script.sh some argumentsno funciona. Da como resultado errores de reubicación (símbolos indefinidos), presumiblemente por cargar incorrectamente las bibliotecas en./lib

Además, ejecutar las dos declaraciones siguientes desde la línea de comando da como resultado segmentation fault:

> LD_LIBRARY_PATH=$CWD/LIB:$LD_LIBRARY_PATH
> ./some_binary some arguments

Con esto, mis preguntas son:

  1. ¿Qué hace el primer guión?
  2. ¿Por qué obtengo resultados diferentes en estos tres intentos? ¿Y por qué no puedo simplemente agregar $pwd/liby LD_LIBRARY_PATHluego ejecutar some_binarydirectamente?

Respuesta1

El programa viene con su propiocargador dinámico. Es bastante raro que los programas necesiten su propio cargador dinámico: normalmente el de su sistema también funcionará. Esto puede ser necesario si el programa se vinculó a una biblioteca estándar que no sea GNU libc o si se vinculó a una libc GNU compilada con configuraciones extrañas.

Puede ser suficiente decirle al cargador dónde encontrar las bibliotecas preferidas del programa. Tu intento casi logra eso, pero no del todo. Si LD_LIBRARY_PATHaún no está en el entorno, entonces la asignación LD_LIBRARY_PATH=$CWD/LIB:$LD_LIBRARY_PATHsolo define una variable de shell, no una variable de entorno, por lo que el programa no ve nada. Además, $CWDgeneralmente se expande a la cadena vacía, probablemente quiso decir $PWDo mejor $(dirname "$0")(es decir, el directorio que contiene el script). También tenga en cuenta que utilizó liby LIBde manera inconsistente en su pregunta. Intentar

#!/bin/sh
export LD_LIBRARY_PATH="$(dirname "$0")/lib:$LD_LIBRARY_PATH"
exec "$(dirname "$0")/some_binary" "$@"

o mejor, para evitar tener una entrada vacía al final LD_LIBRARY_PATHsi no se definió antes (esto puede ser malo porque una entrada vacía representa el directorio actual, aunque al final de la ruta solo es perjudicial si hay una biblioteca). No se encuentra donde debería estar):

#!/bin/sh
export LD_LIBRARY_PATH="$(dirname "$0")/lib:$LD_LIBRARY_PATH"
case "$LD_LIBRARY_PATH" in *:) LD_LIBRARY_PATH=${LD_LIBRARY_PATH%:};; esac
exec "$(dirname "$0")/some_binary" "$@"

información relacionada