Como permitir que usuários transfiram arquivos para outros usuários no linux

10

Temos um ambiente de alguns milhares de usuários executando aplicativos em cerca de 40 clusters, variando em tamanho, de 20 nós de computação a 98.000 nós de computação. Os usuários desses sistemas geram arquivos maciços (às vezes> 1PB) controlados por permissões tradicionais do unix (as ACLs geralmente não estão disponíveis ou são práticas devido à natureza especializada do sistema de arquivos).

Atualmente, temos um programa chamado "give", que é um programa suid-root que permite ao usuário "dar" um arquivo a outro usuário quando as permissões de grupo são insuficientes. Portanto, um usuário digitaria algo como o seguinte para fornecer um arquivo a outro usuário:

> give username-to-give-to filename-to-give ...

O usuário receptor pode então usar um comando chamado "take" (parte do programa give) para receber o arquivo:

> take filename-to-receive

As permissões do arquivo são então efetivamente transferidas para o usuário receptor.

Este programa existe há anos e gostaríamos de revisar as coisas do ponto de vista funcional e de segurança.

Nosso plano de ação atual é remover a podridão dos bits em nossa implementação atual do "give" e empacotá-lo como um aplicativo de código aberto antes de reimplementá-lo na produção.

Alguém tem outro método que eles usam para transferir arquivos extremamente grandes entre usuários quando apenas as permissões unix tradicionais estão disponíveis?

Jon Bringhurst
fonte
1
Existe alguma razão para você não poder simplesmente criar um diretório compartilhado ao qual todos os usuários tenham acesso?
precisa
1
Se houver um diretório com acesso compartilhado, os usuários sem permissão terão acesso aos arquivos enquanto estiverem sendo compartilhados. Nesse ambiente, às vezes os nomes de arquivos também são sensíveis. Infelizmente, um diretório compartilhado não é uma opção. Com um diretório compartilhado, também há a possibilidade de um terceiro usuário adulterar o arquivo.
Jon Bringhurst
Não seria suficiente que um trabalho cron copiasse os arquivos? Exemplo: o usuário foo deseja dar uma barra de arquivos ao usuário filhote. então ele cria um diretório especializado que é verificado pelo job cron com um arquivo 'control' contendo o nome de usuário de recebimento. Os trabalhos do cron leriam esse arquivo de 'controle'; se o usuário estiver OK, o diretório de destino tem espaço, a cópia. Você ainda pode criar um wrapper para 'give' para criar apenas o arquivo 'control' para ter compatibilidade histórica. Não há necessidade de suid-root, você pode copiar esse arquivo em usuário não-root e, em seguida, sudo para alterar a propriedade.
jirib
Se você apenas deseja alterar as permissões, chowndeve fazê-lo. Parece que você também deseja copiar o arquivo, assim que as duas partes envolvidas concordarem.
zebediah49
@JiriXichtkniha Eu gosto da idéia de um arquivo de controle e um trabalho cron. No entanto, os arquivos são muito grandes para serem copiados.
Jon Bringhurst

Respostas:

1

Se o emissor estiver realmente disposto a fornecer o arquivo, você pode usar um binário SUID que move o arquivo para um diretório que pode ser gravado por todos e possui o bit adesivo (como /tmp), depois muda a propriedade para o novo proprietário. chown(3)já cuida de remover os bits set-user-IDe set-group-IDpara você. Dessa forma, o novo proprietário pode fazer o que quiser com o arquivo, incluindo movê-lo.

Este diretório gravável por todos pode pertencer ao diretório inicial do usuário, caso você queira usar vários sistemas de arquivos para diretórios pessoais e queira garantir que não ultrapasse os limites do sistema de arquivos, pois o desempenho seria imediatamente terrível. Nesse caso, você provavelmente desejará garantir que o destinatário saiba quando um novo arquivo é oferecido.

E-mails seriam suficientes. Uma solução mais Unixy seria /etc/profileaquela que lista seus arquivos entregues recentemente. Bônus adicional se você oferecer esse recurso com pam_echo( por exemplofile=/tmp/deliveries/%u , com , consulte pam_echo(8)). Como em qualquer coisa relacionada ao PAM, convém verificar se todas as suas implementações oferecem esse módulo primeiro.

Pierre Carrier
fonte
0

Você pode usar um sistema com um diretório compartilhado (possivelmente sem permissões de execução.), Onde as coisas para um determinado usuário são arquivadas com uma estrutura de nome de arquivo específica ( to-$username_from-$username.tarpor exemplo). Give cria o arquivo e o arquivo chownspara o usuário alvo; pegue extrai o arquivo e o remove.

Se você quiser fazê-lo como uma mudança real (IE, alterar o local e as permissões do arquivo; sem copiar devido ao tamanho gigante do arquivo), poderá mudar para um diretório compartilhado com permissões -x (para que ninguém possa listar arquivos lá) e o mesmo chownmétodo. mv, chown/ mv.

zebediah49
fonte
0

Como o xryl669 diz, você pode usar um diretório para realmente compartilhar os arquivos. Deve ficar assim:

$ ls -ld shared
drwxrws--- 2 root usergroup 4096 somedate shared
$ ls -l shared
drwx-wx--- 2 user1 usergroup 4096 somedate user1
drwx-wx--- 2 user2 usergroup 4096 somedate user2
drwx-wx--- 2 user3 usergroup 4096 somedate user3
drwx-wx--- 2 user4 usergroup 4096 somedate user4

O comando give se torna

#!/bin/sh
#Use a random suffix to prevent guessing
RANDOM=$(dd if=/dev/urandom count=4 2> /dev/null | sha512sum | cut -d' ' -f1)
NEWNAME=/path/to/shared/$2/$1$RANDOM
#Move the file
mv $1 $NEWNAME
#Make it readable
chmod 440 $NEWNAME

O comando take é mais ou menos assim:

$ cd /path/to/shared/user
$ ls
...
$ mv somefile ~
miniBill
fonte
0

Eu sugiro reescrever o aplicativo para simular um "dar" e "receber", mas sim "empurrar" e "puxá-lo" de um diretório protegido. Seu diretório pode ser acessível apenas ao aplicativo push / pull - que lida com as movimentações do arquivo. Como alternativa, seu aplicativo / script pode criar um diretório temporário aleatório, com permissões definidas para o remetente e o destinatário.

Deseja ter mais segurança? Você pode criptografar / assinar o PGP (usando a chave pública do receptor).

Em termos de refazê-lo de um "ponto de vista funcional e de segurança", sugiro fortemente que não crie programas SUID. Se você não remover privilégios de maneira adequada, poderá acessar virtualmente qualquer arquivo no sistema. Se o seu programa estiver com erros (buffer overflow, etc ...) - pode-se explorar isso para obter acesso root no seu sistema.

ndrix
fonte
0

Provavelmente, isso não serve para você, mas, para referência, o cp --reflink source target faz cópias finas dos arquivos usando a cópia na gravação.

Isso significa que você pode copiar o arquivo imediatamente e apenas os blocos alterados serão realmente copiados. Ao contrário de um link físico, o novo arquivo possui seu próprio inode e metadados, o que significa que você pode fornecer a cópia do arquivo para o novo usuário usando material de chown padrão.

Tanto quanto sei, esse é um recurso disponível apenas no OCFS2 e no btrfs atualmente. Eu acho que isso resolve o seu problema, mas, como a disponibilidade dele não é generalizada, provavelmente não será útil.

Matthew Ife
fonte