Não é possível declarar o link simbólico para o arquivo

4

Plano de fundo Eu estou tentando entender como o html é incapaz de acessar um arquivo através de um symlink. Realizei o seguinte experimento simples para tentar entender como o apache estaria tentando acessar / acessar um arquivo apontado por um simlink, mas não consigo entender por que ele não funcionou.

Como o usuário jzhu, eu tenho um link simbólico no meu diretório home para um diretório na raiz chamado outro que tem o arquivo anaconda-ks.cfg que eu quero poder stat / read no vi. No entanto, estou obtendo os seguintes resultados quando estou executando o comando stat.

[jzhu@localhost ~]$ stat /home/jzhu/other/anaconda-ks.cfg
stat: cannot stat '/home/jzhu/other/anaconda-ks.cfg': Permission denied

Aqui está o comando stat do link simbólico / home / jzhu / other para que você possa esclarecer melhor como estou configurado.

[jzhu@localhost ~]$ stat /home/jzhu/other
  File: '/home/jzhu/other' -> '/root/other/'
  Size: 12          Blocks: 0          IO Block: 4096   symbolic link
Device: fd00h/64768d    Inode: 43313       Links: 1
Access: (0777/lrwxrwxrwx)  Uid: (    0/    root)   Gid: (    0/    root)
Access: 2013-11-03 08:52:20.602126433 +0000
Modify: 2013-11-03 08:52:20.187918394 +0000
Change: 2013-11-03 08:52:20.187918394 +0000

Pesquisando a página man do lstat, vejo a seguinte citação:

These functions return information about a file. No permissions are required on the file itself, but — in the case of stat() and lstat() — execute (search) permission is required on all of the directo- ries in path that lead to the file.

Do meu entender o comando stat não precisa de permissões executáveis no / root em si porque, ao contrário do lstat, o diretório raiz com o qual ele inicia é o atual no qual ele é executado, o que significa que ele não usará o caminho completo de "/ root / other /" mas usará o caminho "/ home / jzhu / other /". Confirmei isso via strace com a seguinte saída relevante abaixo

lstat("/home/jzhu/other/anaconda-ks.cfg", 0x7fff14d5a7c0) = -1 EACCES (Permission denied)

Portanto, para que eu possa registrar este arquivo, tudo que eu preciso é de uma permissão executável em / home / home / jzhu e / home / jzhu / other

Como jzhu, eu corri um stat em ambos / home e / home / jzhu para confirmar que eu tinha permissões executáveis. Mostrado abaixo

[jzhu@localhost ~]$ stat /home/
  File: '/home/'
  Size: 4096        Blocks: 8          IO Block: 4096   directory
Device: fd00h/64768d    Inode: 2278        Links: 4
Access: (0755/drwxr-xr-x)  Uid: (    0/    root)   Gid: (    0/    root)
Access: 2013-11-03 08:52:13.797724760 +0000
Modify: 2013-11-04 00:03:45.377150769 +0000
Change: 2013-11-04 00:03:45.377150769 +0000
[jzhu@localhost ~]$ stat /home/jzhu
  File: '/home/jzhu'
  Size: 4096        Blocks: 8          IO Block: 4096   directory
Device: fd00h/64768d    Inode: 43317       Links: 3
Access: (0700/drwx------)  Uid: (  500/    jzhu)   Gid: (  500/    jzhu)
Access: 2013-11-04 00:00:30.809916040 +0000
Modify: 2013-11-03 23:49:54.781060426 +0000
Change: 2013-11-03 23:49:54.781060426 +0000

No entanto, eu não consegui stat / home / jzhu / other como jzhu:

[jzhu@localhost ~]$ stat /home/jzhu/other/
stat: cannot stat '/home/jzhu/other/': Permission denied

Alterando também e executando stat no diretório. Estou confuso sobre o porquê eu sou incapaz de indicar o diretório como jzhu. Como pode ser visto abaixo, outras permissões de leitura e executáveis nesse diretório.

[root@localhost jzhu]# stat /home/jzhu/other/
  File: '/home/jzhu/other/'
  Size: 4096        Blocks: 8          IO Block: 4096   directory
