2018-10-17 18:42:13 +00:00
|
|
|
## Limiter les ressources
|
|
|
|
|
2018-10-19 23:51:25 +00:00
|
|
|
Lorsque l'on gère un environnement de production, on souhaite bien
|
|
|
|
évidemment éviter tout déni de service autant que possible. Ou
|
|
|
|
parfois, contenir un programme métier avec une fuite mémoire, dans
|
|
|
|
certaines limites : il vaut parfois mieux le tuer et le relancer
|
|
|
|
automatiquement, plutôt que d'attendre que potentiellement un autre
|
|
|
|
processus se fasse tuer à sa place.
|
2018-10-17 18:42:13 +00:00
|
|
|
|
2018-10-19 23:51:25 +00:00
|
|
|
Pour cela, Docker expose tout un arsenal, reposant sur les cgroups du
|
|
|
|
noyau Linux, que l'on verra plus en détail dans un prochain cours.
|
2018-10-17 18:42:13 +00:00
|
|
|
|
|
|
|
### Mémoire
|
|
|
|
|
2018-10-19 23:51:25 +00:00
|
|
|
Comme on peut s'y attendre, il est possible de limiter la mémoire que
|
|
|
|
peut occuper un conteneur avec l'option `-m`/`--memory`.
|
|
|
|
|
|
|
|
|
|
|
|
### CPU
|
|
|
|
|
|
|
|
En ce qui concerne la limitation d'utilisation du CPU, ce n'est pas
|
|
|
|
aussi simple. En effet, on ne peut pas définir le nombre
|
|
|
|
d'instructions par seconde qu'un conteneur est autorisé à consommer.
|
|
|
|
|
|
|
|
On ne peut définir qu'un taux d'utilisation relatif par rapport à
|
|
|
|
l'ensemble du système (ou du groupe de processus auquel il
|
|
|
|
appartient). Ce taux est appliqué par l'ordonnanceur, lorsqu'il
|
|
|
|
détermine la prochaine tâche qui sera exécutée.
|
|
|
|
|
|
|
|
Ainsi, lorsque la machine n'est pas chargée, que le processeur n'a pas
|
|
|
|
constamment du travail à effectuer, l'ordonnanceur ne va pas empêcher
|
|
|
|
une tâche très consommatrice en puissance de calcul de s'exécuter.
|
|
|
|
|
|
|
|
Par contre, sous une forte charge, si l'on défini que notre conteneur
|
|
|
|
exécutant un cpuburn ne peut pas utiliser plus de 50% des ressources
|
|
|
|
de la machine, ce pourcentage ne pourra effectivement pas être
|
|
|
|
dépassé, l'ordonnanceur privilégiant alors les autres processus du
|
|
|
|
système.
|
|
|
|
|
|
|
|
Par défaut, le taux maximal (1024 = 100%) d'utilisation CPU est donné
|
|
|
|
aux nouveaux conteneurs, on peut le réduire en utilisant l'option
|
|
|
|
`-c`/`--cpu-shares` : 512 = 50%, par exemple.
|
2018-10-17 18:42:13 +00:00
|
|
|
|
|
|
|
|
|
|
|
## Sécuriser l'exécution
|
|
|
|
|
2018-10-19 23:51:25 +00:00
|
|
|
En plus des dénis de service, on peut également vouloir se protéger
|
|
|
|
contre des attaques provenant des conteneurs eux-mêmes. On n'est pas à
|
|
|
|
l'abri d'une vulnérabilité dans un des services exécuté dans un
|
|
|
|
conteneur. Plusieurs mécanismes sont mis en place pour accroître la
|
|
|
|
difficulté du rebond.
|
|
|
|
|
|
|
|
### Capabilities
|
|
|
|
|
|
|
|
Un certain nombre de capabilities Linux sont retirées par Docker au
|
|
|
|
moment de l'exécution du conteneur, on peut utiliser les options
|
|
|
|
`--cap-add` et `--cap-drop` pour respectivement ajouter et retirer une
|
|
|
|
capabilities.
|
|
|
|
|
|
|
|
Notez que l'option `--privileged` ne retire aucune capabilities à
|
|
|
|
l'exécution.
|
|
|
|
|
|
|
|
Nous verrons dans un prochain cours exactement ce que permettent ces
|
|
|
|
capabilities.
|
|
|
|
|
2018-10-17 18:42:13 +00:00
|
|
|
|
|
|
|
### seccomp
|
|
|
|
|
2018-10-19 23:51:25 +00:00
|
|
|
Si les capabilities sont un regroupement grossiers de fonctionnalités
|
|
|
|
du noyau, seccomp est un filtre que l'on peut définir pour chaque
|
|
|
|
appel système. Liste blanche, liste noire, tout est possible.
|
|
|
|
|
|
|
|
Docker filtre notamment tous les appels systèmes qui pourraient
|
|
|
|
débordés à l'extérieur du conteneur : il n'est par exemple pas
|
|
|
|
possible de changer l'heure dans un conteneur, car il n'y a
|
|
|
|
aujourd'hui aucun mécanisme pour isoler les visions des dates d'un
|
|
|
|
conteneur à l'autre.
|
|
|
|
|
|
|
|
Voici par exemple un fichier de profil seccomp, interdisant
|
|
|
|
l'utilisation de l'appel système `nanosleep(2)` (utilisé notamment par
|
|
|
|
`sleep(1)`) :
|
|
|
|
|
|
|
|
<div lang="en-US">
|
|
|
|
```js
|
|
|
|
{
|
|
|
|
"defaultAction": "SCMP_ACT_ALLOW",
|
|
|
|
"syscalls": [
|
|
|
|
{
|
|
|
|
"names": [
|
|
|
|
"nanosleep"
|
|
|
|
],
|
|
|
|
"action": "SCMP_ACT_ERRNO",
|
|
|
|
"args": [],
|
|
|
|
"comment": "",
|
|
|
|
"includes": {},
|
|
|
|
"excludes": {}
|
|
|
|
}
|
|
|
|
]
|
|
|
|
}
|
|
|
|
```
|
|
|
|
</div>
|
|
|
|
|
|
|
|
On peut ensuite l'appliquer à un conteneur Docker :
|
|
|
|
|
|
|
|
<div lang="en-US">
|
|
|
|
```
|
2018-11-16 01:38:41 +00:00
|
|
|
42sh$ docker container run -it --security-opt seccomp=nanosleep.json ubuntu /bin/bash
|
|
|
|
(cntnr)$ sleep 42
|
|
|
|
sleep: cannot read realtime clock: Operation not permitted
|
2018-10-19 23:51:25 +00:00
|
|
|
```
|
|
|
|
</div>
|