O que eu fiz aqui é testar se a raiz do init
processo (PID 1) é igual à raiz do processo atual. Embora /proc/1/root
seja sempre um link para /
(a menos que init
ele seja chrootado, mas esse não é um caso que me importe), segui-lo leva ao diretório raiz "mestre". Esta técnica é usada em alguns scripts de manutenção no Debian, por exemplo, para pular o início do udev após a instalação em um chroot.
if [ "$(stat -c %d:%i /)" != "$(stat -c %d:%i /proc/1/root/.)" ]; then
echo "We are chrooted!"
else
echo "Business as usual"
fi
(A propósito, este é mais um exemplo de por que chroot
é inútil para a segurança se o processo chroot tiver acesso root. Processos não raiz não podem ler /proc/1/root
, mas podem ser seguidos /proc/1234/root
se houver um processo em execução com o PID 1234 sendo executado da mesma forma. do utilizador.)
Se você não possui permissões de root, pode ver /proc/1/mountinfo
e /proc/$$/mountinfo
(brevemente documentado na documentação filesystems/proc.txt
do kernel do Linux ). Este arquivo é legível por todo o mundo e contém muitas informações sobre cada ponto de montagem na visualização do processo do sistema de arquivos. Os caminhos nesse arquivo são restritos pelo chroot que afeta o processo do leitor, se houver. Se a leitura do processo /proc/1/mountinfo
for chroot em um sistema de arquivos diferente da raiz global (supondo que a raiz do pid 1 seja a raiz global), nenhuma entrada para será /
exibida /proc/1/mountinfo
. Se a leitura do processo /proc/1/mountinfo
for chroot para um diretório no sistema de arquivos raiz global, uma entrada para /
aparecerá /proc/1/mountinfo
, mas com um ID de montagem diferente. Aliás, o campo raiz ($4
) indica onde o chroot está em seu sistema de arquivos mestre.
[ "$(awk '$5=="/" {print $1}' </proc/1/mountinfo)" != "$(awk '$5=="/" {print $1}' </proc/$$/mountinfo)" ]
Esta é uma solução Linux pura. Pode ser generalizável para outras variantes do Unix com uma similaridade suficiente /proc
(o Solaris tem uma similar /proc/1/root
, eu acho, mas não mountinfo
).