Linux - Criação de um ambiente OpenSSH-CHROOT

Linux - Criação de um ambiente OpenSSH-CHROOT

Mais uma vez agradeço à jipicy por sua disponibilidade e sua paciência para as correções lingüística.

I. Instalação de openssh-chroot

A. Download e verificação da assinatura

Criação de um repertório para o download dos arquivos

$ mkdir /home/lami20j/prisonssh   
$ cd /home/lami20j/prisonssh   
$ wget ftp://ftp.club-internet.fr/pub/OpenBSD/OpenSSH/portable/openssh-4.3p1.tar.gz*   
$ wget http://chrootssh.sourceforge.net/download/osshChroot-4.3p1.diff   
 

Parece que o patch não é disponível no endereço indicado. Olhe mais abaixo (Chap V. )

Nós estamos no /home/lami20j/prisonssh e, veja ali, o que o diretório contém :

$ ls -1   
openssh-4.3p1.tar.gz   
openssh-4.3p1.tar.gz.asc   
osshChroot-4.3p1.diff   
prisonssh.pl   
useradd_prisonssh.pl 

prisonssh.pl et useradd_prisonssh.pl são os dois scripts Perl que veremos mais abaixo.

Verificação da assinatura

$ gpg --keyserver pgp.mit.edu --recv-keys 0x86FF9C48   
gpg: consulta da chave 86FF9C48 do servidor hkp pgp.mit.edu   
gpg: clé 86FF9C48: nome de usuário duplo detectado  - fusão com sucesso   
gpg: clé 86FF9C48: chave publica « Damien Miller (Personal Key) » importada   
gpg: nenhuma chave de confiança última não foi encontrada.   
gpg: Quantidade tratada : 1   
gpg: importada: 1   

$ gpg --fingerprint 86FF9C48   
pub 1024D/86FF9C48 2001-02-26   
Impressão da chave = 3981 992A 1523 ABA0 79DB FC66 CE8E CB03 86FF 9C48   
uid Damien Miller (Personal Key)    
sub 2048g/AA2B1C41 2001-02-26   

$ gpg --verify openssh-4.3p1.tar.gz.asc openssh-4.3p1.tar.gz   
gpg: Assinatura feita quart feira 01 fév 2006 12:34:31 CET com a chave DSA ID 86FF9C48   
gpg: Boa assinatura de « Damien Miller (Personal Key) »   
gpg: Atenção : Esta chave não é certificada com uma assinatura de confiança !   
gpg: Nada diz que a assinatura pertence ao seu proprietário.   
Impressão da chave principal : 3981 992A 1523 ABA0 79DB FC66 CE8E CB03 86FF 9C48 

B. Instalação

Supressão dos pacotes instalados.

Debian :

# apt-get remove --purge ssh 

Mandriva2006 et Fedora :

# for i in $(rpm -qa | grep openssh);do rpm --nodeps -e $i;done 

Dependências exigidas: zlib et openssl
Leia o arquivo README para maiores detalhes. code>$ su
Password:
# cd /usr/local
# tar xzvf /home/lami20j/prisonssh/openssh-4.3p1.tar.gz
# cd openssh-4.3p1/
# patch < /home/lami20j/prisonssh/osshChroot-4.3p1.diff
patching file session.c
# ./configure
# make
# make install</code>

C. Ecrita do script de arranque para sshd

Com seu editor de texto preferido, criar o arquivo /etc/init.d/sshd
E escreva o seguinte script.
Depois da edição do arquivo terminado, registre e feche.

#!/bin/bash   

case $1 in   
'start' )   
        /usr/local/sbin/sshd   
        ;;   
'stop'  )   
        pkill sshd   
        ;;   

  • )

echo "usage : /etc/init.d/sshd {start|stop}" ;; esac

Estabeleça os direitos com o comando

# chmod -v 0755 /etc/init.d/sshd    

Se o usuário sshd não existe, você pode cria-lo com o comando :

# useradd -c 'Privilege-separated SSH' -d /var/empty/sshd -s /sbin/nologin sshd  

Lancçar o daemon

# /etc/init.d/sshd start 

Para que o arranque do daemon seja levado em consideração no arranque do PC feito :

# update-rc.d sshd start 99 2 3 4 5 . 

II. Criação de um ambiente chroot openssh

- o script prisonssh.pl

SYNOPSIS

# perl /caminho/para/script/prisonssh.pl    

Na solicitação do diretório coloque o nome de sua escolha.
O diretório sera criado no /home

