Les pipelines provoquent de nouveaux problèmes, en particulier d'interdépendance, ils ne sont pas tous listés ci dessous, juste deux cas simples sont abordés.
Interdépendance des données
Une instruction ne peut récupérer le résultat de la précédente car celui-ci n'est pas encore disponible. Ainsi, la séquence :
ADD R1, R2, R3 // R1 = R2 + R3 STORE R1, 1000 // C(1000) = R1
Ne stocke pas à l'emplacement mémoire 1000 la valeur de R1 contenant la somme R2 + R3, mais la valeur de R1 contenue avant l'instruction ADD. Pour résoudre ce problème particulier, il est parfois possible de créer des courts-circuits pour amener le résultat de l'étape précédente vers l'unité qui en a besoin directement, sans passer par les registres de pipeline.
Interdépendance procédurale
Se pose le même problème avec les sauts :
MOV R1, #1000 // R1 = 1000 JUMP R1 // Saut inconditionnel
R1 ne contient pas encore la valeur 1000 au moment où l'instruction de saut va s'exécuter.
Une solution possible à ces deux problèmes est d'insérer une instruction entre les deux qui sont interdépendantes. Prenons par exemple la séquence suivante :
1: A = B + C 2: D = A + C 3: E = F + B
qui comporte une dépendance directe simple, A ne pouvant être disponible pour la partie droite de la seconde instruction.
- la première solution, triviale, est d'insérer des NOP (No Operation), c'est ce que font les compilateurs quand on ne précise pas d'option d'optimisation du code :
1: A = B + C 1b: NOP 2: D = A + C 3: E = F + B
- la seconde solution consiste à réarranger les instructions. Dans cet exemple, l'opération de la ligne 3 n'a aucune interdépendance avec les deux précédentes. Le code modifié sera :
1: A = B + C 2: E = F + B 3: D = A + C