FR 3090932 A1 20200626 FR 1873594 A 20181220 Description Titre de l'invention : Système de multiplication de matrices par blocs Domaine [0001] L'invention est relative à la multiplication de matrices de nombres représentés numé- riquement, notamment à des processeurs assistés d'accélérateurs matériels spécialisés pour les opérations de matrices. Arrière-plan [0002] Les technologies d'intelligence artificielle, notamment l'apprentissage profond, sont particulièrement consommatrices de multiplications de grandes matrices, pouvant avoir plusieurs centaines de rangées et de colonnes. On assiste ainsi à l'émergence d'accélérateurs matériels spécialisés dans les multiplications de matrices en précision mixte. [0003] La multiplication de grandes matrices est généralement effectuée par blocs, c'est-à-dire en passant par une décomposition des matrices en sous-matrices de taille adaptée aux ressources de calcul. Les accélérateurs sont ainsi conçus pour calculer efficacement les produits de ces sous-matrices. [0004] Par exemple, NVidia propose dans son processeur graphique Volta des opérateurs matériels appelés coeurs de tenseurs, qui monopolisent chacun les ressources de plusieurs coeurs graphiques du processeur pour effectuer en parallèle de nombreux calculs intervenant dans la multiplication de sous-matrices. NVidia propose également dans son processeur intégré Xavier une unité NVDLA (« NVidia Deep Leaming Accelerator »), indépendante des coeurs graphiques avec des coeurs de tenseurs, et spécialisée dans l'accélération de l'inférence neuronale 100051 Un tel accélérateur est dit « faiblement couplé » en ce qu'il reçoit des tâches à effectuer par lots préparés par un processeur hôte, et gère ensuite les tâches de manière indépendante du processeur hôte, notamment les accès à une mémoire partagée pour lire les données des matrices. L'accélérateur et le processeur hôte fonctionnent ainsi de façon asynchrone, de sorte que le processeur hôte et l'accélérateur sont en concurrence pour les accès mémoire et doivent se synchroniser régulièrement pour que le processeur hôte récupère les résultats des tâches et communique de nouvelles tâches. Résumé 100061 On prévoit de façon eénérale un procédé de multiplication de matrices, comprenant les étapes suivantes : 100071 a) stocker une première matrice source par rangées dans une mémoire partagée, d'où il résulte que des éléments consécutifs d'une rangée de la matrice sont stockés à des 2 adresses mémoire consécutives ; [0008] h) stocker une deuxième matrice source par colonnes dans la mémoire partagée, d'où il résulte que des éléments consécutifs d'une colonne de la matrice sont stockés à des adresses mémoire consécutives ; [0009] c) en un seul cycle de transfert de la mémoire partagée vers des registres de processeur par un bus mémoire de N bits : [0010] - lire un mot de N bits dans une matrice source ; [0011] - écrire K segments consécutifs du mot à une position désignée dans K registres respectifs de N bits, K étant tel que N soit divisible par K ; [0012] c) effectuer l'étape c) pour K = R rangées différentes de la première matrice source de manière à remplir R premiers registres, d'où il résulte que chacun des R premiers registres contient une sous-matrice différente de R rangées de N/R bits organisées dans R segments consécutifs du registre ; [0013] f) effectuer l'étape c) pour K = Q colonnes différentes de la deuxième matrice source de manière à remplir Q deuxièmes registres, d'où il résulte que chacun des Q deuxièmes registres contient une sous-matrice différente de Q colonnes de N/Q bits organisées dans Q segments consécutifs du registre ; et [0014] g) en réponse à l'exécution d'une instruction machine de multiplication de sous- matrices désignant comme premier opérande l'un des R premiers registres et comme deuxième opérande l'un des Q deuxièmes registres, effectuer en parallèle, à l'aide d'un opérateur matériel dédié, un produit scalaire de chaque segment du registre premier opérande par chaque segment du registre deuxième opérande, les segments des registres opérandes étant considérés comme des vecteurs. [0015] Le procédé peut en outre comprendre les étapes consistant à recevoir dans une unité centrale de traitement d'un processeur une instruction machine de lecture-dispersion ; en réponse à l'instruction de lecture-dispersion, déléguer l'étape c) à un coprocesseur couplé à l'unité centrale, la position des segments et les registres étant désignés par l'instruction de lecture-dispersion ; recevoir dans l'unité centrale une instruction machine de multiplication de sous-matrices ; et en réponse à l'instruction de multiplication de sous-matrices, déléguer au coprocesseur l'étape g). [0016] L'unité de traitement et le coprocesseur peuvent être couplés selon une architecture VLIVV, le procédé comprenant une étape d'exécution simultanée d'une instruction de lecture-dispersion et d'une instruction de multiplication de sous-matrices, contenues dans un même paquet d'instructions reçu par l'unité centrale, d'où il résulte que l'instruction de lecture-dispersion prépare une prochaine sous-matrice opérande tandis que l'instruction de multiplication de sous-matrices opère sur des sous-matrices opérandes courantes. [0017] L'opérateur matériel peut être configuré pour accumuler chaque produit scalaire dans 3 un segment respectif d'un registre destination désigné par l'instruction, avec le contenu précédent du segment respectif, le procédé comprenant les étapes consistant à exécuter l'instruction de multiplication de sous-matrices R fois en désignant à chaque fois une paire différente de registres opérandes de même rang parmi les R premiers registres et les Q deuxièmes registres, et un même jeu de registres destination. [0018] Les éléments de chaque matrice source peuvent avoir une précision configurable parmi 8, 16 et 32 bits. [0019] On prévoit également un processeur comprenant un bus de données de N bits configuré pour accéder à une mémoire ; une unité centrale de traitement connectée au bus de données ; un coprocesseur couplé à l'unité centrale, comprenant des registres de travail de N bits ; une unité de traitement d'instructions dans l'unité centrale, configure° pour, en réponse à une instruction machine de lecture-dispersion reçue par l'unité centrale, accéder en lecture à une adresse mémoire et déléguer au coprocesseur le traitement du mot correspondant de N bits arrivant sur le bus de données ; une unité de commande de registres dans le coprocesseur, configure° par l'unité centrale en réponse à l'instruction de lecture-dispersion, pour diviser le mot arrivant sur le bus de données en K segments et écrire les K segments à une même position dans K registres respectifs, la position et les registres étant désignés par l'instruction de lecture-dispersion. [0020] Le coprocesseur peut comprendre une matrice d'opérateurs matériels de produit scalaire, chaque opérateur configuré pour effectuer simultanément le produit scalaire de deux vecteurs contenus dans deux segments de deux registres opérandes respectifs, les rangs des deux segments dans les registres opérandes étant fixés par la position de l'opérateur dans la matrice d'opérateurs, et les registres opérandes étant désignés par une instruction machine de multiplication de sous-matrices reçue par l'unité centrale, d'où il résulte que les registres opérandes contiennent des sous-matrices opérandes respectives, et la matrice d'opérateurs produit une sous-matrice résultat. [0021] Les opérateurs peuvent être configurés pour accumuler les produits scalaires dans des segments respectifs de registres destination désignés par l'instruction de multiplication de sous-matrices. [0022] Les éléments de chaque sous-matrice opérande peuvent avoir une précision configurable parmi 8, 16 et 32 bits. Description sommaire des dessins [0023] Des modes de réalisation seront exposés dans la description suivante, faite à titre non limitatif en relation avec les figures jointes parmi lesquelles : [0024] [fig.1] la figure 1 est un schéma-bloc d'un processeur intégrant un coprocesseur fortement couplé à une unité centrale de traitement ; 100251 Ifig.21 les figures 2A à 2D illustrent différentes étapes de remplissage de registres du co- processeur à partir de données d'une matrice stockées en mémoire ; [0026] [fig.3] la figure 3 est un schéma-bloc d'un mode de réalisation d'une unité matérielle de calcul du coprocesseur conçue pour faire unc multiplication de deux sous-matrices en réponse à unc seule instruction machine ; [0027] [fig.4] la figure 4 est un schéma-bloc d'un opérateur de produit scalaire utilisé dans l'unité de calcul de la figure 3 ; [0028] [fig.5] la figure 5 est un schéma-bloc d'un autre mode de réalisation d'une unité matérielle de calcul du coprocesseur conçue pour faire une multiplication de deux sous-matrices en réponse à une seule instruction machine ; [0029] [fig.6] la figure 6 est un schéma-bloc d'un opérateur de produit scalaire utilisé dans l'unité de calcul de la figure 5 ; [0030] [fig.7] la figure 7 est un schéma-bloc d'un mode de réalisation d'opérateur de produit scalaire configurablc ; et [0031] [fig.8] la figure 8 est un schéma-bloc d'un mode de réalisation d'une unité matérielle de calcul du coprocesseur conçue pour faire une multiplication de sous-matrices de tailles différentes en réponse à une seule instruction machine. Description détaillée [0032] Les accélérateurs matériels dédiés à la multiplication de matrices sont confrontés à des difficultés liées à l'alimentation des unités dc calcul dc l'accélérateur avec des données de matrices stockées dans une mémoire partagée, sans provoquer une famine des unités de calcul ou une sous-exploitation de ces unités. Par exemple, le format de stockage des données en mémoire peut être inadapté au format requis par les unités de calcul, de sorte qu'une latence et des tampons de données peuvent être introduits pour réorganiser les données. [0033] Ces difficultés sont exacerbées lorsque l'accélérateur est faiblement couplé et fonctionne de façon asynchrone avec un processeur hôte qui orchestre les tâches de l'accélérateur. En effet, le processeur hôte et l'accélérateur, fonctionnant chacun de façon autonome, peuvent entrer en conflit d'accès à la mémoire partagée. De plus, un mécanisme de synchronisation entre le processeur hôte et l'accélérateur peut provoquer l'arrêt de l'un ou l'autre en attendant l'arrivée à un point de synchronisation. [0034] Une difficulté supplémentaire survient lorsque les éléments des matrices ont une précision configurahlc parmi plusieurs valeurs. [0035] Pour soulager ces difficultés, on prévoit une architecture de processeur intégrant un coprocesseur fortement couplé, ayant ses propres registres dc travail, et un mécanisme particulier de transfert de données entre la mémoire et les registres du coprocesseur. [0036] La figure 1 est un schéma-bloc d'une telle architecture de processeur. Elle comprend une unité centrale de traitement (CPU) générique 10 fortement couplée à un coprocesseur 12 intégrant des opérateurs matériels dédiés au calcul de produits de matrices. Par « couplage fort » on entend que le coprocesseur obéit cycle par cycle à des instructions machine qui sont exécutées dans l'unité centrale et qui sont mises en oeuvre par des unités d'exécution matérielles 14. [0037] Plus spécifiquement, certaines instructions machine du jeu d' instructions du processeur incorporent des commandes dédiées au coprocesseur. Lorsque ces instructions parviennent à une unité d'exécution correspondante 14 de l'unité centrale, l'unité d'exécution configure le fonctionnement du coprocesseur par des lignes dc commande CTRL. Le coprocesseur est câblé pour obéir immédiatement aux signaux présentés sur ces lignes de commande. En fait, le coprocesseur est une extension des unités d'exécution 14 de l'unité centrale, obéissant à une extension d'un jeu d'instructions génériques du processeur. Ainsi, hormis l'adaptation des unités d'exécution à la commande du coprocesseur, l'unité centrale 10 peut être d'un type générique, permettant notamment d'exécuter un système d'exploitation ou un programme compilé à partir d'un langage de programmation générique. [0038] Le coprocesseur 12 comprend des unités matérielles de calcul algébrique 16, intégrant notamment des opérateurs matériels dédiés au calcul de multiplications de matrices. Le coprocesseur intègre en outre son propre jeu de registres de travail 18, indépendant d'un jeu de registres 20 classique de l'unité centrale 10. [0039] Les registres 18 et 20 sont reliés à une mémoire partagée 22 par un bus de données D de N bits. Des bus d'adresses et de commande de la mémoire, obéissant à des unités d'exécution classiques de l'unité centrale, ne sont pas représentés. Les registres 18 du coprocesseur ont la même taille N que le bus de données et sont configurés pour obéir à des commandes d'une unité d'exécution 14 de l'unité centrale. [0040] Deux matrices à multiplier [21] et [b] sont initialement stockées dans la mémoire partagée 22. Selon le langage de programmation utilisé, une matrice est stockée par défaut pal- rangées (format dit « row-major »), à savoir que les éléments d'une même rangée se trouvent à des adresses consécutives, ou par colonnes (format dit « column-major »), à savoir que les éléments d'une même colonne se trouvent à des adresses consécutives. Le langage de programmation C utilise le premier format, tandis 6 que le Fortran utilise le deuxième format. Quoiqu'il en soit, des bibliothèques standard d'algèbre linéaire (BLAS) exploitées depuis ces langages de programmation prévoient des paramètres de transposition pour passer une matrice d'un format à un autre selon les besoins des calculs. [0041] Pour les besoins de la présente architecture, les deux matrices à multiplier sont stockées selon des formats complémentaires, par exemple la première matrice [a] est stockée par rangées, tandis que la deuxième matrice [h] est stockée par colonnes. La matrice [h] est ainsi stockée sous forme transposée. La figure 1 illustre le contenu de la mémoire pour une matrice [a] de x+1 rangées et y-F1 colonnes et une matrice [h] de y-F1 rangées et z+1 colonnes. La matrice [h], ayant un nombre de rangées égal au nombre de colonnes de la matrice [a], est multipliable par la matrice [a]. [0042] Le coprocesseur 12 est conçu pour multiplier, de manière entièrement câblée, deux sous-matrices des matrices source, la première sous-matrice [A] ayant un nombre fixe Q de rangées, et la deuxième sous-matrice [B] ayant un nombre fixe de colonnes que l'on supposera pour l'instant égal à Q. La dimension restante des sous-matrices, que l'on appellera ci-après profondeur, est configurahle en fonction de la précision souhaitée pour les éléments des matrices. La multiplication de ces sous-matrices produit donc une sous-matrice résultat [C] de QxQ éléments. [0043] Le nombre Q détermine les ressources matérielles nécessaires à effectuer la multi- plication. Pour les applications d'intelligence artificielle, la valeur Q = 4 offre un compromis raisonnable et sera utilisée à titre d'exemple dans la suite. En effet, dans les calculs d'intelligence artificielle on utilise plutôt des nombres de 8 ou 16 bits, rarement de 32 bits, en représentation flottante, fractionnaire ou entière, résultant en des opérateurs moins complexes que ceux requis pour traiter les nombres à virgule flottante « simple précision » et « double précision » classiquement utilisés dans des unités centrales génériques, et respectivement codés sur 32 et 64 bits. [0044] Par ailleurs, chaque sous-matrice à multiplier est considérée comme ayant une taille globale de N bits, à savoir la taille du bus de données D, que l'on supposera égale à 256 bits à titre d'exemple dans la suite. Ainsi, dans les exemples considérés ci-après, les sous-matrices ont 4 rangées ou colonnes de profondeur 64 bits. Cette profondeur est occupée, selon les applications, par huit octets, quatre mots de 16 bits, deux mots de 32 bits, ou un mot de 64 bits. Il peut s'agir d'entiers ou de nombres en virgule fixe ou flottante. [0045] Compte tenu de cette structure, un objectif est d'alimenter le coprocesseur avec des séries de sous-matrices à multiplier en exploitant pleinement le bus mémoire D. En théorie, il suffirait de deux lectures pour lire une quantité de données con-espondant à deux sous-matrices. Mais l'organisation des matrices source en mémoire ne permet pas cela directement dans un cas général. En effet, 256 bits consécutifs en mémoire 7 couvrent des données de rangées (ou colonnes) consécutives de profondeur quelconque, et ne contiennent pas 4 sous-rangées (ou sous-colonnes) alignées pouvant former une sous-matrice. [0046] Pour contourner cette complication, on étend le jeu d'instructions du processeur par une instruction machine de lecture mémoire spéciale, que l'on désignera par instruction de lecture-dispersion ou « load-scatter » et qui a K variantes notées load.0 à load.3 pour K = 4. Une instruction de lecture-dispersion désigne K registres 18 du coprocesseur, notés VO à V3 pour K = 4, et l'adresse mémoire où lire un mot W de 256 bits. A l'exécution de l'instruction dans l'unité centrale 10, alors que la mémoire présente le mot W sur le bus, une unité de commande de registres du coprocesseur 12 est configurée pour diviser le mot W en K segments de N/K bits et écrire ces segments respectivement dans les K registres désignés. En d'autres termes, le mot W est « dispersé » dans les registres. La position à laquelle les segments sont écrits dans les registres désignés est déterminée par la variante de l'instruction de lecture-dispersion exécutée. [0047] Les figures 2A à 2D illustrent l'exécution des variantes de l'instruction de lecture- dispersion sur des matrices source [a] et [h] de profondeur supérieure à 256 bits. On suppose à titre d'exemple que les éléments des matrices sont des mots de 16 bits. [0048] A la figure 2A, une instruction load 0 est exécutée. L'adresse mémoire véhiculée dans l'instruction désigne, par exemple, le premier élément de la première rangée de la matrice [a], à savoir l'élément a[0][0]. Le mot WO retourné sur le bus contient donc les éléments a[0][0] à a[0][15]. La variante de l'instruction configure les registres VO à V3 pour recevoir les quatre segments respectifs du mot WO dans leur premier quart. [0049] A la figure 2B, une instruction load.1 est exécutée. L'adresse mémoire désigne l'élément a[1][0]. Le mot W1 retourné sur le bus contient donc les éléments a[1][0] a[1][15]. La variante de l'instruction configure les registres VO à V3 pour recevoir les quatre segments respectifs du mot W1 dans leur deuxième quart. [0050] A la figure 2C, une instruction load.2 est exécutée. L'adresse mémoire désigne l'élément a[2][0]. Le mot W2 retourné sur le bus contient donc les éléments a[2][0] a[2][15]. La variante de l'instruction configure les registres VO à V3 pour recevoir les quatre segments respectifs du mot W2 dans leur troisième quart. [0051] A la figure 2D, une instruction load.3 est enfin exécutée. L'adresse mémoire désigne l'élément a[3][0]. Le mot W3 retourné sur le bus contient donc les éléments a[3][0] a[3][15]. La variante de l'instruction configure les registres VO à V3 pour recevoir les quatre segments respectifs du mot W3 dans leur quatrième quart. [0052] Au terme de ces quatre lectures-dispersions, chacun des registres VO à V3 contient une sous-matrice [A] consécutive de 4x4 mots de 16 bits (aussi notée 4x4x16) dans le sens des rangées de la matrice source [a]. Les rangées de chaque sous-matrice sont 8 contenues dans quatre segments respectifs du registre V correspondant. Les registres VO à VI contenant des sous-matrices [A], seront désignés VAO à VA3. [0053] En procédant de manière similaire pour la deuxième matrice [h] et quatre registres VBO à VB3, chacun de ces registres reçoit une sous-matrice [B] consécutive de 4x4x16 dans le sens des colonnes de la matrice source [h]. Les colonnes de chaque sous-matrice sont contenues dans quatre segments respectifs du registre VB correspondant. [0054] Avec cette procédure, on obtient dans les registres du coprocesseur quatre sous- matrices [A] et quatre sous-matrices [B] multipliables en huit cycles d'horloge consécutifs. On atteint ainsi un taux de transfert d'une sous-matrice par cycle, ce qui est optimal, car la largeur complète du bus est utilisée à chaque cycle. [0055] Les segments des registres VA et VB, contenant des rangées ou des colonnes de sous-matrices, peuvent être traités ci-après comme des vecteurs. Ainsi, un registre VAi contient quatre vecteurs A[0] à A[3] et un registre VBj contient quatre vecteurs B[0] à B[3], chaque vecteur ayant quatre composantes de 16 bits. [0056] La figure 3 est un schéma-bloc d'un mode de réalisation d'une unité matérielle de calcul 16 du coprocesseur, destinée à effectuer une multiplication de deux sous-matrices [A] et [B] en réponse à une seule instruction machine dédiée que l'on notera mm4a. Ce mode de réalisation correspond à l'exemple considéré aux figures 2A à 2B, où les éléments de matrice ont une taille de 16 bits. [0057] L'unité de calcul comprend une matrice de 4x4 opérateurs matériels de produit scalaire et accumulation notés DP4A, où le nombre 4 désigne la dimension des vecteurs. Un opérateur DP4A de la rangée i et colonne j est câblé pour effectuer le produit scalaire des vecteurs A[i] et BU] contenus respectivement dans des registres VA et VB, et accumuler le produit scalaire dans une cellule Cij d'une sous-matrice résultat [C]. La cellule Cij peut être tout ou partie d'un segment de taille appropriée d'un registre VC du coprocesseur. Une taille confortable est 64 bits, ce qui implique quatre registres VCa à VCd pour stocker la sous-matrice résultat [C]. Les registres VA, VB et VC sont désignés par une instruction mm4a en cours d'exécution dans l'unité centrale 10, ici les registres VAO, VBO et VCOa-VCOd. [0058] Les registres VC sont configurés pour préserver l'organisation en Q segments des registres VA et VB. Dans le présent exemple, où Q = 4 et chaque élément résultat est codé sur 64 bits, chacun des 4 segments des registres VC contient un seul élément. Comme cela est représenté à titre d'exemple, les registres VC sont organisés pour que les quatre segments d'un même registre stockent des éléments de rangées différentes. [0059] Une fois les calculs terminés sur la sous-matrice résultat, dans ce cas particulier de segments contenant un seul élément, les contenus des quatre registres VC peuvent être transférés en mémoire en quatre cycles à des adresses correspondant aux positions des colonnes de la sous-matrice [C] dans la matrice résultat complète [c], contribuant ainsi 9 à une matrice résultat [c] stockée par colonnes (« column-major »). [0060] Les registres VC pourraient aussi être organisés de façon complémentaire pour que les quatre segments d'un même registre stockent des éléments de colonnes différentes. Dans ce cas, les contenus des quatre registres VC peuvent être transférés en mémoire en quatre cycles correspondant aux positions des rangées de la sous-matrice [C] dans la matrice résultat complète [c], contribuant à une matrice résultat [c] stockée par rangées (« row-major »). [0061] De préférence, on étend le jeu d'instructions du processeur par une instruction machine de transposition d'un tuple contenant Q registres. Dans le cas Q = 4, cette instruction dénotée mt4 prend les contenus de quatre registres désignés VCa, VCb, VCc, VCd et remplit quatre autres registres désignés VDa, VDb, VDc, VDd, tels que : [0062] VDa reçoit respectivement dans ses segments les premiers segments de VCa, de VCb, de VCc et de VCd. [0063] VDh reçoit respectivement dans ses segments les seconds segments de VCa, de VCh, de VCc et de VCd. [0064] VDc reçoit respectivement dans ses segments les troisièmes segments de VCa, de VCb, de VCc et de VCd. [0065] VDd reçoit respectivement dans ses segments les quatrièmes segments de VCa, de VCb, de VCc et de VCd. [0066] Comme suite à l'exécution de cette instruction, chacun des registres VCa, VCh, VCc, VCd peut être stocké en mémoire pour contribuer à une rangée de la matrice résultat [c] stockée par rangées (« row-major »). [0067] La figure 4 est un schéma-bloc d'un opérateur de produit scalaire DP4A de position j) dans la matrice d'opérateurs. L'opérateur traite les vecteurs A[i] et B[j]. Plus spé- cifiquement, l'opérateur comprend quatre multiplieurs MUL de 16 bits recevant chacun une composante respective (Ai0 à Ai3) du vecteur A[i] comme premier multi- plicande, et la composante correspondante (B0j à B3j) du vecteur B[j] comme deuxième multiplicande. Les quatre produits, codés sur 32 bits, sont fournis à un multiadditionneur 40 connecté pour accumuler la somme des produits dans un segment de registre Cij de 64 bits. Par « accumuler » on entend que le segment Cij reçoit la somme des produits et du contenu précédent du segment Cij. Le multi-additionneur 40 est ainsi câblé pour effectuer la somme de quatre nombres de 32 bits et un nombre de 64 bits. [0068] En théorie, l'unité de calcul de la figure 3, câblée en logique combinatoire, produit instantanément la matrice résultat [C] en réaction à une instruction min4a qui désigne les registres VA, VB et VC à utiliser. En pratique, une telle unité de calcul, compte tenu des délais de propagation de la logique combinatoire, mettra plus d'un cycle d'horloge du processeur à établir le résultat. Ainsi l'unité de calcul, notamment chaque opérateur DP4A, est généralement conçue en structure pipeline, signifiant que le calcul est décomposé en plusieurs étapes synchronisées sur des cycles d'horloge successifs, niais qu'on peut initier un nouveau calcul, c'est-à-dire exécuter une nouvelle instruction mm4a, à chaque cycle d'horloge. [0069] Ainsi, une structure pipeline est peu optimale pour faire des calculs isolés. Par contre, en organisant de façon adéquate les calculs successifs, de manière à maintenir le pipeline alimenté en permanence, la structure pipeline peut être efficace à 100 % après une phase initiale d'amorçage du pipeline et avant une phase finale de vidage du pipeline. [0070] Le fait qu'on précharge dans les registres du coprocesseur huit sous-matrices à l'aide des instructions de lecture-dispersion (figures 2A-2D), et que les sous-matrices à multiplier se trouvent ainsi dans les registres selon une organisation immédiatement exploitable par l'unité de calcul, permet de maintenir le pipeline alimenté au moins pour le calcul de quatre produits de sous-matrices. Ces quatre produits de sous-matrices, effectuahles en exécutant quatre instructions mm4a consécutives désignant les mêmes registres destination VC, fournissent une matrice résultat [C] de 4x4 qui est le produit d'une sous-matrice source 4x16 par une sous-matrice source 16x4. [0071] En outre, la configuration à fort couplage entre le coprocesseur et l'unité centrale permet d'organiser le processeur en architecture VLIW (« Very Large Instruction Word »). Alors, on peut exécuter une instruction de lecture-dispersion et une instruction mm4a dans un même paquet VLIW, c'est-à-dire exécuter ces deux instructions en parallèle, ce qui occupe le bus mémoire pour chercher les prochaines sous-matrices pendant qu'on effectue les calculs sur les sous-matrices courantes. [0072] Le tableau 1 ci-dessous présente une séquence d'instructions qui permet de multiplier une matrice [a] (le 8x32 par une matrice [b] de 32x8 pour fournir une matrice [c] de 8x8 sans temps mort et en exploitant toute la bande passante du bus mémoire et de l'unité de calcul en parallèle. Des instructions placées sur une même ligne correspondent à des instructions exécutées dans un même paquet VLIW. Pour des raisons de compacité de notation et de clarté, les registres du coprocesseur sont désignés par Ax et By pour les sous-matrices multiplicandes et Cz pour la sous-matrice résultat, en sachant que tous ces registres, choisis dans le jeu de registres 18, sont de même nature. [0073] Le premier paramètre des instructions identifie les registres destination. Les pa- ramètres subséquents des instructions identifient normalement une adresse mémoire ou des registres opérandes - on a utilisé ici une notation explicative qui détaille ce que reçoivent les registres destination. On suppose que les registres C sont tous à 0 avant les opérations, ou bien que les opérateurs sont configurés par un chapeau des instructions mm4a pour désactiver l'accumulation lors de la première écriture dans un registre C, ce qui est illustré par le signe « = » (écriture directe) à la place du signe += » (accumulation). 11 [0074] Les phases 0 et 1 correspondent à ce que l'on a décrit en relation avec les figures 2A-2D. 12 [Tahleauxl] Phase 0: charger les sous-matrices a[0..3][0..3] à a[0..3][12..15] load.0 AOA1A2A3 Q. Dans ce cas, on configure les instructions de lecture-dispersion pour, dans une première série de R cycles, remplir R registres A différents, et, dans une deuxième série de Q cycles, remplir Q registres B différents. Chaque registre A contient alors une sous-matrice de Q rangées avec des éléments de taille N/Q bits, et chaque registre B contient R/Q sous-matrices de Q colonnes avec des éléments de taille N/R bits, où N est la largeur du bus mémoire et la taille des registres, et est divisible par Q et par R. Chaque instruction de multiplication lit le contenu de R/Q registres A et d'un registre B, pour produire une 19 sous-matrice de dimensions RxQ. [0110] Pour que les sous-matrices d'un registre A et d'un registre B soient multipliables, il faut que leurs vecteurs aient la même dimension. La valeur N étant de préférence une constante égale à la taille du bus mémoire, cela implique que les deux sous-matrices ont des précisons différentes si Q *R. En pratique Q et R varient selon un rapport 1, 2 ou 4 selon les combinaisons de précisions choisies pour les matrices parmi 8, 16 et 32 bits. [Revendication I] [Revendication 2]