#! /usr/bin/perl   
#   
use strict; use warnings;   

use File::Basename;   
my (@lib,@ldd,%listreplib);   
# criação do diretório   
print "Entre o nome de diretório: ";   
chomp(my $chroot_rep=<STDIN>);   
mkdir '/home/'.$chroot_rep   
or die "Impossível de criar o diretório: $!";   
# Os aplicativos de ambiente chroot   
#   
# Assegure--se que o caminho das aplicações mencionadas corresponde   
#   
# Por exemplo o comando  id   
# na Debian e Fedora5 o encontramos no /usr/bin   
#   
# no Mandriva 2006 no /bin   
#   
# cabe à você adicionar ou tirar aplicações   
# e, é claro, modificar o script   
#   
# as aplicações (/bin)    
my @apps0=qw (    
              /bin/bash   
              /bin/ls   
              /bin/mkdir   
              /bin/mv    
              /bin/pwd    
              /bin/rm   
              /bin/sh    
              /bin/echo    
              /bin/cp    
              /bin/cat    
              /bin/ln    
              /bin/chown   
              /bin/chmod    
              /bin/grep    
              /bin/more    
              /bin/tar   
              /bin/gzip    
              /bin/true    
              /bin/false   
              /bin/ping    
              /bin/egrep   
              /bin/hostname   
);   

# as aplicações (/usr/bin, etc...)   

my @apps1=qw (    
              /usr/local/bin/scp    
              /usr/bin/env    
              /usr/bin/clear    
              /usr/bin/wc    
              /usr/bin/perl    
              /usr/bin/id    
              /usr/local/bin/ssh   
              /usr/bin/du   
              /usr/bin/less   
              /usr/bin/bzip2   
              /usr/bin/tset   
);   

# o sub sistema sftp   
my @sftp_server=qw ( /usr/local/libexec/sftp-server );   

# recuperar as bibliotecas   
foreach (@apps0,@apps1,@sftp_server){   
    my $ldd='ldd $_';   
    my @temp=split /\n/, $ldd;   
    push @ldd,@temp;   
}   

