2010-11-07 25 views
5

Los comandos de Bash están disponibles desde una sesión de tclsh interactiva. P.ej. en una sesión tclsh puede tener¿Cómo llamar comandos bash desde tcl script?

% ls 

en lugar de

$ exec ls 

Sin embargo, no se puede tener un script tcl que se pide fiesta de comandos directamente (es decir, sin exec).

¿Cómo puedo hacer que tclsh reconozca comandos bash mientras interpreta archivos de script tcl, tal como lo hace en una sesión interactiva?

Supongo que hay algún paquete tcl (o algo por el estilo), que se carga automáticamente al iniciar una sesión interactiva para admitir llamadas directas de bash commandas. ¿Cómo puedo cargarlo manualmente en archivos de script tcl?

Respuesta

7

Lo que sucede aquí es que el procedimiento unknown se invoca cuando se escribe un comando como ls, porque ese no es un comando tcl existente, y de forma predeterminada, ese comando comprobará si el comando se invocó desde una sesión interactiva y desde el nivel superior (no indirectamente en un cuerpo de proceso) y está comprobando si el nombre del proceso existe en alguna parte de la ruta. Puede obtener algo como esto escribiendo su propio proceso desconocido.

Para un buen comienzo en esto, examine la salida de

info body unknown 
+3

+1: Este es el comienzo del camino, pero creo que conduce a un código deficiente. Es mejor tener llamadas 'exec' explícita IMO ... –

+0

@Donal: Sí, estoy de acuerdo. Explicit es mejor que implícito, y nunca recomendaría reescribir el proceso desconocido para hacer esto, o cualquier otra cosa, excepto tal vez para mejorar la funcionalidad de autocarga ya presente. – SingleNegationElimination

4

Una cosa que debes saber es que ls no es un comando de Bash. Es una utilidad independiente. La pista de cómo tclsh ejecuta esas utilidades está ahí en su nombre: sh significa "shell". Así que es el equivalente aproximado de Bash porque Bash también es un caparazón. Tcl! = Tclsh, por lo que debe usar exec.

10

Si usted quiere tener utilidades específicas disponibles en las secuencias de comandos, escribir procedimientos de puente:

proc ls args { 
    exec {*}[auto_execok ls] {*}$args 
} 

que la voluntad, incluso trabajo (con adaptación obvia) para la mayoría de los shell builtins o en Windows. (Para ser justos, generalmente no desea utilizar un ls externo; el comando interno glob suele ser suficiente, a veces con ayuda adicional de algunos subcomandos file). Algunos comandos necesitan un poco más de trabajo (por ejemplo, redirigir la entrada para que proceda de la terminal, con un extra de <@stdin o </dev/tty; eso es necesario para stty en algunas plataformas) pero eso funciona razonablemente bien.

Sin embargo, si lo que está solicitando es tener una ejecución arbitraria de programas externos sin ningún código adicional para marcar que son externos, eso se considera en contra del ethos de Tcl. El problema es que hace que el código sea mucho más difícil de mantener; no es obvio que estás haciendo una llamada costosa en lugar de usar algo (relativamente) barato que es interno. Poner en el exec en ese caso no es que onerous ...

+1

Podría decirse que no solo está en contra de la ética de Tcl, también es solo una programación deficiente en general. –

Cuestiones relacionadas