Por que a mensagem de erro para dois dois pontos como um comando (: :) no bash tem três pontos, mas um único cólon não fornece saída?

27

Se eu digitar

::

em um shell bash, eu recebo:

-bash: ::: command not found

Mas, apenas um : resulta em nenhuma saída. Por que isso acontece?

    
por NerdOfLinux 15.12.2017 / 02:18

6 respostas

40

O shell : incorporado versus o coexame inexistente ::

O comando% shell_de_automática shell incorporado existe (observe o diferença entre comandos externos e internos ) que não faz nada; apenas retorna sucesso, assim como o comando : . O true embutido é padrão e definido pelo padrão POSIX , onde também é conhecido como o "utilitário nulo". É freqüentemente usado para testes ou para executar loops infinitos como em :

bash-4.3$ type :
: is a shell builtin

No entanto, while : ; do ...;done - dois caracteres de dois pontos juntos - são interpretados como uma "palavra" para o shell, e assume ser um comando que o usuário inseriu. O shell passará pelo processo de verificação de built-ins e, em seguida, por qualquer diretório na variável :: para a existência desse comando. Mas não existe um comando PATH nem um comando externo :: . Portanto, isso produz um erro.

Bem, qual é o formato típico de um erro?

<shell>: <command user typed>: error message

Assim, o que você vê não são 3 pontos, mas o que você digitou no formato de erro padrão.

Note também que :: pode receber argumentos da linha de comando, ou seja, é legal fazer:

: :

Nesse caso, o shell considerará isso como duas "palavras", uma das quais é um comando e a outra um parâmetro posicional. Isso também não produzirá erros! (Veja também a nota histórica (mais adiante nesta resposta) sobre o uso de : com parâmetros posicionais.)

Em shells que não sejam bash

Observe que a formatação também pode variar entre diferentes shells. Para : , bash e ksh , o comportamento é consistente. Por exemplo, o mksh shell padrão do Ubuntu (que na verdade é /bin/sh ):

$ dash
$ ::
dash: 1: ::: not found

em que 1 é o número do comando (equivalente ao número da linha em um script).

/bin/dash por contraste não produz nenhuma mensagem de erro:

$ csh
% ::
%

De fato, se você executar csh , a saída de rastreio no arquivo strace -o csh.trace csh -c :: revela que csh.trace sai com o status de saída 0 (sem erros). Mas csh produz o erro (sem gerar seu nome):

$ tcsh
localhost:~> ::
::: Command not found.

Mensagens de erro

Em geral, o primeiro item na mensagem de erro deve ser o processo ou função em execução (seu shell tenta executar tcsh , portanto a mensagem de erro vem do shell). Por exemplo, aqui o processo de execução é :: :

$ stat noexist
stat: cannot stat 'noexist': No such file or directory

Na verdade, o POSIX define a função perror () , que, de acordo com a documentação, leva um argumento de seqüência de caracteres, em seguida, gera uma mensagem de erro após dois pontos e, em seguida, nova linha. Citação:

% bl0ck_qu0te%

E o argumento string para stat tecnicamente poderia ser qualquer coisa, mas é claro que, normalmente, é o nome da função ou perror() .

Por outro lado, o GNU possui seu próprio conjunto de funções e variáveis para tratamento de erros , que um programador pode usar com argv[0] to fprintf() stream. Como mostra um dos exemplos da página vinculada, algo assim poderia ser feito:

  fprintf (stderr, "%s: Couldn't open file %s; %s\n",
           program_invocation_short_name, name, strerror (errno));

Nota histórica

No antigo shell Unix e Thompson, stderr foi usado com a : declaração (que, de acordo com Um usuário chamado Perderabo em este tópico não era um shell embutido). Cite o manual:

% bl0ck_qu0te%

Você pode fazer algo assim para criar um script de loop infinito:

: repeat
echo "Hello World"
goto repeat
    
por Sergiy Kolodyazhnyy 15.12.2017 / 02:33
54

Os últimos dois pontos são apenas parte da mensagem padrão "não encontrada":

$ x
x: command not found
$ ::
::: command not found

A razão pela qual um single dois pontos não produz nada é que : é um comando válido - embora não faça nada (exceto return TRUE ). Na seção SHELL BUILTIN COMMANDS de man bash :

   : [arguments]
          No effect; the command does nothing beyond  expanding  arguments
          and  performing any specified redirections.  A zero exit code is
          returned.

Você as verá em construções como

while :
do
  something
done

Veja, por exemplo, Qual é a finalidade do cólon embutido?

    
por steeldriver 15.12.2017 / 02:30
8

Tente qualquer outro comando inexistente e você verá que o : serve a sua finalidade normal em inglês:

$ ---
---: command not found
    
por Olorin 15.12.2017 / 02:29
6

Os dois pontos adicionados fazem parte da mensagem de erro em si. Se alguém digitar cd ow , isso resultará em bash: cd: ow: No such file or directory , o que mostra que o erro está colocando o cólon extra : No such file or directory

    
por John Orion 15.12.2017 / 02:31
5
$ ::
bash: ::: command not found
$ kkkk
bash: kkkk: command not found

o terceiro é um espaçador da formatação

no bash a : é uma instrução vazia de linha vazia

    
por user688056 15.12.2017 / 02:30
4

você recebe 3 dois-pontos porque o formato do erro contém dois pontos:

bash: <command>: command not found
    
por ravery 15.12.2017 / 02:31