!
!
!
!
!
!
!
!

Les Rollback Segments

Ceci est un extrait du livre. Ne cherchez pas les liens ;-)

Comme nous avons vu dans les paragraphes précédents, les rollback segments sont essentiels pour le maintien de la consistance de la base de données. Appelés aussi segments d’annulation, ils enregistrent l'image des données avant qu'elles ne soient modifiées. Les rollback segments assurent trois principales fonctions :

  • Lecture consistante/cohérente (read consistency):

Une transaction qui lit les données modifiées par une transaction ultérieure récupère les données avant la modification dans le rollback segment. ORACLE utilise ces images avant pour assurer une lecture consistante au niveau de la transaction. Le SCN courant du système est affecté à chaque transaction a son début. Lors de la lecture d'un bloc de données, ORACLE compare le SCN du bloc avec celui de la transaction. Si le SCN de la transaction est supérieur ou égal avec celui du bloc, ORACLE lira la donnée depuis ce bloc. Si le SCN de la transaction est inférieur au SCN du bloc, ORACLE lira la donnée dans le rollback segment. Cette dernière situation implique qu’une transaction ultérieure à la notre a modifié les données demandées.

  • Annulation de transactions

L’annulation de la transaction exige la remise des données modifiées pendant le déroulement de celle-ci dans l’état avant son début.. Toute transaction validée (COMMIT) ne peut plus être annulée. L'annulation peut être automatique (erreur dans la transaction, etc.) ou manuelle, déterminée avec la commande ROLLBACK.

  • Réstauration

Lors de la réhabilitation d’une base après son crash, les données modifiées (validées ou non) présentes dans les redo logs sont appliquées. Pour toutes les transactions actives lors du crash, l’image avant des données est reconstituée à partir des rollback segments.

Fonctionnement des rollback segments

Oracle alloue à une transaction dès son début un rollback segment  choisi d’une manière circulaire dans un pool de rollback segments disponibles[1]. Le résultat de ce choix est une distribution uniforme des transactions actives parmi les RBS et malheureusement une indépendance de la taille du RBS du type de transaction.

Pour chacun des rollback segments ORACLE maintient une table des transactions associées à celui-ci, visible dans son en-tête (premier bloc du rollback segment).

Les données stockées dans le RBS constituent des entrées de rollback (rollback entries). Une entrée de rollback contient le ROWID de l'information modifiée et les données avant modification. Le bloc initial d’ou provenaient les données modifiées est ainsi identifiable. Les entrées de rollback sont identifiées par transaction afin de pouvoir réaliser un rollback ou une lecture cohérente. Elles appartiennent à SYS.

Un segment rollback est constitué comme tout segment Oracle d’une collection de groupes de blocs contigus  appelés extents. Les rollbacks segments sont constitués d'au moins deux extents[2], utilisées de façon circulaire en utilisant un autre quand le précédent est plein. Une transaction écrit dans le RBS et avance un pointeur de localisation au fur et à mesure. Appelons tête la position courante de la transaction dans le RBS et queue le début du premier enregistrement de la transaction. Voici quelques principes importants, applicables a toutes les versions d’ORACLE :

·         Une transaction utilise au moins une extension de rollback segment. Elle peut utiliser un seul segment rollback pour stocker ses informations.

·         Plusieurs transactions peuvent écrire dans un même extent.

·         Un bloc est utilisé par une seule transaction.

·         La tête d’une transaction n’utilisera jamais un extent occupé par la queue.

·         Les extents sont utilisés en ordre

·         Si le nombre d’extension du RBS n’est pas suffisant pour contenir toutes les images avant de toutes les transactions ayant été aiguillées dessus, ORACLE peut allouer des extensions supplémentaires jusqu’à atteindre la valeur du paramètre MAXEXTENT définie dans la clause STORAGE à sa création. Cette allocation des extents se fait de façon circulaire: si la tête ne peut pas utiliser ni l’extent suivant, ni le premier, elle va allouer un autre et l’insérer dans le cercle.

·         Les extensions supplémentaires du RBS pourront être rendues à la base de données (au tablespace dans lequel il est localisé) par rétrécissement jusqu’à sa taille OPTIMAL définie, à sa création, par le paramètre OPTIMAL de la clause STORAGE.

·         Un Rollback segment DOIT être structuré en plusieurs extensions de taille identique.