Device: fd00h/64768d    Inode: 32674       Links: 2
Access: (0755/drwxr-xr-x)  Uid: (    0/    root)   Gid: (    0/    root)
Access: 2013-11-03 08:50:36.935318703 +0000
Modify: 2013-11-03 08:50:35.772737444 +0000
Change: 2013-11-03 08:50:35.772737444 +0000
[root@localhost jzhu]# stat /home/jzhu/other/anaconda-ks.cfg 
  File: '/home/jzhu/other/anaconda-ks.cfg'
  Size: 985         Blocks: 8          IO Block: 4096   regular file
Device: fd00h/64768d    Inode: 43297       Links: 1
Access: (0777/-rwxrwxrwx)  Uid: (    0/    root)   Gid: (    0/    root)
Access: 2013-11-03 08:50:35.772737444 +0000
Modify: 2013-11-03 08:50:35.781741701 +0000
Change: 2013-11-03 08:54:50.814196796 +0000

Então as duas perguntas que quero fazer são as seguintes.

  1. Por que não consigo stat / home / jzhu / other / mesmo que eu tenha lido e permissão executável em outro nesse diretório?
  2. Por que não consigo registrar o arquivo anaconda-ks.cfg?
por Jason Zhu 04.11.2013 / 02:34

1 resposta

4

Sua resposta está no primeiro resultado que você forneceu:

$ stat /home/jzhu/other
  File: '/home/jzhu/other' -> '/root/other/'

Isso mostra que /home/jzhu/other é um link simbólico para /root/other .

Então, basicamente, para acessar qualquer coisa em /home/jzhu/other/ você precisará acessar /root/other . Isso significa que seu usuário deve ter permissões de execução em /root e /root/other .

Em seguida, vamos para este comando:

$ stat /home/jzhu/other/
stat: cannot stat '/home/jzhu/other/': Permission denied

A razão pela qual isso falha e a que está acima funciona é por causa do / . Em qualquer comando que trabalhe com um caminho, se o componente final desse caminho (por exemplo: other ) for um symlink, e o caminho terminar com um / , então qualquer chamada de sistema para operar nesse caminho tentará desreferencia o link simbólico e opere o que o link simbólico aponta para o próprio link simbólico.

Soluções:

Existem duas soluções possíveis para isso.

1. Alterar permissões em /root/other :

Como mencionado, adicione o recurso de execução a /root e /root/other . Você pode fazer isso com atributos básicos ou estendidos do sistema de arquivos.

  • Você pode adicionar o usuário jzhu ao grupo root ( usermod -a -G root jzhu ) e adicionar a execução do grupo ao caminho ( chmod g+x /root; chmod g+x /root/other ).
    Esta não é uma solução ideal, pois concede o seu acesso a qualquer coisa restrita ao grupo root .

  • Use as ACLs do sistema de arquivos.

    setfacl -m u:jzhu:x /root
    setfacl -R -m u:jzhu:x /root/other
    setfacl -d -R -m u:jzhu:x /root/other
    

    Isso faz com que seu usuário específico obtenha acesso de execução a /root/other e qualquer coisa dentro dele.
    Ainda não é ideal como se esses recursos fossem compartilhados, eles não deveriam estar no diretório pessoal do root.

Note que em ambas as soluções nós apenas concedemos o bit execute ( x ). O bit de execução é necessário em um diretório para um usuário acessar qualquer coisa dentro desse diretório. No entanto, você também precisa do bit de leitura ( r ) para poder listar ( ls ) o diretório. O que significa que sem o bit de leitura, você terá que saber exatamente onde /root/other os arquivos estão. Se você quiser permitir a leitura, basta alterar o x nos últimos 2 setfacl de comandos para rx (por exemplo, -m u:jzhu:rx ).

2. Mova os recursos para fora de /root/other .

Esta é a solução preferida. Você pode se livrar do symlink em /home/jzhu/other e criar um diretório em seu lugar, ou colocá-los em um local compartilhado em algum outro lugar do sistema (sem saber o que é, eu não posso recomendar uma boa localização embora).

A razão pela qual essa é a solução preferida é que, se esses recursos forem compartilhados entre os usuários, eles não pertencerão a um usuário específico e não deverão estar no diretório inicial desse usuário.

    
por 04.11.2013 / 02:50

Tags