# recuperar o caminho de cada biblioteca   
foreach(@ldd){   
    if ( $_=~/(?:\/?.*=>\s*)?(\/.*)\b\s*\(/ ){   
        print "$1\n";   
        push @lib,$1 if $1 !~ /^\s*$/;   
    }   
}   

# os diretórios à criar (/lib,/usr/lib,etc...)   
foreach(@lib){   
    my $replib=dirname($_);   
    $listreplib{$replib} +=1;   
}   

# criação dos diretórios no ambiente chroot   
foreach (keys %listreplib){   
    system "mkdir","-p","/home/$chroot_rep/$_";   
}   

# criação do diretório bin no ambiente chroot   
mkdir "/home/$chroot_rep/bin";   

my @rep=qw {    
            home usr/bin   
            usr/lib/locale   
            usr/share/locale   
            tmp   
            dev/pts   
            etc/pam.d   
            usr/local/libexec   
};   

foreach (@rep) {   
    system "mkdir", "-p", "/home/$chroot_rep/$_";   
}   

# copiar as aplicações no diretório /bin do ambiente  chroot   
foreach(@apps0){   
    system "cp","-p","$_","/home/$chroot_rep/bin";   
}   

# copiar as aplicações  nos diretórios /usr/bin do ambiente  chroot   
foreach(@apps1){   
    next if /.*sftp-server.*/i;   
    system "cp","-p","$_","/home/$chroot_rep/usr/bin";   
}   

# copiar sftp-server   
system "cp","-p","/usr/local/libexec/sftp-server","/home/$chroot_rep/usr/local/libexec";   

# copiar as bibliotecas   
foreach (@lib){   
    my $rep_lib=dirname($_);   
    system "cp","-p","$_","/home/$chroot_rep/$rep_lib";   
}   

opendir (LIBNSS,"/lib")   
        or die "Impossível de abrir o diretório: $!";   
while (defined (my $libnss = readdir(LIBNSS))) {   
    next unless $libnss=~/libnss.*/;   
    system "cp","-p","/lib/$libnss","/home/$chroot_rep/lib";   
}    

#   
system "cp","-RPp","/usr/share/terminfo","/home/$chroot_rep/usr/share";   

#   
system "mknod","-m","0666","/home/$chroot_rep/dev/null","c","1","3";   
system "mknod","-m","0666","/home/$chroot_rep/dev/zero","c","1","5";   
system "mknod","-m","0444","/home/$chroot_rep/dev/urandom","c","1","9";   
system "mknod","-m","0666","/home/$chroot_rep/dev/tty","c","5","0";   
system "mknod","-m","0666","/home/$chroot_rep/dev/ptmx","c","5","2";   

#   
my @etc_conf=qw(   
                nsswitch.conf host.conf resolv.conf bashrc termcap    
                hosts localtime login.defs profile tsocks.conf   
);   

foreach (@etc_conf){   
    system "cp","/etc/$_","/home/$chroot_rep/etc";   
}   

#   
system "cp","-R","/usr/lib/perl5","/home/$chroot_rep/usr/lib";   

#   
my @pamd=qw(   
            other   
);   

foreach (@pamd){   
    system "cp","/etc/pam.d/$_","/home/$chroot_rep/etc/pam.d";   
}   

# Criação dos arquivos padrão   
{   
open ETCPASSWD,"> /home/$chroot_rep/etc/passwd"   
        or die "Impossível de criar o arquivo: $!\n";   

print ETCPASSWD "root:x:0:0::/:/bin/bash\n";   

open ETCGROUP,"> /home/$chroot_rep/etc/group"   
        or die "Impossível de criar o arquivo: $!\n";   

print ETCGROUP "root:x:0:\n"   
}

III. Criação de usuários

-o script useradd_prisonssh.pl

SYNOPSIS

# perl /chemin/vers/script/useradd_prisonssh.pl nome_usuário diretório   

Para o diretório utilize o nome do diretório que você cria com o script prisonssh.pl (sem areborescência)

#! /usr/bin/perl    
#   
use strict;use warnings;   

die "Uso: \n\t$0 nome_usurio chroot-dir\n" unless @ARGV == 2;   

my $user = $ARGV[0];   
my $chroot = "/home/$ARGV[1]";   

system "groupadd", "$user";   
system "useradd", "-d", "$chroot/./home/$user", "-g", "$user", "-m", "-s", "/bin/bash", "$user";   

open PASSWD,">>$chroot/etc/passwd"   
        or die "E/S : $!\n";   

#   
my ($u) = grep { /$user/ } 'cat /etc/passwd';   
$u =~ s/[^:]*\.//;   

print PASSWD $u;   

#   
open GROUP,">>$chroot/etc/group"   
         or die "E/S : $!\n";   

print GROUP grep { /$user/ } 'cat /etc/group';   

#   
chmod 0700, "$chroot/home/$user";   
system "chown", "-R", "$user:$user", "$chroot/home/$user";   

#   
print "Entre a senha para $user\n";   

system "passwd", "$user";   

print "O usuário < $user > foi criado com sucesso.\n";   
 

IV. Com as mãos nos subterrâneos ou uma olhadela em baixo do capô

O acontece afinal de contas?

O patch que se aplica para permiter à openssh criar este ambiente e que se pode chamar uma prisão.

Trata-se de uma mini arborescência Linux que se encontrará no diretório/home.
Esta arborescência contém os diretórios e os programas necessários para abertura de uma conexão que não permite sair da (/home/prison)

Então depois de estar conectado você está preso em /home/prison qui est la racine / para nosso mini ambiente graças ao patch que se utilizou.
Se você olhar o verdadeiro arquivo /etc/passwd você irá perceber que os usuários criados com o script useradd_prison.pl tem o diretório home escrito com a seguinte sintaxe: /home/prisão/./home/usuário.

Você pode testar a conexão com ssh -v usuário@localhost

Até o momento o arquivo de configuração ( /usr/local/etc/sshd_config )
Não foi modificado, então a autenticação se fera com a senha.
Se você quer uma autenticação para a chave privada/publica.
Cabe à você modificar o arquivo de modificação.

Tudo o que eu descrevi foi testado nas distribuições GNU/Linux :
Mandriva2006, Fedora5 e Debian Sarge 3.1 com Perl versão 5.8.4 e superior

 

V. O patch osshChroot-4.3p1.diff

--- openssh-4.3p1/session.c 2005-12-24 04:59:12.000000000 +0100   
+++ openssh-4.3p1-chroot/session.c 2006-02-02 13:39:03.000000000 +0100   
@@ -59,6 +59,8 @@   
 #include "kex.h"   
 #include "monitor_wrap.h"   
    
+#define CHROOT   
+   
 #if defined(KRB5) && defined(USE_AFS)   
 #include <kafs.h>   
 #endif   
@@ -1251,6 +1253,11 @@   
 void   
 do_setusercontext(struct passwd *pw)   
 {   
+#ifdef CHROOT   
+       char *user_dir;   
+       char *new_root;   
+#endif /* CHROOT */   
+   
 #ifndef HAVE_CYGWIN   
  if (getuid() == 0 || geteuid() == 0)   
 #endif /* HAVE_CYGWIN */   
@@ -1308,6 +1315,27 @@   
    restore_uid();   
   }   
 #endif   
+   
+#ifdef CHROOT   
+       user_dir = xstrdup(pw->pw_dir);   
+       new_root = user_dir + 1;   
+   
+       while((new_root = strchr(new_root, '.')) != NULL) {   
+               new_root--;   
+               if(strncmp(new_root, "/./", 3) == 0) {   
+                       *new_root = '\0';   
+                       new_root += 2;   
+   
+                       if(chroot(user_dir) != 0)   
+                               fatal("Couldn't chroot to user's directory %s", user_dir);   
+                       pw->pw_dir = new_root;   
+                       break;   
+               }   
+   
+               new_root += 2;   
+       }   
+#endif /* CHROOT */   
+   
 # ifdef USE_PAM   
   /*   

  • PAM credentials may take the form of supplementary groups.

VI.O patch osshChroot-4.5p1.diff

Original patch by Ricardo Cerqueira <rmcc@clix.pt>   

Updated by Pierre Schiesser <pierre.schiesser@gmail.com> for OpenSSH-4.5p1   

A patch to cause sshd to chroot when it encounters the magic token   
'/./' in a users home directory. The directory portion before the   
token is the directory to chroot() to, the portion after the   
token is the user's home directory relative to the new root.   

Patch source using: patch -p0 < /path/to/patch   

Systems with a bad diff (doesn't understand -u or -N) should use gnu diff.   
Solaris may store this as gdiff under /opt/sfw/bin. I can't say much about   
other systems (unless you email me your experiences!).   

================================================================================   
--- openssh-4.5p1/session.c 2006-10-23 19:01:56.000000000 +0200   
+++ openssh-4.5p1-chroot/session.c 2006-11-07 21:33:12.000000000 +0100   
@@ -88,6 +88,8 @@   
 #include "kex.h"   
 #include "monitor_wrap.h"   
    
+#define CHROOT   
+   
 #if defined(KRB5) && defined(USE_AFS)   
 #include <kafs.h>   
 #endif   
@@ -1287,6 +1289,11 @@   
 void   
 do_setusercontext(struct passwd *pw)   
 {   
+#ifdef CHROOT   
+       char *user_dir;   
+       char *new_root;   
+#endif /* CHROOT */   
+   
 #ifndef HAVE_CYGWIN   
  if (getuid() == 0 || geteuid() == 0)   
 #endif /* HAVE_CYGWIN */   
@@ -1344,6 +1351,27 @@   
    restore_uid();   
   }   
 #endif   
