¿Qué es the? (signo de interrogación dólar) variable en shell scripting?
Estoy tratando de aprender shell scripting, y necesito entender el código de otra persona. ¿Qué es la variable $?
hold? No puedo buscar la respuesta en Google porque bloquean los caracteres de puntuación.
9 answers
$?
se utiliza para encontrar el valor devuelto del último comando ejecutado.
Prueba lo siguiente en el shell:
ls somefile
echo $?
Si somefile
existe (independientemente de si se trata de un archivo o directorio), obtendrá el valor de retorno arrojado por el comando ls
, que debería ser 0
(valor de retorno predeterminado de "éxito"). Si no existe, usted debe conseguir un número otro entonces 0. El número exacto depende del programa.
Para muchos programas puede encontrar los números y su significado en el correspondiente página de manual. Estos generalmente se describirán como" estado de salida " y pueden tener su propia sección.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-06-29 10:35:24
Es el estado de salida de la última función/programa/comando ejecutado. Refiérase a:
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-07-26 18:18:55
Un valor devuelto del proceso previamente ejecutado.
10.4 Obtener el valor devuelto de un programa
En bash, el valor de retorno de un programa se almacena en una variable especial llamado $?.
Esto ilustra cómo capturar el valor devuelto de un programa, I supongamos que el directorio dada no existe. (Esto también fue sugerido por mike)
#!/bin/bash cd /dada &> /dev/null echo rv: $? cd $(pwd) &> /dev/null echo rv: $?
Ver Bash Programming Manual para más detalles.
$? es el resultado (código de salida) del último comando ejecutado.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-07-26 18:09:45
Ejemplo de C mínimo
Para entender $?
, primero debe entender el concepto de estado de salida del proceso.
En Linux:
-
Cuando un proceso llama a la llamada al sistema
exit
, el núcleo almacena el valor pasado a la llamada al sistema incluso después de que el proceso muere.La llamada al sistema de salida es llamada por la función ANSI C
exit()
, e indirectamente cuando hacesreturn
desdemain
. -
El proceso que llamó al niño saliente proceso (Bash), a menudo con
fork
+exec
, puede recuperar el estado de salida del hijo con la llamada al sistemawait
Considere el código Bash:
$ false
$ echo $?
1
La C "equivalente" es:
Falso.c:
#include <stdlib.h> /* exit */
int main() {
exit(1);
}
Bash.c:
#include <unistd.h> /* execl */
#include <stdlib.h> /* fork */
#include <sys/wait.h> /* wait, WEXITSTATUS */
#include <stdio.h> /* printf */
int main() {
if (fork() == 0) {
/* Call false. */
execl("./false", "./false", (char *)NULL);
}
int status;
/* Wait for a child to finish. */
wait(&status);
/* Status encodes multiple fields,
* we need WEXITSTATUS to get the exit status:
* http://stackoverflow.com/questions/3659616/returning-exit-code-from-child
**/
printf("$? = %d\n", WEXITSTATUS(status));
}
En Bash, cuando se pulsa enter, ocurre una bifurcación + exec + wait como la anterior, y bash entonces establece $?
al estado de salida del proceso bifurcado.
Nota: para comandos integrados como echo
, no es necesario generar un proceso, y Bash solo establece $?
a 0 para simular un proceso externo.
Normas y documentación
POSIX 7 2.5.2 "Parámetros especiales" http://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html#tag_18_05_02 :
? Se expande al estado de salida decimal de la canalización más reciente (consulte Canalizaciones).
man bash
"Parámetros Especiales":
El shell trata varios parámetros especialmente. Estos los parámetros solo pueden ser referenciados; la asignación a ellos no está permitida. [...]
? Se expande al estado de salida de la canalización de primer plano ejecutada más recientemente.
ANSI C y POSIX recomiendan entonces que:
-
0
significa que el programa tuvo éxito -
Otros valores: el programa falló de alguna manera.
El valor exacto podría indicar el tipo de fallo.
ANSI C no define el significado de ninguna vaues, y POSIX especifica valores mayores que 125: Nunca entendí realmente: ¿qué es POSIX?
Bash usa el estado de salida para if
En Bash, a menudo usamos el estado de salida $?
implícitamente para controlar if
declaraciones como en:
if true; then
:
fi
Donde true
es un programa que sólo devuelve 0.
Lo anterior equivale a:
true
result=$?
if [ $result = 0 ]; then
:
fi
Y en:
if [ 1 = 1 ]; then
:
fi
[
es solo un programa con un nombre extraño (y Bash incorporado que se comporta así), y 1 = 1 ]
sus argumentos, ver también: ¿Cuál es la diferencia entre corchetes simples y dobles en Bash?
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-11-30 15:08:16
Es el código de error devuelto del último comando ejecutado. 0 = éxito
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-07-26 18:09:35
$?
es el estado de salida de un comando, de modo que puede encadenar una serie de comandos.
Ejemplo
command1 && command2 && command3
command2
se ejecutará si command1's
$?
los rendimientos de un success (0)
y command3
ejecutará si $?
de command2
producirá un success
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-06-14 03:13:51
Se ejecutó el código de salida del último comando.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-07-26 23:43:02
Es muy adecuado para la depuración en caso de que su script salga si se utiliza "set-e". Por ejemplo, poner "echo $?"después del comando que causa que salga y vea el valor de error devuelto.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-08-04 20:04:36