Moulette 2018 !

This commit is contained in:
nemunaire 2018-11-07 12:23:01 +01:00
parent 50cbff18eb
commit 33877c12ba
5 changed files with 192 additions and 65 deletions

View File

@ -1,4 +1,4 @@
SOURCES = subject.md project-part1.md project-part2.md rendu.md end.md
SOURCES = subject.md project-part1.md project-part2.md sample.md rendu.md end.md
PANDOCOPTS = --latex-engine=xelatex \
--standalone \
--normalize \

View File

@ -1,4 +1,4 @@
### Palier 1 : Restreindre l'environnement (2 points)
## Palier 1 : Restreindre l'environnement (2 points) {.unnumbered}
Après avoir mis en place les bases de votre programme, commencez par créer les
différentes hiérarchies (si vous avez un noyau récent, vous pouvez utiliser les
@ -17,28 +17,28 @@ moulinette ne possède pas tous ces *CGroup*s, au lieu de planter, ne rien faire
n'est pas forcément une mauvaise solution.
### Palier 2 : Réduire les *capabilities* (2 points)
## Palier 2 : Réduire les *capabilities* (2 points) {.unnumbered}
Réduisez au maximum les *capabilities*, de telle sorte qu'il ne soit pas
possible de faire un ping dans l'environnement restreint :
<div lang="en-US">
```shell
42sh# ping 8.8.8.8
PING 8.8.8.8 (8.8.8.8) 56(84) bytes of data.
64 bytes from 8.8.8.8: icmp_seq=1 ttl=56 time=3.93 ms
64 bytes from 8.8.8.8: icmp_seq=2 ttl=56 time=3.97 ms
^C
--- 8.8.8.8 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1002ms
rtt min/avg/max/mdev = 3.931/3.954/3.978/0.067 ms
42sh# ping 9.9.9.9
PING 9.9.9.9 (9.9.9.9) 56(84) bytes of data.
64 bytes from 9.9.9.9: icmp_seq=1 ttl=56 time=3.93 ms
64 bytes from 9.9.9.9: icmp_seq=2 ttl=56 time=3.97 ms
^C
--- 9.9.9.9 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1002ms
rtt min/avg/max/mdev = 3.931/3.954/3.978/0.067 ms
42sh# ./mymoulette /bin/bash
bash# curl http://www.linuxcontainers.org/ | md5sum
59e714c4331e71ac3529a6502994ef1d
42sh# ./mymoulette /bin/bash
bash# curl http://www.linuxcontainers.org/ | md5sum
c7d68d1cb4737125a84cd69f55add202
bash# ping 8.8.8.8
ping: icmp open socket: Permission denied
bash# ping 9.9.9.9
ping: icmp open socket: Permission denied
```
</div>
@ -48,14 +48,14 @@ Aidez-vous du visualisateur de *capabilities* de la partie 4, pour voir si vous
êtes sur la bonne voie.
### Palier 3 : Utilisable par un utilisateur (1 point)
## Palier 3 : Utilisable par un utilisateur (1 point) {.unnumbered}
Jouez avec les attributs étendus pour qu'un utilisateur non-privilégié puisse
exécuter votre moulinette. Ajoutez la/les commande(s) à votre Makefile ou
script d'installation.
### Création d'un environnement d'exécution minimal
## Création d'un environnement d'exécution minimal {.unnumbered}
Plutôt que d'utiliser votre système hôte au complet, avec tous ses programmes
et toutes ses bibliothèques, il faudrait utiliser un système contenant le
@ -66,15 +66,40 @@ dans la partie sur les *chroot*.
sera seulement utile pour faire des tests.**
### Palier 4 : Isolation du pauvre (1 point)
## Palier 4 : Isolation du pauvre (1 point) {.unnumbered}
Nous n'avons pas encore vu de meilleure méthode pour mieux isoler
l'environnement que de faire un `chroot`, ajoutez à votre programme cette
isolation rudimentaire. Et rendez-vous au prochain cours pour avoir une
meilleure isolation !
<div lang="en-US">
```shell
42sh$ which firefox
/usr/bin/firefox
42sh# ./mymoulette ./newrootfs/ /bin/bash
bash# which firefox
which: no firefox in (/usr/bin:/usr/local/bin:/bin:/opt/bin)
```
</div>
### Palier 5 (bonus) : automatisation de la création de l'environnement (5 points)
## Palier 5 : seccomp (2 points) {.unnumbered}
Filtrez les appels systèmes de telle sorte qu'aucun programme exécuté dans
votre bac à sable ne puisse plus lancer les appels systèmes suivants :
* `nfsservctl(2)` ;
* `personality(2)` ;
* `pivot_root(2)` ;
* ...
N'hésitez pas à en utiliser d'autres pour vos tests ;)
Astuces : `seccomp(2)`, `seccomp_init(3)`, `seccomp_load(3)`, ...
## Palier bonus : Automatisation de la création de l'environnement (5 points) {.unnumbered}
Pour *moulinéter* plusieurs étudiants en parallèle, vous allez avoir besoin de
plusieurs environnements identiques. Plutôt que de recopier cet environnement,
@ -86,3 +111,7 @@ L'usage est laissé à votre discrétion : vous pouvez ajouter un/des paramètre
votre *moulette* pour indiquer le volume LVM à utiliser ou le définir en dur ou
encore séparer la création de l'environnement et de la snapshot initiale dans
un programme distinct.
Si votre noyau dispose d'un UnionFS (AUFS ou OverlayFS par exemple), ou que
vous disposez d'une partition `btrfs`, vous pouvez utiliser l'une de ces
méthodes pour ajouter une couche en écriture, à la place de LVM.

