FPGA開発日記

カテゴリ別記事インデックス https://msyksphinz.github.io/github_pages , English Version https://fpgadevdiary.hatenadiary.com/

BOOM (Berkeley Out-of-Order Machine) のマイクロアーキテクチャドキュメントを読む (10)

RISC-VのアウトオブオーダコアであるBOOM (Berkely Out-of-Order Machine) について勉強を進めている。以下のドキュメントを日本語に訳しながら読んでいくことにした。

docs.boom-core.org


実行パイプライン

Dual Issue Pipeline

Fig. 19: 2命令発行のBOOMのパイプライン例。最初の発行ポートは、ALU演算、FPU演算、整数乗算命令を受け付けることができるExecute Unit #0に、UOP<Micro-Op (UOP)をスケジューリングします。 2番目の発行ポートは、ALU演算、整数除算命令(非パイプライン)、ロード/ストア演算をスケジュールします。 ALU演算は、依存する命令にバイパスすることができます。なお、実行ユニット#0のALUには、FPUやiMulユニットとのレイテンシーを合わせるためにパイプラインレジスタが追加されており、 書き込みポートのスケジューリングが容易になっています。 各 :term:`Execution Unit は、それ専用の1つの命令発行ポートを持っていますが、 その中にはいくつかの下位レベルの 機能ユニット が含まれています。

実行パイプライン は、 Micro-Ops (UOPs) の実行とライトバックをカバーしています。 UOPs はパイプラインを次々と通過しますが、 UOPs 自体は実行パイプラインに順番通りではない形で発行されている可能性があります。 Fig. 19 は2命令発行の BOOM の実行パイプラインの例を示しています。

実行ユニット

Example :term:`Execution Unit`

Fig. 20 例 実行ユニット: この例では、整数のALU(依存する命令に結果をバイパスできる)と、 動作中にビジー状態になるパイプライン化されていない分周器を示しています。 両方の 機能ユニット は、1つの書き込みポートを共有しています。 実行ユニットは、kill信号と分岐解決信号の両方を受け取り、必要に応じて内部の機能ユニットに渡します。

実行ユニット とは、1つの命令発行ポートが UOPs<Micro-Op (UOP) をスケジュールするモジュールで、 機能ユニット のいくつかの組み合わせを含みます。 別の言い方をすると、 命令発行キュー からの各命令発行ポートは、1つだけの 実行ユニット と通信します。 1つの実行ユニットは1つの単純な整数ALUだけを含むかもしれませんし、 完全な浮動小数点ユニット、整数ALU、整数乗算ユニットを含むかもしれません。

実行ユニット の目的は、アーキテクトがパイプラインにどのような種類の 実行ユニット を追加できるかについて、 多くのコントロールを与える柔軟な抽象化を提供することです。

スケジューリングの準備

実行ユニット は、利用可能な 機能ユニット のビットベクターを命令発行スケジューラに提供します。 命令発行スケジューラは、その 実行ユニット がサポートする UOPs<Micro-Op (UOP)のみをスケジュールします。 常に準備ができていない可能性のある :term:Functional Unit (例えば、パイプライン化されていない除算器)については、 ビットベクタの適切なビットが無効になります(参照 Fig. 19)。

機能ユニット

Abstract :term:`Functional Unit`

Fig. 21 抽象的なパイプライン化された 機能ユニット クラスです。 専門家によって書かれた低レベルの 機能ユニット の中でインスタンス化されます。 UOPs<Micro-Op (UOP)は、低レベルの機能ユニットを出るときに、 そのレスポンスをゲートオフすることで個別に殺されます。

機能ユニット はCPUの筋肉であり、命令に応じて必要な演算を行います。 機能ユニット を正しく効率的に実装するには、知識豊富なドメインエキスパートが必要です。

このような理由から、BOOMは抽象的な 機能ユニット クラスを使用して、Rocket リポジトリから エキスパートが書いた低レベルの 機能ユニット を「ラップ」しています( Rocket Chip SoC Generator 参照)。 しかし、Rocketのインオーダープロセッサ用に作成されたエキスパートが書いた 機能ユニット は、 インオーダーの発行ポイントとコミットポイントについて仮定しています(つまり、一旦命令がそれらにディスパッチされたら、決してキルする必要はないということです)。 この仮定はBOOMでは崩れます。

しかし、BOOM は 機能ユニット を書き直したりフォークしたりするのではなく、抽象的な 機能ユニット クラス( Fig. 21 参照)を提供しています。 このクラスは、低レベルの機能ユニットを BOOM 内で動作させるために必要なパラメータ化された自動生成サポートコードで「ラップ」します。 リクエストポートとレスポンスポートは抽象化されているので、 機能ユニット クラスは統一された交換可能なインターフェースを提供することができます。

パイプライン化された機能ユニット

パイプライン化された 機能ユニット は、1サイクルごとに新しい UOP<Micro-Op (UOP) を受け入れることができます。 それぞれの UOP<Micro-Op (UOP) は、既知の固定されたレイテンシーをとります。

投機実行のサポートは、専門家によって書かれた 機能ユニット 内の UOP<Micro-Op (UOP) メタデータ分岐マスク を並行して渡すパイプラインを自動的に生成することによって提供されます。 もし UOP<Micro-Op (UOP) が誤って指定された場合、その応答は機能ユニットを出るときに無効にされます。

パイプライン化された 機能ユニット の例を Fig. 21 に示します。

非パイプラインの機能ユニット

パイプライン化されていない 機能ユニット (例:除算器)は、1つの操作を完了するために可変の(そして未知の)サイクル数を要します。 一旦占有されると、レディ信号のアサートが解除され、追加の UOP<Micro-Op (UOP) がスケジューリングされることはありません。

投機実行のサポートは、 UOP<Micro-Op (UOP) の ブランチマスク を 機能ユニット でトラッキングすることで行われます。

専門家によって書かれたパイプライン化されていない 機能ユニット の唯一の要件は、 誤って仕様化された UOPs<Micro-Op (UOP) を素早く取り除くための kill シグナルを提供することです。1

Functional Unit Hierarchy

Fig. 22 破線の楕円は専門家によって書かれた低レベルの 機能ユニット であり、四角は低レベルの 機能ユニット をインスタンス化する具象クラスであり、 八角は汎用的な投機のサポートと BOOM パイプラインとのインターフェイスを提供する抽象クラスです。 浮動小数点の除算と平方根のユニットは PipelinedUnpipelined のどちらの抽象クラスにも きれいに収まらないので、FunctionalUnitスーパークラスを直接継承しています。