foo=$bar
é seguro porque é uma atribuição , e uma atribuição a uma variável escalar, usando a sintaxe de atribuição escalar. É um contexto escalar , somente um valor pode ser armazenado em $var , não faria sentido dividir ou glob $bar . Se a expansão resultasse em várias palavras, o shell precisaria de alguma forma combiná-las novamente para poder armazená-las como uma string em $foo .
É diferente quando você usa:
foo=($bar)
Onde você está atribuindo a uma variável de matriz. Existe um contexto de lista. Você está atribuindo um número de palavras aos elementos da matriz. split + glob ocorre.
Tenha também cuidado com a natureza dupla de coisas como export / local / typeset / declare / readonly em algumas conchas (explicado em mais detalhes em Citações são necessárias para atribuição de variável local? )
Você notará que:
foo=$bar
é analisado como uma atribuição enquanto
"foo"=$bar
é apenas uma tentativa de executar o comando foo=content_of_bar (onde o conteúdo da barra está sujeito a split + glob).
Em shells em que export (e outros local / typeset ...) é tanto uma palavra-chave quanto uma versão interna (ksh, bash e versões recentes do zsh), em:
export foo=$bar
export é reconhecido como uma palavra-chave e foo=$bar como uma atribuição, portanto $bar não está sujeito a divisão + glob. Mas é preciso pouco para que export pare de ser reconhecido como uma palavra-chave . Nesse caso, ele é tratado apenas como um comando simples e split + glob acontece como em qualquer argumento para qualquer outro comando.
E mesmo nos casos em que export é visto como uma palavra-chave, se os argumentos não se parecem com atribuições de variáveis (como no "foo"=$bar acima), eles são tratados como argumentos normais e sujeitos a divisão + glob novamente.