GNU/Linux >> Tutoriales Linux >  >> Linux

¿Los paréntesis realmente ponen el comando en una subcapa?

Por lo que he leído, poner un comando entre paréntesis debería ejecutarlo en una subcapa, similar a ejecutar un script. Si esto es cierto, ¿cómo ve la variable x si x no se exporta?

x=1

Ejecutando (echo $x) en la línea de comando da como resultado 1

Ejecutando echo $x en un script no da como resultado nada, como se esperaba

Respuesta aceptada:

Un subshell comienza como una copia casi idéntica del proceso de shell original. Debajo del capó, el caparazón llama al fork llamada al sistema, que crea un nuevo proceso cuyo código y memoria son copias. Cuando se crea el subshell, hay muy pocas diferencias entre este y su padre. En particular, tienen las mismas variables. Incluso el $$ La variable especial mantiene el mismo valor en las subcapas:es el ID del proceso de la capa original. Del mismo modo $PPID es el PID del padre del shell original.

Algunas conchas cambian algunas variables en la subcapa. Bash establece BASHPID al PID del proceso de shell, que cambia en subshells. Bash, zsh y mksh organizan $RANDOM para producir diferentes valores en el padre y en el subshell. Pero aparte de los casos especiales incorporados como estos, todas las variables tienen el mismo valor en el subshell que en el shell original, el mismo estado de exportación, el mismo estado de solo lectura, etc. Todas las definiciones de funciones, definiciones de alias, opciones de shell y otras configuraciones también se heredan.

Una subcapa creada por (…) tiene los mismos descriptores de archivo que su creador. Algunos otros medios para crear subcapas modifican algunos descriptores de archivos antes de ejecutar el código de usuario; por ejemplo, el lado izquierdo de una tubería se ejecuta en una subcapa con salida estándar conectada a la tubería. La subcapa también comienza con el mismo directorio actual, la misma máscara de señal, etc. Una de las pocas excepciones es que las subcapas no heredan trampas personalizadas:señales ignoradas (trap '' SIGNAL ) permanecen ignorados en la subcapa, pero otras trampas (trap CODE SEÑAL ) se restablecen a la acción predeterminada.

Por lo tanto, una subcapa es diferente de ejecutar un script. Un script es un programa separado. Este programa separado podría ser también un script ejecutado por el mismo intérprete que el padre, pero esta coincidencia no le da al programa separado ninguna visibilidad especial en los datos internos del padre. Las variables no exportadas son datos internos, por lo que cuando se ejecuta el intérprete del script de shell secundario, no ve estas variables. Las variables exportadas, es decir, las variables de entorno, se transmiten a los programas ejecutados.

Así:

x=1
(echo $x)

imprime 1 porque el subshell es una réplica del shell que lo generó.

x=1
sh -c 'echo $x'

pasa a ejecutar un shell como un proceso secundario de un shell, pero el x en la segunda línea ya no tiene conexión con x en la segunda línea que en

x=1
perl -le 'print $x'

o

x=1
python -c 'print x'

Una excepción es el ksh93 shell donde se optimiza la bifurcación y se emulan la mayoría de sus efectos secundarios.
Semánticamente, son copias. Desde una perspectiva de implementación, se está compartiendo mucho.
Para el lado derecho, depende del caparazón.
Si prueba esto, tenga en cuenta que cosas como $(trap) puede informar las trampas de la concha original. Tenga en cuenta también que muchos caparazones tienen errores en los casos de esquina que involucran trampas. Por ejemplo, ninjalj señala que a partir de bash 4.3, bash -x -c 'trap "echo ERR at $BASH_SUBSHELL $BASHPID" ERR; set -E; false; echo one subshell; (false); echo two subshells; ( (false) )' ejecuta el ERR trampa de la subcapa anidada en el caso de "dos subcapas", pero no del ERR trampa de la subcapa intermedia — set -E la opción debería propagar el ERR trap a todas las subcapas, pero la subcapa intermedia está optimizada y, por lo tanto, no está allí para ejecutar su ERR trampa.

Relacionado:Linux – ¿Por qué setuid no funciona?
Linux
  1. ¿El punto del comando externo `cd`?

  2. ¿Cuál es la diferencia de obtener salida de comando usando `command` y $(command) en Shell?

  3. ¿Las variables que no son de entorno se pasan al subshell invocado por sustitución de comando?

  4. Personalización de Bash Shell:Negrita/color ¿El comando?

  5. ¿Cómo se interpretan los paréntesis en la línea de comandos?

Alias ​​de línea de comandos en el shell de Linux

Comando fuente en Linux

¿Qué es el Shell en Linux?

Construcción de comandos

Comando Bash fc:maneja fácilmente el Bash Shell como un profesional

Usando el comando passwd desde dentro de un script de shell