これはおそらく議論の質問ですが、stackoverflowがそれを尋ねるのに適切な場所である可能性があると思いました。私は命令パイプラインの概念を研究しています。パイプラインのステージ数を増やすと、パイプラインの命令スループットが上がると教えられてきましたが、スループットが変わらない場合もあります。どのような条件下で、これは起こりますか?ストールと分岐が質問の答えになると思いますが、重要な何かが欠けているのではないかと思います。
5 に答える
スループットは、結果を待っているとき、またはキャッシュ ミス時に、他の命令によって停止する可能性があります。パイプライン処理自体は、操作が完全に独立していることを保証するものではありません。これは、x86 Intel/AMD アーキテクチャの複雑さに関する素晴らしいプレゼンテーションです: http://www.infoq.com/presentations/click-crash-course-modern-hardware
このようなことを非常に詳細に説明し、スループットをさらに向上させ、レイテンシーを隠す方法に関するいくつかのソリューションをカバーしています。JustJeff は 1 つのアウトオブオーダー実行について言及し、プログラマー モデルによって公開されていないシャドウ レジスタ (x86 では 8 つを超えるレジスタ) があり、分岐予測もあります。
同意した。最大の問題は、ストール (前の命令の結果を待つこと) と、誤った分岐予測です。パイプラインが 20 ステージの深さであり、条件または操作の結果を待機してストールした場合、パイプラインが 5 ステージのみの場合よりも長く待機することになります。間違った分岐を予測した場合、パイプラインから 5 ではなく 20 の命令をフラッシュする必要があります。
おそらく、複数のステージが同じハードウェア (ALU など) にアクセスしようとする深いパイプラインを持つことができると思いますが、これはパフォーマンス ヒットの原因となりますが、各ステージをサポートするのに十分な追加ユニットを投入することをお勧めします。
命令レベルの並列処理では、利益が減少します。特に、命令間のデータの依存関係によって、可能な並列処理が決まります。
Read after Write (教科書では RAW として知られています) の場合を考えてみましょう。
最初のオペランドが結果を取得する構文で、次の例を検討してください。
10: add r1, r2, r3
20: add r1, r1, r1
10 行目の結果は、10 行目の計算が始まるまでにわかっている必要があります。データ転送によりこの問題は軽減されますが、データが認識される程度までしかありません。
また、一連の中で最も長い命令の実行にかかる時間を超えてパイプライン化を増やしても、パフォーマンスは向上しないと思います。ただし、ストールとブランチは基本的な問題だと思います。
長いパイプラインでのストール/バブルは、スループットに大きな損失をもたらします。もちろん、パイプラインが長くなればなるほど、より多くのクロック サイクルが浪費されます。
パイプラインが長くなるとパフォーマンスが低下する可能性がある他のシナリオを長い間考えてみましたが、すべてストールに戻ります。(そして、実行ユニットと発行スキームの数ですが、それらはパイプラインの長さとはあまり関係がありません。)