¿Por qué salir con un código de retorno almacenado de un comando anidado da como resultado diferentes códigos de retorno en Dash y Bash?

8

Corriendo

bash -c 'bash -c "echo test1; exit 1;" &> /tmp/x; buildresult=$?; tail -n 100 /tmp/x; exit $buildresult;'

da como resultado que test1se imprima en la consola e echo $?imprima lo 1que, en mi opinión, es correcto, porque el comando debe regresar con lo [b/d]ash -cque devolvió el interior, mientras que

dash -c 'dash -c "echo test1; exit 1;" &> /tmp/x; buildresult=$?; tail -n 100 /tmp/x; exit $buildresult;'

da como resultado la misma salida, pero regresa de 0acuerdo con echo $?.

Me gustaría entender esta diferencia para ampliar mi comprensión de los shells y la programación de shell portátil.

Estoy usando bash4.4.12 y dash0.5.8-2.3ubuntu1 en Ubuntu 17.10 (Artful Aardvark).

Karl Richter
fuente

Respuestas:

20

&>no está en POSIX y no es compatible con dash. Se analiza como & >, por lo que el comando está en segundo plano. Los comandos en segundo plano tienen un estado de salida de cero desde la perspectiva del padre, ya que no han salido cuando lees $ ?.

Esa es también la razón por la que (al menos para mí) test1aparece la salida " " en mi solicitud, después de que el comando ha finalizado.

Bash &> fooes equivalente a> foo 2>&1 , y un script portátil debería usar este último.

Michael Homer
fuente
55
&>está en POSIX. Eso es &seguido por >. En foo &> bar, eso es foo &comenzar fooen segundo plano y > barrealizar una redirección sin un comando. bashno es compatible con POSIX cuando lo interpreta de manera diferente.
Stéphane Chazelas
44
Lo suficientemente interesante es que esto no se mencionó en wiki.ubuntu.com/DashAsBinSh. Me tomé la libertad de editar la página e incluir eso
Sergiy Kolodyazhnyy