+   
+#ifdef CHROOT   
+       user_dir = xstrdup(pw->pw_dir);   
+       new_root = user_dir + 1;   
+   
+       while((new_root = strchr(new_root, '.')) != NULL) {   
+               new_root--;   
+               if(strncmp(new_root, "/./", 3) == 0) {   
+                       *new_root = '\0';   
+                       new_root += 2;   
+   
+                       if(chroot(user_dir) != 0)   
+                               fatal("Couldn't chroot to user's directory %s", user_dir);   
+                       pw->pw_dir = new_root;   
+                       break;   
+               }   
+   
+               new_root += 2;   
+       }   
+#endif /* CHROOT */   
+   
 # ifdef USE_PAM   
   /*   

  • PAM credentials may take the form of supplementary groups.

Tradução feita por Ana Spadari

Nosso conteúdo é produzido em colaboração com especialistas em tecnologia da informação sob o comando de Jean-François Pillou, fundador do CCM.net. CCM é um site sobre tecnologia líder em nível internacional e está disponível em 11 idiomas.
Este documento, intitulado ' Linux - Criação de um ambiente OpenSSH-CHROOT', está disponível sob a licença Creative Commons. Você pode copiar e/ou modificar o conteúdo desta página com base nas condições estipuladas pela licença. Não se esqueça de creditar o CCM (br.ccm.net) ao utilizar este artigo.

Assine nossa newsletter!

Assine nossa newsletter!
Junte-se à comunidade