View File

@ -1,7 +1,7 @@
### Palier 5 : Une vraie isolation (3 points)
## Palier 6 : Une vraie isolation (2 points) {.unnumbered}
En plus du `chroot`, assignez de nouveaux *namespaces* au processus que vous
allez lancer : `cgroups`, `IPC`, `mount`, `net`, `PID`, `UTS`, `user`.
allez lancer : `cgroups`, `IPC`, `mount`, `net`, `PID`, `UTS`.
Il est requis que le nouveau processus ne puisse pas s'échapper de ses
*namespaces* !
@ -9,7 +9,17 @@ Il est requis que le nouveau processus ne puisse pas s'échapper de ses
Astuce : `unshare(2)`.
### Palier 6 : Empêcher les fuites d'information (2 points)
## Palier bonus : Révolution des utilisateurs (2 points) {.unnumbered}
Utilisez le *namespace* `user` pour vous permettre de ne plus avoir besoin de
lancer votre moulinette en tant que `root` ou avec plus de *capabilities* que
nécessaire dans vos attributs étendus.
Vous aurez besoin de déplacer le code écrit pour les premiers paliers (cgroups,
caps, ...), après vous être dissocié de cet espace de noms.
## Palier 7 : Empêcher les fuites d'information (2 points) {.unnumbered}
Démontez tous les systèmes de fichiers qui ne sont pas nécessaires au
fonctionnement de votre conteneur et remontez les partitions
@ -20,33 +30,69 @@ opération est nécessaire afin de terminer l'étape d'isolation.
Astuce : `mount(2)`.
### Palier 7 : Identification du conteneur (1 point)
## Palier 7 bis : Volume attaché au code à moulinéter (1 point) {.unnumbered}
Ajoutez une option à votre moulinette afin de lier le dossier (qui se trouve
sur la machine hôte) contenant le code d'un étudiant, à l'intérieur du
conteneur. Cette option est similaire à l'option `--volume`/`-v` de Docker :
L'option devra attendre le répertoire contenant le code de l'étudiant, et le
monter dans `/home/student` :
<div lang="en-US">
```
42sh$ ./mymoulette ./newrootfs/ /bin/bash
bash# ls /home/student/
bash#
42sh$ ./mymoulette -v /var/lib/git/login_x/42sh/ ./newrootfs/ /bin/bash
bash# ls /home/student/
src/ tests/ AUTHORS configure Makefile.am README TODO
bash#
```
</div>
Astuce : `mount(2)`, `mkdir(2)`.
## Palier 8 : Identification du conteneur (1 point) {.unnumbered}
Maintenant que vous avez votre conteneur, personalisez-le un peu en lui donnant
un nom unique.
Astuce : `sethostname(2)`
<div lang="en-US">
```
42sh$ ./mymoulette ./newrootfs/ hostname
ush9ukohh3Ch
42sh$ ./mymoulette ./newrootfs/ hostname
shie6aif2aiH
```
</div>
### Palier 8 : `pivot_root` (4 points)
## Palier 9 : `pivot_root` (3 points) {.unnumbered}
Effectuez un `pivot_root(2)` de telle sorte qu'il ne reste plus de trace du
système de fichiers hôte.
Astuce : `pivot_root(2)`, `umount(2)`.
Attention : vos filtres `seccomp` filtrant l'appel système `pivot_root(2)`,
vous devrez donc ne les appliquer qu'après cette étape.
### Palier 9 : Bac à sable connecté (4 points)
## Palier 10 : Bac à sable connecté (2 points) {.unnumbered}
Partant d'une liste d'interfaces sur la machine hôte similaire à :
<div lang="en-US">
```
42sh$ ip link
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP mode DEFAULT group default qlen 1000
link/ether 90:2b:34:5e:fa:a7 brd ff:ff:ff:ff:ff:ff
42sh$ ip link
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP mode DEFAULT group default qlen 1000
link/ether 90:2b:34:5e:fa:a7 brd ff:ff:ff:ff:ff:ff
```
</div>
@ -54,23 +100,23 @@ Vous devrez pouvoir `ping`er votre conteneur depuis votre hôte :
<div lang="en-US">
```
42sh$ ip address
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1
[...]
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
[...]
3: veth3e06cad@if82: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP mode DEFAULT group default
link/ether 42:a2:a0:89:54:ef brd ff:ff:ff:ff:ff:ff
inet 10.10.10.41/24 brd 10.10.10.255 scope global veth3e06cad
valid_lft forever preferred_lft forever
42sh$ ping 10.10.10.42
PING 10.10.10.42 (10.10.10.42) 56(84) bytes of data.
64 bytes from 10.10.10.42: icmp_seq=1 ttl=56 time=3.90 ms
64 bytes from 10.10.10.42: icmp_seq=2 ttl=56 time=3.78 ms
^C
--- 10.10.10.42 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1003ms
rtt min/avg/max/mdev = 3.789/3.847/3.906/0.085 ms
42sh$ ip address
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1
[...]
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
[...]
3: veth3e06cad@if82: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP mode DEFAULT group default
link/ether 42:a2:a0:89:54:ef brd ff:ff:ff:ff:ff:ff
inet 10.10.10.41/24 brd 10.10.10.255 scope global veth3e06cad
valid_lft forever preferred_lft forever
42sh$ ping 10.10.10.42
PING 10.10.10.42 (10.10.10.42) 56(84) bytes of data.
64 bytes from 10.10.10.42: icmp_seq=1 ttl=56 time=3.90 ms
64 bytes from 10.10.10.42: icmp_seq=2 ttl=56 time=3.78 ms
^C
--- 10.10.10.42 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1003ms
rtt min/avg/max/mdev = 3.789/3.847/3.906/0.085 ms
```
</div>
@ -79,15 +125,3 @@ tandis que la machine hôte a l'IP `10.10.10.41`.
Astuces : vous pouvez utiliser la `libnetlink(3)` ou même faire des appels aux
programmes `ip(8)`, `brctl(8)`, ...
### Palier 10 (bonus) : seccomp (2 points)
Filtrez les appels systèmes de telle sorte qu'aucun programme exécuté dans
votre bac à sable ne puisse plus lancer les appels systèmes suivants :
* `nfsservctl(2)` ;
* `personality(2)` ;
* `pivot_root(2)`.
Astuce : `seccomp(2)`.

