6. Accès par noms : adressage associatif#
Les objets JEVEUX, objets simples et objets de collections, sont accessibles par nom. Les noms manipulés par les routines JE…. comportent 24 caractères, les noms utilisés en interne par JEVEUX comportent 32 caractères pour traiter le cas des collections. L’accès par nom, s’il facilite la lisibilité et permet de structurer les données, ne peut être utilisé directement en interne. On a donc recours à un algorithme d’adressage associatif qui, à l’aide d’une fonction de codage, permet d’associer un identificateur entier à un nom. Ce système de codage est utilisé pour gérer les noms des objets JEVEUX pour chaque classe définie (associée à chaque base), mais aussi pour les noms des objets de collection.
On utilise à cette fin soit un couple d’objets formé par un vecteur d’entiers et un vecteur de chaînes de caractères pour la gestion des différents classes, soit un objet de genre répertoire de noms ayant la particularité d’être de contenu hétérogène (stockage des chaînes de caractères et des identificateurs entiers) pour les collections nommées. L’usage de ces répertoires requiert des fonctions d’accès particulières. Le dimensionnement de ces objets est effectué de façon à contenir le nombre d’identificateurs requis en minimisant leur taille et les collisions au niveau de la fonction de codage. Notre choix pour dimensionner le pointeur d’entiers associé au résultat de la fonction d’adressage s’est arrêté sur la condition suivante :
\(\mathit{nrep}=\mathit{nprem}\) où \(\mathit{nprem}>1.3\times \mathit{nmax}\)
\(\mathit{nprem}\) est un nombre premier et \(\mathit{nmax}\) le nombre maximum d’identificateurs à stocker.
Le calcul de la taille des répertoires est réalisé par la fonction JJPREM dans laquelle est stockée sous forme de DATA une liste de 56 nombres premiers jusqu’à la valeur 611957 ce qui limite à cette valeur la capacité des répertoires de noms (et celle du pointeur d’entiers à environ 795 000).
La fonction de codage choisie JXHCOD fait appel à la fonction système STRMOV qui permet de transférer octet par octet une chaîne de caractères dans un tableau d’entiers et à la fonction XOR pour cumuler les résultats dans un entier (INTEGER). L’identificateur est enfin obtenu par une congruence modulo la longueur du répertoire \(\mathit{nrep}\) .
Insertion d’un nom
L’insertion d’un nouveau nom dans les répertoires associés aux différentes bases est réalisée à l’aide de la routine JJCREN. L’ensemble des répertoires des bases ouvertes est examiné de façon à assurer l’unicité du nom d’objet, les routines JEVEUX n’acceptant pas comme argument la classe associée à la base.
Si le répertoire de noms commence à être saturé, la fonction de codage, bien que choisie pour être dispersive, peut donner un identificateur identique pour deux chaînes distinctes, il y a alors collision. Un nouvel identificateur doit être déterminé en tenant compte de la valeur obtenue précédemment.
Recherche de nom dans un répertoire
Cet algorithme nécessite un certain nombre de comparaisons de chaînes de caractères et peut donc devenir coûteux. Un commun, actualisé par la dernière recherche dans les répertoires des différentes bases contient l’identificateur et la chaîne associée afin de diminuer le coût de la recherche (/IATCJE/). C’est la routine JJVERN qui effectue une comparaison avec le contenu du commun avant l’appel à JJCREN. Le code retour de la routine JJCREN dépend du type de recherche dans le répertoire: avec insertion dans le répertoire de noms (ICRE=1) ce code retour est obligatoirement non nul (il y a éventuellement arrêt en erreur), sans insertion il peut valoir 0, sinon 1 correspond à un objet simple et 2 à une collection. C’est la présence d’une chaîne non blanche entre les positions 25 à 32 qui indique que l’on traite un objet de collection.
Les caractères composant les noms des objets sont limités aux caractères alphanumériques complétés par les caractères spéciaux :
“ “ |
le blanc, |
“.” |
le point, |
“_” |
le blanc souligné, |
“$” |
le symbole dollar, |
“&” |
le et commercial. |
La conformité des chaînes de caractères est vérifiée après insertion dans les répertoires (lors de la création du nom uniquement) par comparaison caractère par caractère avec le contenu du commun /JCHAJE/ initialisé dans la routine JEDEBU.
Destruction d’un nom
La destruction d’un nom utilise le même algorithme que l’insertion, la position dans le répertoire ne peut être libérée en raison d’éventuelles collisions, on procède donc en rendant négatif l’identificateur et en affectant à “?” la chaîne de caractères du nom à détruire. Ainsi il sera toujours possible de récupérer cette position ultérieurement.
Redimensionnement des répertoires
Le redimensionnement des répertoires est assuré de façon automatique à l’aide de la routine JJAREP. La taille des répertoires des bases est doublée lors de l’opération. Cette opération reconstruit entièrement le nouveau répertoire par insertion des noms existant. L’ordre d’insertion étant conservé, les objets système ne nécessitent pas de traitement particulier, autre qu’une recopie dans un réceptacle plus grand (il s’en suit un déplacement en mémoire de ces derniers) et leur actualisation sur disque.
Cas des répertoires de collection
Les répertoires de collection sont des objets de contenu non homogène : ils stockent à la fois le résultat (de type entier) de la fonction de codage et les chaînes de caractères composant les noms. Ils sont auto-décrits et les routines les utilisant contiennent les instructions suivantes :
INTEGER ILOREP , IDENO , ILNOM , ILMAX , ILUTI , IDEHC PARAMETER ( ILOREP=1,IDENO=2,ILNOM=3,ILMAX=4,ILUTI=5,IDEHC=6)
La valeur positionnée à l’adresse : |
Représente : |
ILOREP |
la taille nécessaire à l’ensemble des codes entiers, |
IDENO |
l’adresse à partir de laquelle les noms sont stockés, |
ILNOM |
la longueur des chaînes stockées, |
ILMAX |
la dimension maximum du répertoire, |
ILUTI |
le nombre de noms effectivement stockés, |
IDEHC |
l’adresse à partir de laquelle les codes entiers sont stockés. |
L’information stockée à l’adresse ILUTI est actualisée et utilisée dans les fonctions internes d’accès aux répertoires, sa valeur est uniquement accessible de façon externe, à l’aide de l’utilitaire JELIRA avec pour nom d’attribut NOMUTI.
Les objets de collection nommée, lors de leur création par la routine JECROC, sont insérés à l’aide de la fonction JJCODN. La routine intermédiaire JJCROC permet, suivant la valeur de son second paramètre, d’insérer un nouveau nom ou de vérifier son existence et de récupérer son ordre d’insertion.