tutorial que online modo instalar español debuggear debug como linux gdb system-calls strace

linux - que - gdb break cuando el programa abre un archivo específico



instalar gdb en ubuntu (3)

Como dijo André Puel:

break open if strcmp($rdi,"/dev/urandom") == 0

Podría hacer el trabajo

Historia posterior: al ejecutar un programa bajo strace me doy cuenta de que ''/ dev / urandom'' se está open ''ed. Me gustaría saber de dónde viene esta llamada (no es parte del programa en sí, es parte del sistema).

Entonces, al usar gdb, estoy intentando interrumpir (usando catch syscall open ) cuando se catch syscall open la llamada open , así puedo ver un retroceso. El problema es que open se llama mucho , como cientos de veces, así que no puedo limitar la llamada específica que está abriendo / dev / urandom. ¿Cómo debo ir para reducir la llamada específica? ¿Hay una manera de filtrar por argumentos, y si es así, cómo lo hago para una syscall?

Cualquier consejo sería útil, tal vez me esté yendo mal.


GDB es una herramienta bastante poderosa, pero tiene una pequeña curva de aprendizaje.

Básicamente, desea configurar un punto de interrupción condicional.

Primero use la marca -i para forzar u objdump -d para encontrar la dirección de la función abierta o, de manera más realista, algo en la cadena de llegar allí, como en el plt.

establezca un punto de interrupción en esa dirección (si tiene símbolos de depuración, puede usarlos en su lugar, omitiendo el *, pero supongo que no, aunque es posible que los tenga para las funciones de la biblioteca, si no es otra cosa.

break * 0x080482c8

A continuación hay que hacerlo condicional.

(Lo ideal sería comparar un argumento de cadena con una cadena deseada. No estaba logrando que esto funcionara en los primeros minutos de intentarlo)

Esperemos que podamos asumir que la cadena es una constante en algún lugar del programa o en una de las bibliotecas que carga. Puede buscar en / proc / pid / maps para tener una idea de qué está cargado y dónde, luego usar grep para verificar que la cadena está realmente en un archivo, objdump -s para encontrar su dirección, y gdb para verificar que ha en realidad lo encontré en la memoria al combinar la parte alta de la dirección de los mapas con la parte baja del archivo. (EDITAR: probablemente sea más fácil usar ldd en el ejecutable que buscar en / proc / pid / maps)

A continuación, necesitará saber algo sobre el abi de la plataforma en la que está trabajando, específicamente sobre cómo se pasan los argumentos. Últimamente he estado trabajando en arm''s, y eso es muy bueno ya que los primeros argumentos solo van en los registros r0, r1, r2 ... etc. x86 es un poco menos conveniente, parece que van en la pila, es decir, * ($ esp + 4), * ($ esp + 8), * ($ esp + 12).

Así que asumamos que estamos en un x86, y queremos comprobar que el primer argumento en esp + 4 es igual a la dirección que encontramos para la constante que intentamos atrapar. Sólo, esp + 4 es un puntero a un puntero de carácter. Así que tenemos que desreferirlo para la comparación.

cond 1 *(char **)($esp+4)==0x8048514

Entonces puedes escribir correr y esperar lo mejor.

Si detecta su condición de punto de interrupción, y mirar a su alrededor con los registros de información y el comando x para examinar la memoria parece correcto, entonces puede usar el comando de retorno para filtrar la pila de llamadas hasta que encuentre algo que reconozca.


(Adaptado de una edición de pregunta)

Siguiendo la respuesta de Chris , aquí está el proceso que finalmente me dio lo que estaba buscando:

(Estoy tratando de encontrar qué funciones están llamando al syscall open en "/ dev / urandom")

  1. usa ldd en el ejecutable para encontrar las bibliotecas cargadas
  2. grep través de cada lib (comando de shell) buscando ''urandom''
  3. Abra el archivo de la biblioteca en el editor hexadecimal y encuentre la dirección de la cadena
  4. descubra cómo se pasan los parámetros en syscalls (para abrir, el archivo es el primer parámetro. en x86_64 se pasa en rdi ; su millaje puede variar
  5. Ahora podemos establecer el punto de interrupción condicional: break open if $rdi == _addr_
  6. Ejecutar el programa y esperar que llegue el descanso
  7. corre bt para ver el rastro

Después de todo esto me parece que g_random_int () y g_rand_new () de glib usan urandom. Gtk + y ORBit estaban llamando a estas funciones, si alguien tenía curiosidad.