Beaucoup de nouveautés avec la 11GR2 ! L’utilisation de mémoire flash en cache est une des innovations importantes apportée par cette version, mais il reste difficile de faire la synthèse des informations qui circulent sur l’utilisation de la technologie mémoire flash.
Jetons un oeil avisé et détaillé à tout cela … et je vais vous fournir quelques pointeurs très intéressant sur le sujet
EXADATA V2 et FLASH CARD
La première fois que l’on a entendu parler de l’utilisation de flash cache en liaison avec la base de données c’était lors de la présentation de l’Exadata V2 au grand show de San Fransisco en octobre dernier. Oracle à intégré dans le module Exadata Sorage Server, qui sert de contrôleur intelligent aux unités de stockage, quatre cartes flash PCI de 96Go chacune. Ces cartes, de référence « Sun Flash Accelerator F20« , ont des performances impressionnantes et sont de type SSD à mémoire SLC.
Deux utilisations sont possibles pour ces ‘400Go’ :
- Soit ils sont utilisés par le contrôleur comme un cache intelligent et c’est le logiciel intégré qui décide quels sont les blocs qui seront cachés ou non, tout en évitant de conserver des informations inutiles, comme les blocs manipulés pendant les sauvegardes ou ceux des opérations de ré-équilibrage, et en laissant à l’utilisateur l’option de forcer la mise en cache de tables particulières.
- Soit ils peuvent être configurés comme des disques classiques et intégrés via ASM dans des groupes de disques, il n’y alors plus de notion de cache mais on profite pleinement des performances de ce type de mémoire.
Dans les deux cas et pour l’usage de ces cartes flash du module Exadata Storage Server, comme le précise Kevin Closson dans son premier article le sujet, il n’y a aucun lien avec la SGA et le cache des données des instances. Cet article est d’ailleurs une mine d’informations, je vous en recommande la lecture ainsi que celle de ses références et de la seconde partie.
D’autres informations à suivre dès que j’aurais eut le loisir de manipuler ce type de matériel (ce qui ne vas pas tarder).
DATABASE FLASH CACHE
L’autre possibilité d’utilisation d’une mémoire flash avec la base de données est apparue elle aussi avec la version 11GR2 sous la forme de la fonctionnalité Database Smart Flash Cache et des deux paramètres associés db_flash_cache_file et db_flash_cache_size.
Elle permet de disposer d’un cache de niveau 2 pour le cache des données, donc d’une extension de la SGA sur une nouvelle zone d’accès, normalement beaucoup plus rapide que les disques classiques.
Prérequis
Pour disposer de cette fonctionnalité, il faut utiliser un système d’exploitation Linux certifié, la version 11.2.0.1 du logiciel de base de données et surtout le patch 8974084 (disponible uniquement ce jour pour x86 et x86-64, il faudra patienter encore un peu pour les autres distributions).
Sans ce correctif, il est impossible de définir correctement le paramètre db_flash_cache_file, bien que celui ci soit présent.
Une commande de type
alter system set db_flash_cache_file = '/media/disk/flash.dat' scope =spfile ;
nous retourne une erreur « ORA-32005 error while parsing size specification … »
Testons un peu …
Comme Guy Harrison sur son blog, je me suis livré à quelques tests simples sur mon laptop avec une petite clé USB de 64MO sur un environnement OEL5 sous VMware, il n’est donc pas question de parler de performances mais seulement de fonctionnalités.
La mise en œuvre est directe:
Création d’un fichier de 64Mo sous l’arborescence de la clé USB qui est visible sous /media/disk et le faire appartenir à l’ utilisateur oracle.
#dd if=/dev/zero of=/media/disk/flash.dat bs=1M count=64 #chown oracle:dba /media/disk/flash.dat
Positionnement des deux variables:
$sqlplus / as sysdba SQL> alter system set db_flash_cache_file='/media/disk/flash.dat' scope=spfile; SQL> alter system set db_flash_cache_size=64M scope=spfile ;
On peut constater avant de stopper puis de relancer la base que les statistiques associées à l’utilisation du flash cache sont présentes mais toutes à 0 :
SQL> select name,value from v$sysstat where name like '%flash cache%' ; physical read flash cache hits 0 flash cache inserts 0 flash cache eviction: invalidated 0 flash cache eviction: buffer pinned 0 flash cache eviction: aged out 0 flash cache insert skip: not current 0 flash cache insert skip: DBWR overloaded 0 flash cache insert skip: exists 0 flash cache insert skip: not useful 0 flash cache insert skip: modification 0 flash cache insert skip: corrupt 0
Les paramètres ne sont pas dynamiques, il est donc nécessaire de bouncer l’instance de la base de données pour qu’ils soient pris en compte.
Après le redémarrage, on constate tout de suite (certainement à cause de certaines options de sécurité en place dans ma base) la valorisation de certaines des statistiques :
SQL> select name,value from v$sysstat where name like '%flash cache%' ; physical read flash cache hits 24 flash cache inserts 1987 flash cache eviction: invalidated 2 flash cache eviction: buffer pinned 0 flash cache eviction: aged out 0 flash cache insert skip: not current 0 flash cache insert skip: DBWR overladed 965 flash cache insert skip: exists 0 flash cache insert skip: not useful 2 flash cache insert skip: modification 1 flash cache insert skip: corrupt 0
Quelques ordres SELECT simple sur le dictionnaire augmentent encore le nombre de ‘physical read flash cache hits’ ainsi que les insertions de blocs dans le flash cache (flash cache insert) :
SQL> select count(*) from dba_objects ; 73271 SQL> select count(*) from dba_tables ; 2842 SQL> select name,value from v$sysstat where name like '%flash cache%' ; physical read flash cache hits 540 flash cache inserts 2637 flash cache eviction: invalidated 2 flash cache eviction: buffer pinned 0 flash cache eviction: aged out 0 flash cache insert skip: not current 0 flash cache insert skip: DBWR overl 965 flash cache insert skip: exists 364 flash cache insert skip: not useful 57 flash cache insert skip: modification 1 flash cache insert skip: corrupt 0
Il existe un nouveau statut nommé ‘flashcur‘ pour les blocs présents dans le cache et visibles au travers de la vue v$bh,
on peut donc retrouver les objets les plus concernés et leur répartition par la requête suivante :
select owner ||'.'|| object_name object, sum (case when b.status like 'flash%' then 1 end) flash_blocks, sum (case when b.status like 'flash%' then 0 else 1 end) cache_blocks, count(*) total_cached_blocks from v$bh b join dba_objects o on (objd = object_id) group by owner,object_name order by 4 asc /
Ce qui a donné dans mon cas le résultat suivant (affichage des premières lignes):
OBJECT FLASH_BLOCKS CACHE_BLOCKS TOTAL_CACHED_BLOCKS ------------------------------------------------------------------------------------- SYS.C_FILE#_BLOCK# 17 304 321 SYS.C_OBJ#_INTCOL# 203 306 509 XDB.XDB$RESOURCE 510 181 691 SYS.I_OBJ2 750 750 SYS.OBJ$ 911 911 SYS.IDL_UB1$ 479 491 970 SYS.C_OBJ# 546 1380 1926 SYS.C_TOID_VERSION# 2860 2860
Comme le remarque et l’explique Guy Harrison dans son billet suivant « More on the Database Cache‘, la responsabilité de mettre les blocs dans le flash cache est laissé au processus DBWR .
On peut le vérifier en réalisant une insertion d’1 Million de lignes par une boucle dans une table T_EMP (clone de la table HR.EMPLOYEES) , boucle simple de la forme :
CONNECT HR/HR BEGIN FOR I IN 1 .. 100000 INSERT INTO T_EMP SELECT * FROM EMPLOYES; COMMIT; END LOOP; END; /
La table est constituée au finale de 11120 blocs (pour 1071712 lignes) , OBJECT_ID récupéré depuis USER_OBJECTS, la requête suivante à permis de voir la répartition entre le cache des données et le flash cache :
select b.status, count(b.status) from v$bh b join dba_objects o on (objd=object_id) where o.owner='HR' and o.object_id=75599 group by b.status / STATUS COUNT(B.STATUS) ---------- --------------- xcur 4298 flashcur 7700
Donc 7700 blocs dans le flash cache mise à la disposition potentielle des autres utilisateurs par DBWR (seul process impliqué) , évitant de futures lectures disques.
Guy Harrison fait dans son article un certains nombre d’assertions qui paraissent fondées, il nous fournit aussi deux requêtes pertinentes que je n’hésiterai pas à tester lorsque j’aurai l’architecture adéquate à disposition. Sa conclusion sur l’efficacité de la solution est intéressante et il est évident que la qualité et le type d’architecture des cartes flash utilisées sera primordiale (retour au choix de la carte SUN précédemment citée). Quant à la saturation du processus DBWR, j’ai confiance en l’investissement d’Oracle pour que l’algorithme s’améliore rapidement et que ce point de contention disparaisse.
Compléments
Avant de terminer , quelques points de détails que j’ai constaté dans l’utilisation de la fonctionnalité:
- Une fois le flash cache défini , il n’est pas possible de modifier dynamiquement sa taille, cela déclenche des erreurs :
SQL> show parameter flash NAME TYPE VALUE ------------------------------------ ----------- ------------------------------ db_flash_cache_file string /tmp/flashtmp.dat db_flash_cache_size big integer 64M db_flashback_retention_target integer 1440 SQL> alter system set db_flash_cache_size=50M scope=memory ; alter system set db_flash_cache_size=50M scope=memory * ERROR at line 1: ORA-02097: parameter cannot be modified because specified value is invalid ORA-12427: invalid input value for db_flash_cache_size parameter
Et le message suivant dans le fichier journal de la base :
Dynamic resize for flash cache is not supported now (ori 67108864, new 52428800)
- la mise à zéro de la valeur invalide l’utilisation du flash cache avec la trace suivante dans le fichier journal :
Disabling flash cache db_flash_cache_file (/tmp/flashtmp.dat).. 2009-12-21 15:14:22.161000 +01:00 L2 cache file closed by dbwr 0 L2 cache disabled for dbwr 0 ALTER SYSTEM SET db_flash_cache_size='0' SCOPE=MEMORY;
- Il est impossible de refaire une validation dynamique avec une valeur de taille différente de la valeur initiale :
SQL> alter system set db_flash_cache_size=50M scope=memory ; alter system set db_flash_cache_size=50M scope=memory * ERROR at line 1: ORA-02097: parameter cannot be modified because specified value is invalid ORA-12427: invalid input value for db_flash_cache_size parameter
Trace dans le fichier journal :
Dynamically re-enabling flash to a different size is not supported now (ori 67108864, new 52428800)
- Par contre, la remise en place de la valeur initiale valide de nouveau l’utilisation du flash cache :
Dynamically re-enabling flash cache db_flash_cache_file (/tmp/flashtmp.dat) to size 67108864 ALTER SYSTEM SET db_flash_cache_size='64M' SCOPE=MEMORY;
Enfin, pour tester la fonctionnalité, la création d’un fichier dédié au flash cache sur n’importe quel unité de disque suffit, il n’est pas nécessaire de posséder une carte flash (cela reste cependant d’un intérêt très limité et sera réservé uniquement à des tests).
J’espère que ces quelques lignes et les articles qui s’y rattachent vous ont intéressé, n’hésiter pas à réagir et/ou préciser d’autres liens intéressant sur le sujet.
En attendant, meilleurs vœux pour cette année 2010.