2008-11-26 16 views
38

Me gustaría escribir un script que (bajo ciertas condiciones) ejecutará gdb y ejecutará automáticamente algún programa X con un conjunto de argumentos Y. Una vez que el programa haya terminado de ejecutarse el usuario debe permanecer en el prompt de gdb hasta que lo/la cierre explícitamente.Invocar gdb para pasar automáticamente argumentos al programa que se está depurando

Una forma de hacer esto sería que la salida del script de la orden de marcha, más argumentos Y a algún archivo F y luego tener el BGF guión de invocación de esta manera:

gdb X < F 

Pero hay una manera de hacer esto sin introducir un archivo temporal?

Gracias.

Respuesta

26

Si desea ejecutar algunos comandos a través del BGF y luego tener que salir o se termina de ejecutar, acaba de hacer

echo commands | gdb X 

Si desea dejarlo en el símbolo del sistema después de ejecutar esos comandos, puede hacerlo

(echo commands; cat) | gdb X 

Esto se traduce en hacerse eco de los comandos de GDB, y luego se teclea en el proceso de cat, que copia su stdin a la salida estándar, que se canaliza en el BGF.

+1

(echo "ejecutar params"; cat) | gdb X; # trabajado un regalo, muchas gracias! –

+2

Tenga en cuenta que pierde la interactividad del shell si lo hace (todas las características de edición de lectura, historial, etc.). – ijw

+0

Acabo de notar que subir/bajar no funciona ... no es una solución aceptable :( – Nils

0

cat F | gdb X deben ser idénticos. De modo que puede usar cualquier cosa que produzca salida y conectarlo a gdb en lugar del comando cat aquí.

Supongo que es correcto y gdb lee de stdin.

85

La forma más sencilla de hacer esto da un programa X y la lista de parámetros a b c:

X a b c 

es utilizar gdb '--args opción de s, de la siguiente manera:

gdb --args X a b c 

gdb --help tiene esto que decir sobre --args:

--args Arguments after executable-file are passed to inferior

Lo que significa que el primer argumento después --args es el ejecutable para depurar y todos los argumentos después de que se pasan como es a ese ejecutable.

+0

Tenía un caso de uso en el que decía alguna función foo (a , b, c) (cualquier tipo de datos), esto tiene una llamada en decir main(), ahora quiero ingresar estos argumentos incluso antes de comenzar a ejecutar el programa. ¿Podemos lograr esto? – KedarX

+0

@Kedar: No de esta manera. El método determina los argumentos pasados ​​a 'main()'. Depende de usted transferirlos apropiadamente a 'foo'. –

+0

Ok, eso aclara mi duda, que no hay manera de que podamos alimentar argumentos a ningún método interno dentro de main (a menos que se haga por transferencia). Gracias @Nathan Fellman – KedarX

1
gdb target -e "my-automation-commands" 

mi-automatización de comandos que contienen todo lo que normalmente se desea ejecutar,

break 0x123 
set args "foo" bar 2 
r 

No es estrictamente un archivo temporal, si usted tiene un par de scripts de inicio estándar;)

8

existe opción -x, por ejemplo

gdb -x gdb_commands exe_file 

donde gdb_commands pueden ser por ejemplo (en el caso del emulador de Android):

target remote :5039 
+2

También tenga en cuenta que si desea evitar el uso de un archivo temporal, puede usar la sustitución de proceso: 'gdb -x <(Comandos echo) exe_file' –

+1

Simplemente use 'gdb -ex 'foo' -ex 'bar'' para ejecutar gdb con los comandos' foo' y luego 'bar'. – zopieux

1

Bueno, esto es sólo un comentario, no es realmente una respuesta - sólo quería incluir algún código fragmentos. Estoy en bash/Ubuntu Lucid - y para mí, tuve casi los mismos problemas que en: "GDB has problems with getting commands piped to STDIN - Unix Linux Forum - Fixunix.com".

Básicamente, me gustaría conseguir el mismo como en el siguiente fragmento:

$ gdb 
GNU gdb (GDB) 7.1-ubuntu 
Copyright (C) 2010 Free Software Foundation, Inc. 
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html> 
This is free software: you are free to change and redistribute it. 
There is NO WARRANTY, to the extent permitted by law. Type "show copying" 
and "show warranty" for details. 
This GDB was configured as "i486-linux-gnu". 
For bug reporting instructions, please see: 
<http://www.gnu.org/software/gdb/bugs/>. 
(gdb) pwd 
Working directory /media/work/dir. 
(gdb) 

... excepto, me gustaría "tubería" el comando pwd alguna manera, y mantener abierta después GDB (como en el ejemplo anterior).

que he probado algunas de las sugerencias aquí, y lo único que trabaja para mí es la sintaxis (echo commands; cat) | gdb -, así como (un poco de trabajo) Here Strings - aquí están mis resultados:

$ echo "pwd" | gdb 
(gdb) Hangup detected on fd 0 
error detected on stdin 


$ echo "pwd" | gdb -x /dev/stdin 
GNU gdb (GDB) 7.1-ubuntu 
... 
/dev/stdin: Invalid argument. 
(gdb) Hangup detected on fd 0 
error detected on stdin 