59
subject/2/sample.md Normal file
View File

@ -0,0 +1,59 @@
Exemples
========
## Arguments de la ligne de commande
<div lang="en-US">
```
42sh$ ./mymoulette -h
MyMoulette, the students' nightmare, now highly secured
Usage: ./mymoulette [-v student_workdir] environment moulette_prog [moulette_arg [...]]
environment is the path to the directory containing the new rootfs
moulette_prog will be the first program to be launched, must already be in the environment
student_workdir is the directory containing the code to grade
```
</div>
## Réseau accessible
<div lang="en-US">
```
42sh$ ip address show veth0l
2: veth0l@if82: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP mode DEFAULT group default
link/ether 42:a2:a0:89:54:ef brd ff:ff:ff:ff:ff:ff
inet 10.10.10.41/24 brd 10.10.10.255 scope global veth3e06cad
valid_lft forever preferred_lft forever
42sh$ ./mymoulette ./newrootfs/ /usr/bin/ip address show veth0r
2: veth0r@if82: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP mode DEFAULT group default
link/ether 42:a2:a0:89:55:ef brd ff:ff:ff:ff:ff:ff
inet 10.10.10.42/24 brd 10.10.10.255 scope global veth3e06cad
valid_lft forever preferred_lft forever
42sh$ ping -c 1 10.10.10.42
PING 10.10.10.42 (10.10.10.42) 56(84) bytes of data.
64 bytes from 10.10.10.42: icmp_seq=1 ttl=56 time=3.90 ms
--- 10.10.10.42 ping statistics ---
1 packets transmitted, 1 received, 0% packet loss, time 1003ms
rtt min/avg/max/mdev = 3.789/3.847/3.906/0.085 ms
```
</div>
<div lang="en-US">
```
42sh$ ./mymoulette ./newrootfs/ /usr/bin/curl http://www.linuxcontainers.org/ | md5sum
c7d68d1cb4737125a84cd69f55add202
```
</div>
## Capabilities limitées
<div lang="en-US">
```
42sh$ ./mymoulette ./newrootfs/ /bin/ping 9.9.9.9
ping: icmp open socket: Permission denied
```
</div>

