La gestion des ressources a pour objectif d'encadrer la consommation d'un environnement spécifique, que ce soit par le haut (limitation des ressources accessibles à cet environnement) ou par le bas (garantie d'accès à un minimum de ressources). C'est un sujet qui s'impose de plus en plus, et en particulier dans les environnements virtualisés.

Dans le monde Sun, on parle de containers dès qu'un environnement subit un quelconque encadrement de ressources. Cet environnement peut être une zone Solaris 10, mais aussi un projet ou une tâche, qui sont deux notions propres à Solaris 10 permettant de distinguer des workloads différents. En Solaris 8, l'utilisation du Solaris Resource Manager pour encadrer la consommation CPU d'un utilisateur par le biais des lnodes est également appelée container.

Cet article est un petit tour d'horizon de ce qui est actuellement disponible en matière de gestion de ressources dans Solaris 10. Il se limite volontairement au niveau des zones : les projets et les tâches s'appuient sur les mêmes mécanismes, et seront abordés dans un autre article.

Capping mémoire

Le daemon rcapd

Le capping mémoire permet de plafonner la consommation mémoire. Il peut se configurer statiquement dans la zone, et dynamiquement par l’intermédiaire de la commande rcapadm. Quel que soit le mode de configuration retenu, c’est le daemon rcapd qui appliquera les limites définies. L’activation du daemon se fait dans la zone globale par la commande :

# rcapadm –E

et la désactivation par :

# rcapadm –D

Outre le démarrage et l’arrêt du daemon, ces commandes activent ou désactivent le lancement du daemon au reboot de la zone globale.

Un autre paramètre important du rcapd se définit avec rcapadm : l’enforcement cap, qui correspond au pourcentage de la mémoire physique qui doit être réellement occupé pour que le rcapd se déclenche. Par défaut, cette valeur est à zéro, ce qui signifie que les limites sont toujours actives. Si on le passe à 90% avec la commande suivante, les limites ne seront appliquées qu’à partir du moment où il restera moins de 10% de mémoire physique libre (90% occupée) :

# rcapadm –c 90

Configuration statique.

La configuration statique se fait directement avec zonecfg :

# zonecfg –z mazone zonecfg:mazone> add capped-memory zonecfg:mazone:capped-memory> set physical=512M zonecfg:mazone:capped-memory> set swap=512M zonecfg:mazone:capped-memory> set locked=512M zonecfg:mazone:capped-memory> end zonecfg:mazone> exit

Les différents éléments fixés sont :

  • physical : la mémoire résidente (RAM) utilisable par la zone
  • swap : l’espace de swap que la zone pourra s’allouer
  • locked : la quantité maximale d’espace mémoire qui peut être verrouillée (mémoire qui ne sera jamais transférée vers le swap, typiquement ISM/DISM)

Cette configuration ne prendra effet que lors du reboot de la zone.

Configuration dynamique

La configuration dynamique peut s’appliquer sur une zone active, et se fait par la commande suivante :

# rcapadm –z mazone –m 512m

La mise à jour n’est pas instantanée, le daemon ne relisant sa configuration que toutes les minutes (par défaut, ça peut se modifier avec l’option –i config).

Attention : réduire la capacité mémoire d’une zone notablement en-deçà de ce qu’elle utilise au moment de l’opération va générer une forte activité de pagination, et donc une charge CPU élevée. Pire, il est possible que la zone essaie de se réallouer de la mémoire immédiatement, se fasse bloquer par le rcapd, et que son allocation mémoire joue au yoyo pendant un moment.

Afficher l’état du capping

Pour voir en temps réel la configuration du rcapd et l’utilisation de la mémoire, dans la zone globale :

# rcapstat –z id zone nproc vm rss cap at avgat pg avgpg 34 mazone - 20M 21M 512M 0K 0K 0K 0K

Partage CPU avec FSS

FSS : le Fair Share Scheduler

Le FSS est un algorithme d’ordonnancement qui peut remplacer l’algorithme par défaut (TS, pour Timeshare). Il permet d’attribuer des poids respectifs à des groupes d’éléments, par exemple des utilisateurs, des projets, ou encore des zones, ces dernières étant le cas qui nous intéresse ici. En pratique, ces poids relatifs définissent la proportion de CPU à laquelle chaque zone pourra prétendre, en cas de contention. L’algorithme ne rentrera en jeu que si le CPU est saturé, sinon, chaque zone pourra utiliser les ressources sans contraintes.

Par ailleurs, il est à noter que ces poids relatifs peuvent avoir n’importe quel total : rien n’oblige à ce que ce total soit 100, par exemple.

Changer d’algorithme d’ordonnancement requiert un reboot. Pour choisir un algorithme, on utilise la commande suivante :

# dispadmin –d FSS

Pour visualiser l’ordonnanceur par défaut actuellement configuré :

# dispadmin –d FSS (Fair Share)

Configuration statique

La configuration statique se fait directement avec zonecfg :

# zonecfg –z mazone zonecfg:mazone> set cpu-shares=50 zonecfg:mazone> exit

Comme précédemment, la configuration de la zone ne sera relue que lors d’un reboot.

Configuration dynamique

Il est également possible de modifier dynamiquement le nombre de shares affectées à une zone avec la commande prctl :

# prctl –i zone –n zone.cpu-shares –r –v 80 mazone

S’il s’agit d’un premier positionnement du contrôle (autrement dit, pas de cpu-shares déclarés auparavant), il faut remplacer le –r par un –s :

# prctl –i zone –n zone.cpu-shares –s –v 80 mazone

Afficher la configuration actuelle

On peut également utiliser la commande prctl pour consulter les contrôles positionnés :

# prctl –i zone mazone zone: 34: mazone NAME PRIVILEGE VALUE FLAG ACTION RECIPIENT zone.max-swap system 16.0EB max deny - zone.max-locked-memory system 16.0EB max deny - zone.max-shm-memory system 16.0EB max deny - zone.max-shm-ids system 16.8M max deny - zone.max-sem-ids system 16.8M max deny - zone.max-msg-ids system 16.8M max deny - zone.max-lwps system 2.15G max deny - zone.cpu-shares privileged 80 - none - system 65.5K max none

On peut enfin chercher un contrôle spécifique :

# prctl -i zone -n zone.cpu-shares mazone zone: 34: mazone NAME PRIVILEGE VALUE FLAG ACTION RECIPIENT zone.cpu-shares privileged 80 - none - system 65.5K max none -

Processeurs dédiés

Principe

L’idée est, comme son nom l’indique, de dédier un ou plusieurs processeurs à une zone. Ces processeurs seront utilisables exclusivement par elle, et cachés à toutes les autres zones, à l'exception de la zone globale.

A l’inverse, cette zone ne verra plus que son ou ses processeurs dédiés, sans accès aux autres processeurs.

Configuration

Ce type de configuration ne peut se faire que de manière statique :

# zonecfg –z mazone zonecfg:mazone> add dedicated-cpu zonecfg:mazone:dedicated-cpu> set ncpus=1 zonecfg:mazone:dedicated-cpu> end zonecfg:mazone> exit

Là encore, il est évidemment nécessaire de rebooter la zone pour la prise en compte de ces modifications.

Mémoire accessible

Bien que la zone soit limitée en termes de ressources CPU, elle peut néanmoins accéder à l’intégralité de la mémoire vue par la zone globale (en l’absence de capping mémoire, bien sûr) : c’est le kernel, qui tourne dans la zone globale et voit donc tous les processeurs et toute la mémoire, qui va allouer les ressources mémoire au sein de chaque zone.

Cela reste notamment vrai sur un système de type SF20/25K, où la mémoire totale disponible dépend du nombre de processeurs actifs sur la System Board. Attention toutefois, la zone locale ne pourra pas voir plus que la zone globale : sur une SB disposant de 32 Go de RAM, mais où seuls 2 des 4 processeurs sont actifs, la zone globale ne verra que 16 Go de RAM, et notre zone locale ne dépassera donc jamais ce seuil.

Limite CPU absolue

Principe

Cette fonctionnalité permet de limiter de manière absolue la quantité de CPU qu'une zone non-globale peut utiliser. On appelle parfois cette fonctionnalité le hard capping. Cette fonctionnalité est présente à partir de l'update 5.

Configuration

Cette configuration se fait de manière statique avec zonecfg, et le paramètre zone.cpu-cap (également accessible par l'alias capped-cpu), et la propriété ncpus, exprimée en nombre de cpus. Ce nombre n'est pas nécessairement un entier : un ncpus égal à 2 signifie que la zone pourra utiliser 2 CPUs, et une valeur de .75 correspond à 75% d'un processeur.

# zonecfg –z mazone zonecfg:mazone> add capped-cpu zonecfg:mazone:capped-cpu> set ncpus=.75 zonecfg:mazone:capped-cpu> end zonecfg:mazone> exit