$ gdb -x <(echo "pwd") 
GNU gdb (GDB) 7.1-ubuntu 
... 
/dev/fd/63: No such file or directory. 
(gdb) q 


$ gdb -e "pwd" 
GNU gdb (GDB) 7.1-ubuntu 
... 
For bug reporting instructions, please see: 
<http://www.gnu.org/software/gdb/bugs/>. 
(gdb) q # nothing happens 


$ gdb <<<"pwd" 
GNU gdb (GDB) 7.1-ubuntu 
... 
(gdb) Working directory /media/work/dir. 
(gdb) quit # OK, but autoexits 


$ gdb <<<"pwd 
> " 
GNU gdb (GDB) 7.1-ubuntu 
... 
(gdb) Working directory /media/work/dir. 
(gdb) Working directory /media/work/dir. 
(gdb) quit # with a line break at end, it execs twice, then exits 


# the only one OK for my needs - 
# except locks after quit, and needs Ctrl-C 
$ (echo "pwd"; cat) | gdb 
GNU gdb (GDB) 7.1-ubuntu 
... 
(gdb) Working directory /media/work/dir. 
(gdb) q 
^C 

Bueno, la esperanza esto ayuda a alguien,
¡Salud!

 
Editar: Ahora por lo menos sé qué substitución proceso no funcionará - se utilizará un descriptor de archivo temporal, que no puede ser reconocido como un archivo por ls (tanto gdb definitivamente no puede leerlo; además, el referencia desaparece casi inmediatamente, a menos que el proceso de alguna manera está bloqueado, al igual que con cat) - ver el terminal fragmento de registro:

$ echo -e "***\n" <(echo "pwd") "\n***\n`cat <(ls -C /dev/fd ; echo; for ix in /dev/fd/*; do irl=$(readlink -f $ix); echo $ix -\> $irl; ls -la $ix 2>&1; ls -la $irl 2>&1; echo '______'; done ; ls -C /dev/fd)`" 

*** 
/dev/fd/63 
*** 
0 1 2 3 63 

/dev/fd/0 -> /dev/pts/0 
lrwx------ 1 user user 64 2010-11-07 21:18 /dev/fd/0 -> /dev/pts/0 
crw--w---- 1 user tty 136, 0 2010-11-07 21:18 /dev/pts/0 
______ 
/dev/fd/1 -> /proc/10713/fd/pipe:[236191] 
l-wx------ 1 user user 64 2010-11-07 21:18 /dev/fd/1 -> pipe:[236151] 
ls: cannot access /proc/10713/fd/pipe:[236191]: No such file or directory 
______ 
/dev/fd/2 -> /dev/pts/0 
l-wx------ 1 user user 64 2010-11-07 21:18 /dev/fd/2 -> pipe:[236151] 
crw--w---- 1 user tty 136, 0 2010-11-07 21:18 /dev/pts/0 
______ 
/dev/fd/255 -> /proc/10721/fd/255 
ls: cannot access /dev/fd/255: No such file or directory 
ls: cannot access /proc/10721/fd/255: No such file or directory 
______ 
/dev/fd/3 -> /proc/10725/fd/3 
ls: cannot access /dev/fd/3: No such file or directory 
ls: cannot access /proc/10725/fd/3: No such file or directory 
______ 
0 1 2 3 

Además, las teclas arriba/abajo no funcionan con (echo commands; cat) | gdb, porque así es como se comporta el gato; si sólo corremos cat por lo que las copias entrada estándar a la salida estándar, obtenemos:

$ cat # or `cat -`: and start pressing up/down keys - and get: 
^[[A^[[B^[[A^[[B^[[A^[[B^C 

Usted puede tratar de activar el modo de caracteres en bruto (o desactivar el modo de buffer/cocinado) con stty -cooked, y luego cat Marcarán los dos escriba caracteres como ^[[A, y mueva el cursor - desafortunadamente, en este modo, Ctrl-C ya no funciona, por lo que no podrá cerrar cat de esa manera ...

1

Con bash puede crear una secuencia de comandos que le da al usuario como entrada a cualquier ejecutable que está ejecutando:

#!/bin/sh 
gdb X <<GDB_INPUT 
pwd 
run X a b c 
quit 
GDB_INPUT 
+1

¿Cómo puedo hacer que gdb continúe ejecutándose después de eso, en lugar de dejarlo? .. Entonces: gdb -ex run --args prog arg ... parece ser el mejor enfoque – Alex

+0

Simplemente elimine el comando "quit". – selalerer

4

Después de probar todas las respuestas aquí,

  1. El truco/gato de eco, mientras que inteligente, rompe un buen número de características importantes del BGF. En particular, todos los mensajes del usuario se responden automáticamente (para que no tenga la oportunidad de confirmar operaciones potencialmente peligrosas), y Ctrl + C (para detener un proceso que está depurando) termina matando a gato, por lo que no puede habla con gdb después de eso.
  2. Se supone que la opción -x funciona, pero no pude hacer que funcione con mi versión de gdb, y requiere un archivo temporal.

Sin embargo, resulta que sólo puede utilizar -ex, así:

gdb -ex "target remote localhost:1234" 

También puede especificar -ex varias veces para ejecutar varios comandos!

Cuestiones relacionadas