View File

@ -1,14 +1,14 @@
---
title: Virtualisation légère -- Projet n^o^ 2
title: Virtualisation légère -- Projet
author: Pierre-Olivier *nemunaire* Mercier
institute: EPITA
date: EPITA -- SRS 2018
date: EPITA -- SRS 2019
...
Le laboratoire des assistants a besoin de votre expertise afin de renforcer la
sécurité et la réactivité de son système de correction automatisé.
Votre projet consistera à réaliser la partie d'isolation de la moulinette des
Votre mission consistera à réaliser la partie d'isolation de la moulinette des
ACUs : dans un premier temps vous ferez en sorte de restreindre un groupe de
processus pour qu'il ne puisse pas faire de déni de service sur notre machine ;
puis dans une seconde partie, vous vous assurerez de l'isolation de chaque
@ -17,7 +17,7 @@ puis dans une seconde partie, vous vous assurerez de l'isolation de chaque
\vspace{1em}
Il n'y a pas de restriction sur le langage utilisé, vous pouvez tout aussi bien
utiliser du C, du C++, du Python, du shell, etc.
utiliser du C, du C++, du Python, etc.
L'usage de bibliothèques **non relatives** au projet est autorisé : le but de
ce sujet est d'évaluer votre compréhension et votre utilisation de la
@ -28,6 +28,11 @@ plomberie, n'hésitez pas à l'utiliser !
\vspace{1em}
Ce projet est à rendre à <virli@nemunai.re> au plus tard le dimanche
26 novembre 2017 à 23 h 42.
25 novembre 2018 à 23 h 42.
\tableofcontents
\newpage
Paliers
=======