Les principes précédents impliquent que les rollback segments augmentent et diminuent de taille durant l'activité normale de la base (si le paramètre OPTIMAL est spécifié). Le paramètre OPTIMAL permet  d'indiquer la taille idéale (supposée) des rollback segments. Lorsque Oracle assigne une transaction à un segment de rollback, il vérifie si sa taille actuelle est supérieure à OPTIMAL. Si tel est le cas et que des extents sont libres de toute transaction active, les extents en excès sont désalloués, les plus anciens en priorité. PCTINCREASE ne doit pas être spécifié dans la clause de stockage, il est implicitement à 0. MINEXTENTS doit avoir 2 pour valeur minimale[3].

La cuisine du rollback

Pendant toute la transaction, pour chaque ligne modifiée, une ligne ITL dans l’en-tête du bloc d’origine pointera vers le bloc du RBS qui contient la donnée avant la modification. Nous avons vu dans les paragraphes précédents comment les informations concernant une transaction qui modifie une ligne dans un bloc sont référencées dans l’en-tête du bloc respectif dans un slot ITL (voir ‘Les ITL (interested transactions list)’, page 137). Reprenons :

1.        Le bloc de données est mis en mémoire s'il n'y est pas déjà présent.

2.        Génération de l’information dite ‘undo’

3.        Mise de l’enregistrement 'undo’ dans un bloc du redo buffer cache

4.        Utilisation d’un bloc disponible dans la SGA (DB BLOCK BUFFERS) pour l’image du bloc initial (avant modification)

5.        Écriture du buffer ainsi constitué dans un block du rollback segment

6.        Modification du SCN dans l’en-tête du buffer modifié, renseignement d’une entrée ITL avec le SCN de la transaction en cours et l’adresse du bloc RBS qui contient l’avatar antérieur du bloc. Rappelons que le nombre de slots ITL est strictement dépendant des paramètres INITRANS / MAXTRANS du segment dont le bloc fait partie et de l’espace réellement disponible dans l’en-tête. Rappelons également que si l’en-tête du bloc est insuffisant, les entrées ITL peuvent déborder dans l’espace PCTFREE du bloc.

7.        Enregistrement de la modification dans une entrée d'undo (rollback)

8.        Écriture de la modification dans un enregistrement du redo buffer cache

9.        Écriture de la modification dans le bloc de données

Les deux entrées dans le redo log buffer concernent le bloc de données lui-même et le bloc du rollback segment. Un bloc du rollback segment peut ainsi être reconstruit. Les informations undo pointeront également sur l’adresse du bloc RBS.

Lors de la validation (COMMIT) :

1.        LGWR écrit les changements dans les fichiers de REDO LOG. Ceci garantit la parfaite réhabilitation de la base en cas de catastrophe.

2.        La table des transactions du RBS est mise à jour, déclarant les blocs disponibles, mais les blocs ne seront pas effacés. Il continueront d’être utilisés a) par toute transaction antérieure à celle qui vient de faire COMMIT qui veut lire d’une manière cohérente les blocs des données et b) par toute transaction dans une autre instance.

En réalité, les modifications apportées à l’en-tête du bloc récemment modifié peuvent ne pas être répercutées  immédiatement. En effet, bien que validée, le slot ITL de la transaction finie continue de pointer vers la table de transactions du RBS en tant que non validée. La première transaction qui aura besoin des données de ce bloc ira jusqu'à cette table des transactions ou elle trouvera que la donnée est validée et c’est elle qui mettra le bloc à jour. Il s’agit du phénomène de nettoyage retardé du bloc (delayed block cleanout). Cette action est parfois nécessaire lors de la validation de la modification d’un grand nombre de lignes (la mise à jour des en-têtes de tous les blocs validés prendrait trop de temps)

Un problème lié au delayed block cleanout est évident lors de l’utilisation de Oracle Parallel Server: dans cet environnement, les fichiers des données sont partagés mais les RBS sont privés.  Ainsi, un bloc non nettoyé après la modification validée provoquera l’accès aux données dans le RBS de l’instance qui a validé les données par des transactions provenant de l’autre instance. Cette option avait été prise dans les versions antérieures à  la version 8.1 pour alléger les pings des données inter instance. Une solution pour nettoyer les blocs est de provoquer un full table scan des données récemment validées. Aujourd’hui le problème est réglé avec l’utilisation de cache fusion.

Le block cleanout consiste en la libération des locks sur les lignes modifiées et validées. Les locks sont répertoriés dans le header du bloc et ils pointent vers l’entrée ITL correspondante.

 



[1] Sauf SET TRANSACTION READ ONLY et transactions discrètes.

[2] Ce qui est largement insuffisant.

[3] Mais nous le mettons d’habitude à 20

 

Copyright © 1998-2002 Radu Caulea, TAFORA MAJ 20/04/2006 !
Commentaires et suggestions radu[CHEZ]tafora.fr