Removendo “.” em pé sobre ele

5

Enquanto brincava com o sistema de arquivos, tentei o seguinte:

mkdir a
cd a
rmdir .

O que resulta em:

rmdir: failed to remove ‘.’: Invalid argument

Ok, Sr. rmdir , deixe-me ser mais esperto do que você:

rmdir ../a

... Ok.

O que? Nenhum erro desta vez?

Meu terminal ainda diz que estou no diretório a , mas ls -a não lista nada (nem . nem .. ), mas ls .. e pwd ainda funcionam como esperado.

Eu sou como um daqueles personagens de desenhos animados que cortam seu próprio ramo, mas ainda não caiu?

Se eu tentar

mkdir ../a

Ele cria um diretório a , mas esse ainda não é o diretório em que estou ( ls -a . e ls -a ../a mostram resultados diferentes).

Se eu tentar criar um arquivo com touch b , ele responderá:

touch: cannot touch ‘b’: No such file or directory

Mas touch . funciona.

Finalmente, assim que saio do meu diretório, ele desaparece e não posso voltar a ele.

Editar: Alguém poderia explicar o que está acontecendo aqui? Existe um nome para esta situação? Isso é um problema entre o sistema de arquivos e o Bash, ou algum comportamento especial codificado no Bash?

    
por anol 29.01.2014 / 20:24

2 respostas

9

Isto não tem nada a ver com o bash.

É o comportamento padrão do Unix, essas décadas passadas. É o comportamento padrão do kernel e nada a ver com shells.

O importante é lembrar que arquivos e diretórios não precisam ter nomes. Um arquivo ou diretório continua existindo desde que (a) tenha uma contagem de link diferente de zero, (b) seja referenciado por um descritor de arquivo aberto ou (c) seja o diretório de trabalho de um processo. (Há algumas outras condições que podem impedir que um arquivo ou um diretório desapareça para a inexistência, mas não são relevantes para sua pergunta aqui.)

Com arquivos, você deve estar bem acostumado com a idéia de criar um arquivo temporário sem nome, que é automaticamente limpo quando o último descritor de arquivo aberto para ele é fechado, abrindo um arquivo e, em seguida, desvinculando-o para que sua contagem de links cai para zero. (Isso está encobrindo muitos detalhes relacionados à segurança que não são relevantes para essa pergunta.)

Você também deve estar bem acostumado com a idéia de que pode desvincular um arquivo para o qual algum processo possui um descritor de arquivo aberto, criar um novo arquivo com o mesmo nome e eles serão dois arquivos diferentes .

Você acabou de fazer as mesmas coisas com um diretório. Você esvaziou o diretório e desvinculou-o, mas ele continuou existindo até não ser mais referenciado por um descritor de arquivo aberto e não era mais o diretório de trabalho de nenhum processo. Quando você criou um novo diretório com o mesmo nome que você tinha desvinculado, você tinha dois diretórios diferentes .

Observe que o SUS permite que rmdir ../a falhe se o diretório nomeado for o diretório atual de qualquer processo. (Isto não é para dar uma lacuna nas APIs POSIX no topo do Windows NT, como alguns podem pensar. O QNX também falha na chamada neste caso, por exemplo.) Você está obviamente rodando um sistema operacional que (na ausência de considerações como diretórios raiz e pontos de montagem, que sua pergunta não envolve) escolhe a outra alternativa permitida, que é desvincular o diretório, remover as entradas . e .. e proibir a criação de novas entradas.

Leitura adicional

  • "rmdir" . As especificações básicas do grupo aberto . IEEE Std 1003.1. Edição 7. 2013.
  • "rmdir" . Referência da Biblioteca do Sistema Operacional em Tempo Real QNX Neutrino . Suporte ao desenvolvedor do QNX.
por 29.01.2014 / 21:46
1

Como complemento à excelente resposta do JdeBP, você pode confirmar que isso é realmente o que está acontecendo verificando o inode de o diretório em questão:

$ mkdir ~/foo
$ ls -di ~/foo
16654483 /home/terdon/foo
$ cd ~/foo
$ rmdir ../foo/
$ ls -di ../foo
ls: cannot access ../foo: No such file or directory
$ mkdir ../foo
$ ls -di ../foo
16654484 ../foo

Observe que o número do inode foi alterado, este é um novo diretório sem conexão com o antigo, além de ter o mesmo nome.

    
por 29.01.2014 / 23:13

Tags