Il comando chroot può mandarti in prigione, mantenere isolati i tuoi ambienti di sviluppo o test o semplicemente migliorare la sicurezza del tuo sistema. Ti mostriamo il modo più semplice per usarlo.
Sommario:
Cos’è un chroot?
Se provi a misurare l’utilità di un comando, devi tenere conto delle funzionalità che fornisce e della sua facilità d’uso. Se è troppo complicato da usare per le persone o troppo prolisso per convincerli a provare a usarlo, la funzionalità potrebbe anche essere zero. Se nessuno lo usa, non fornisce alcuna funzionalità.
Nelle discussioni con utenti Linux, di persona e sui forum, sembra che il comando chroot sia considerato difficile da usare o troppo perspicace e noioso da configurare. Sembra che questa fantastica utility non sia utilizzata quanto potrebbe essere.
Con chroot puoi configurare e eseguire programmi o shell interattive come Bash in un filesystem incapsulato a cui è impedito di interagire con il tuo normale filesystem. Tutto all’interno dell’ambiente chroot è racchiuso e contenuto. Niente nell’ambiente chroot può vedere oltre la propria directory di root speciale senza passare ai privilegi di root. Ciò ha fatto guadagnare a questo tipo di ambiente il soprannome di una prigione chroot. Il termine “prigione” non deve essere confuso con FreeBSD’s comando jail, che crea un ambiente chroot questo è più sicuro rispetto al solito ambiente chroot.
Ma in realtà, c’è un modo molto semplice per usare chroot, che esamineremo. Stiamo usando normali comandi Linux che funzioneranno su tutte le distribuzioni. Alcune distribuzioni Linux hanno strumenti dedicati per configurare ambienti chroot, come debootstrap per Ubuntu, ma qui siamo indipendenti dalla distribuzione.
Quando dovresti usare un chroot?
Un ambiente chroot fornisce funzionalità simili a quelle di una macchina virtuale, ma è una soluzione più leggera. Il sistema captive non necessita di un hypervisor per essere installato e configurato, ad esempio VirtualBox o Virtual Machine Manager. Né è necessario avere un kernel installato nel sistema captive. Il sistema captive condivide il kernel esistente.
In un certo senso, gli ambienti chroot sono più vicini a contenitori come LXC rispetto alle macchine virtuali. Sono leggeri, veloci da implementare e la creazione e il lancio di uno può essere automatizzato. Come i contenitori, un modo conveniente per configurarli è installare quel tanto che basta del sistema operativo per eseguire ciò che è richiesto. Alla domanda “cosa è richiesto” si risponde osservando come si utilizzerà l’ambiente chroot.
Alcuni usi comuni sono:
Sviluppo software e verifica del prodotto. Gli sviluppatori scrivono il software e il team di verifica del prodotto (PV) lo testa. A volte vengono rilevati problemi da PV che non possono essere replicati sul computer dello sviluppatore. Lo sviluppatore ha tutti i tipi di strumenti e librerie installati sul proprio computer di sviluppo che l’utente medio, e il PV, non avranno. Spesso, un nuovo software che funziona per lo sviluppatore ma non per altri risulta utilizzare una risorsa sul PC dello sviluppatore che non è stata inclusa nella versione di prova del software. chroot consente agli sviluppatori di avere un semplice ambiente captive vanilla sul proprio computer in cui possono immergere il software prima di darlo a PV. L’ambiente captive può essere configurato con le dipendenze minime richieste dal software.
Riduzione del rischio di sviluppo. Lo sviluppatore può creare un ambiente di sviluppo dedicato in modo che nulla di ciò che accade al suo interno possa rovinare il suo vero PC.
Esecuzione di software obsoleto. A volte devi solo avere una vecchia versione di qualcosa in esecuzione. Se il vecchio software ha requisiti che sarebbero in conflitto o incompatibili con la propria versione di Linux, è possibile eseguire il chroot di un ambiente per il software problematico.
Ripristino e aggiornamenti del file system: se un’installazione di Linux diventa inutilizzabile, è possibile utilizzare chroot per montare il file system danneggiato su un punto di montaggio su un Live CD. Ciò ti consente di lavorare nel sistema danneggiato e tentare di ripararlo come se fosse montato normalmente su root /. Ciò significa che i percorsi dei file previsti all’interno del sistema danneggiato verranno referenziati correttamente dalla directory principale e non dal punto di montaggio del Live CD. Una tecnica simile è stata utilizzata nell’articolo che descrive come migrare il filesystem Linux da ext2 o ext3 a ext4.
Applicazioni ringfencing. L’esecuzione di un server FTP o di un altro dispositivo connesso a Internet all’interno di un ambiente chroot limita i danni che un utente malintenzionato esterno può causare. Questo può essere un passo prezioso per rafforzare la sicurezza del tuo sistema.
Creazione di un ambiente chroot
Abbiamo bisogno di una directory che funga da directory principale dell’ambiente chroot. In modo da avere un modo abbreviato per fare riferimento a quella directory, creeremo una variabile e memorizzeremo il nome della directory in essa. Qui stiamo impostando una variabile per memorizzare un percorso alla directory “testroot”. Non importa se questa directory non esiste ancora, la creeremo presto. Se la directory esiste, dovrebbe essere vuota.
chr=/home/dave/testroot
Se la directory non esiste, dobbiamo crearla. Possiamo farlo con questo comando. L’opzione -p (genitori) garantisce che tutte le directory padre mancanti vengano create contemporaneamente:
mkdir -p $chr
Dobbiamo creare directory per contenere le parti del sistema operativo che il nostro ambiente chroot richiederà. Creeremo un ambiente Linux minimalista che utilizzi Bash come shell interattiva. Includeremo anche i comandi touch, rm e ls. Questo ci consentirà di utilizzare tutti i comandi incorporati di Bash e touch, rm e ls. Saremo in grado di creare, elencare e rimuovere file e utilizzare Bash. E, in questo semplice esempio, è tutto.
Elenca le directory che devi creare all’interno di {} espansione del tutore.
mkdir -p $chr/{bin,lib,lib64}
Ora cambieremo directory nella nostra nuova directory root.
cd $chr
Copiamo i binari di cui abbiamo bisogno nel nostro ambiente Linux minimalista dalla normale directory “/ bin” nella nostra directory chroot “/ bin”. L’opzione -v (verbose) fa in modo che cp ci dica cosa sta facendo mentre esegue ogni azione di copia.
cp -v /bin/{bash,touch,ls,rm} $chr
I file vengono copiati per noi:
Questi binari avranno dipendenze. Dobbiamo scoprire cosa sono e copiare anche quei file nel nostro ambiente, altrimenti bash, touch, rm e ls non saranno in grado di funzionare. Dobbiamo farlo a turno per ciascuno dei nostri comandi scelti. Faremo prima Bash. Il comando ldd lo farà elenca le dipendenze per noi.
ldd /bin/bash
Le dipendenze vengono identificate ed elencate nella finestra del terminale:
Dobbiamo copiare quei file nel nostro nuovo ambiente. Scegliere i dettagli da quell’elenco e copiarli uno alla volta richiederà molto tempo e sarà soggetto a errori.
Per fortuna, possiamo semi-automatizzarlo. Elencheremo di nuovo le dipendenze e questa volta formeremo un elenco. Quindi eseguiremo un ciclo nell’elenco copiando i file.
Qui stiamo usando ldd per elencare le dipendenze e inserire i risultati attraverso una pipe in egrep. Usare egrep equivale a usare grep con l’opzione -E (espressioni regolari estese). L’opzione -o (solo corrispondenza) limita l’output alle parti corrispondenti delle righe. Stiamo cercando file di libreria corrispondenti che terminano con un numero [0-9].
list="$(ldd /bin/bash | egrep -o '/lib.*.[0-9]')"
Possiamo controllare il contenuto della lista usando echo:
echo $list
Ora che abbiamo l’elenco, possiamo scorrerlo con il seguente ciclo, copiando i file uno alla volta. Stiamo usando la variabile i per scorrere l’elenco. Per ogni membro della lista, copiamo il file nella nostra directory root chroot che è il valore contenuto in $ chr.
L’opzione -v (verbose) fa sì che cp annunci ogni copia mentre la esegue. L’opzione –parents assicura che tutte le directory padre mancanti vengano create nell’ambiente chroot.
for i in $list; do cp -v --parents "$i" "${chr}"; done
E questo è l’output:
Useremo questa tecnica per catturare le dipendenze di ciascuno degli altri comandi. E useremo la tecnica del loop per eseguire la copia effettiva. La buona notizia è che dobbiamo solo apportare una piccola modifica al comando che raccoglie le dipendenze.
Possiamo recuperare il comando dalla nostra cronologia dei comandi premendo il tasto Freccia su alcune volte e quindi apportare la modifica. Il comando di copia in loop non ha bisogno di cambiare affatto.
Qui abbiamo usato il tasto Freccia su per trovare il comando e lo abbiamo modificato per dire touch invece di bash.
list="$(ldd /bin/touch | egrep -o '/lib.*.[0-9]')"
Ora possiamo ripetere lo stesso identico comando di ciclo di prima:
for i in $list; do cp -v --parents "$i" "${chr}"; done
E i nostri file vengono copiati per noi:
Ora possiamo modificare la riga di comando dell’elenco per ls:
list="$(ldd /bin/ls | egrep -o '/lib.*.[0-9]')"
Ancora una volta, useremo lo stesso comando loop. Non importa quali file ci sono nell’elenco. Funziona alla cieca attraverso l’elenco copiando i file per noi.
for i in $list; do cp -v --parents "$i" "${chr}"; done
E le dipendenze per ls vengono copiate per noi:
Modifichiamo la riga di comando della lista per l’ultima volta, facendola funzionare per rm:
list="$(ldd /bin/ls | egrep -o '/lib.*.[0-9]')"
Usiamo il comando di copia in loop un’ultima volta:
for i in $list; do cp -v --parents "$i" "${chr}"; done
L’ultima delle nostre dipendenze viene copiata nel nostro ambiente chroot. Siamo finalmente pronti per usare il comando chroot. Questo comando imposta la radice dell’ambiente chroot e specifica quale applicazione eseguire come shell.
sudo chroot $chr /bin/bash
Il nostro ambiente chroot è ora attivo. Il prompt della finestra del terminale è cambiato e la shell interattiva è gestita dalla shell bash nel nostro ambiente.
Possiamo provare i comandi che abbiamo portato nell’ambiente.
ls
ls /home/dave/Documents
Il comando ls funziona come ci aspetteremmo quando lo usiamo nell’ambiente. Quando proviamo ad accedere a una directory al di fuori dell’ambiente, il comando fallisce.
Possiamo usare touch per creare un file, ls per elencarlo e rm per rimuoverlo.
touch sample_file.txt
ls
rm sample_file.txt
ls
Naturalmente, possiamo anche usare i comandi incorporati forniti dalla shell Bash. Se digiti help nella riga di comando, Bash li elencherà per te.
help
Usa exit per uscire dall’ambiente chroot:
exit
Se vuoi rimuovere l’ambiente chroot, puoi semplicemente eliminarlo:
rm -r testroot/
Questo cancellerà ricorsivamente i file e le directory nell’ambiente chroot.
Automatizza per comodità
Se stai pensando che gli ambienti chroot potrebbero esserti utili, ma sono un po ‘complicati da configurare, ricorda che puoi sempre eliminare lo sforzo e il rischio di attività ripetitive utilizzando alias, funzioni e script.