FPGA開発日記

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

「30日でできる!OS自作入門」を読み始めた (20日目. APIの実装)

30日でできる! OS自作入門

30日でできる! OS自作入門

30日でできる!20日目はOSのAPIを実装する。まずはコンソールに文字を表示するAPIを実装している。 最初はレジスタアドレスを決め打ちしてcons_putcharを呼び出していたのだけれども、これは良くないので割り込みを使ってAPIを呼び出すようにしている。

最初のcons_putcharをアドレスを固定して呼び出す方法は、どうも方式が違っていて本書とアドレスが異なっているので最初は苦労した。 以下の記事を参考にしてアドレスを特定するようにした。

OS自作入門20日目 【Linux】 | APIを作る | サラリーマンがハッカーを真剣に目指す

なるほど、バイナリファイルをダンプしてアドレスを見つけるのか。

$(TARGET).bin: $(OBJ_FILES)
    ld -Map bootpack.map -m elf_i386 -e HariMain -n -Thrb.ld -static -o $(TARGET).bin $^
    hexdump -C $(TARGET).bin > $(TARGET).bin.dmp

上記を実行すると、bootpack.mapの中にアドレスが記述されている。

...
 .text          0x0000000000006300     0x2808 console.o
                0x0000000000006590                cons_newline
                0x0000000000006680                cmd_mem
                0x00000000000069a0                cmd_cls
                0x0000000000006a10                cmd_dir
                0x0000000000006e50                cmd_type
                0x00000000000072a0                cmd_hlt
                0x0000000000007500                cons_putchar

そこで、関数の呼び出し位置を決める。

[BITS    32]
    mov     al, 'h'
    call    2*8:0x7500
    mov     al, 'e'
    call    2*8:0x7500
    mov     al, 'l'

次に、この方式はアドレスが変わるたびに場所を書き換えないといけないので、割り込みを使ってAPIを呼び出すように変更している。 さらに、1種類の割り込みを呼び出せば、それからAPIの種類を判断してジャンプできるようにした。

void hrb_api (int edi, int esi, int ebp, int esp, int ebx, int edx, int ecx, int eax)
{
  struct CONSOLE *cons = (struct CONSOLE *) *((int *)0xfec);
  if (edx == 1) {
    cons_putchar (cons, eax & 0xff, 1);
  } else if (edx == 2) {
    cons_putstr0 (cons, (char *) ebx);
  } else if (edx == 3) {
    cons_putstr1 (cons, (char *) ebx, ecx);
  }

  return;
}

これで、アプリケーションを呼び出せるようにした。

f:id:msyksphinz:20180421143543p:plain
図. APIを使って、文字列を出力する。

RISC-VツールセットをインストールしたDockerコンテナ作成(1. 検討)

f:id:msyksphinz:20180418005224p:plain

RISC-V 対応の自作エミュレータを作成している。テストパタンセットであるriscv-toolsがかなりPassできるようになってきた。

満足したところで公開したいので、一応リグレッションテストをいつでも実行できるような状態にしておきたい。

というわけで、RISC-VのツールセットをインストールしたDockerコンテナの作成方法について調査を始めよう。 というか、Dockerコンテナについてあまり詳しくないから、勉強しなければ...

RISC-Vのツール群が入ったDockerコンテナ

手っ取り早くDockerコンテナを用意したければ、以下のコンテナがGitHubに用意されていた。

github.com

以下で起動することができた。

sudo docker pull sbates130272/riscv
sudo docker run -it sbates130272/riscv

これでもいいのだけれど、自分で管理できるRISC-V環境を維持しておきたいし、自作エミュレータをリグレッションする環境を構築したいので、自分でDockerコンテナを管理しておきたい。

というわけで自分でDockerfileを書き始めた。

  • Dockerfile
# Pull base image (use Wily for now).
FROM ubuntu:17.10

# Set the maintainer
MAINTAINER msyksphinz

# Install some base tools that we will need to get the risc-v
# toolchain working.
RUN apt update && apt install -y \
  autoconf \
  automake \
...
  libtool \
  ncurses-dev \
  patchutils \
  squashfs-tools \
  texinfo

さらにビルドを行うために、riscv-tools をcloneしてビルドする環境を作っておく。

# Make a working folder and set the necessary environment variables.
ENV RISCV /opt/riscv
ENV NUMJOBS 1
RUN mkdir -p $RISCV

# Add the GNU utils bin folder to the path.
ENV PATH $RISCV/bin:$PATH

# Obtain the RISCV-tools repo which consists of a number of submodules
# so make sure we get those too.
WORKDIR $RISCV
RUN git clone https://github.com/riscv/riscv-tools.git && \
  cd riscv-tools && git submodule update --init --recursive

ここまでで、RISC-Vのツールチェインが動作するDockerコンテナを作ることができた。

docker build -t msyksphinz/riscv-docker
sudo docker run -it msyksphinz/riscv-docker   # Login

2018/04/20追記。自作RISC-Vエミュレータのビルドも行ってみた。以下でDocker上でエミュレータをclone, コンパイルすることができる。 あとはリグレッションだな。

RUN git clone https://msyksphinz:PASSWORD@bitbucket.org/msyksphinz/riscv_swimmer.git && \
  cd riscv_swimmer/ && git submodule update --init --recursive

RUN cd riscv_swimmer/vendor/gflags && cmake . && make
RUN cd riscv_swimmer/vendor/softfloat/build && cmake . && make
RUN cd riscv_swimmer/build_riscvforest/ && cmake . && make

RISC-VのシステムレジスタCSRの定義について

RISC-Vのシステムレジスタの仕様は、RISC-V Privileged ISA Manual に記載されている。 ここにはシステムレジスタCSRの定義がいくつか記述されている。このなかには、いくつかの略語が使われており、CSR内部のフィールドの扱い方が説明されている。

riscv.org

自分でもよくわからなくなりそうだったのでまとめておいた。

CSRフィールドの仕様

CSR内のフィールドの動作を記述するために、以下の定義と略語を用いる。

Reserved Writes Ignored, Reads Ignore Values (WIRI)

いくつかのRead-only および Read/Writeレジスタには、将来の仕様のためのRead-onlyレジスタを保持している。これらのRead-onlyフィールドは、読み込み時には無視されるべきである。このフィールドへの書き込みは何の効果もないが、CSRレジスタフィールド全体がRead-onlyレジスタの場合は、そのレジスタへの書き込みが発生すると不定命令例外が発生する。これらのフィールドはWIRIと呼ばれる。

Reserved Writes Preserve Values, Reads Ignore Values (WPRI)

いくつかのRead/Writeフィールドは、将来のために予約されている。ソフトウェアはこのフィールドの値は無視するべきであるし、同じレジスタ内の別の有効なフィールドへの書き込みが発生した場合は、あらかじめ設定された値が保持されているべきである。これらのフィールドはWPRIと呼ばれる。

Write/Read Only Legal Values (WLRL)

いくつかのRead/Writeフィールドは、可能なビットエンコーディングのうち一部のみが有効であり、他の値は予約されている場合がある。ソフトウェアは、このフィールドに対して有効な値以外は書くべきではないし、そのフィールドに無効な値を書き込んでから、他の操作(リセットなど)により有効な値が設定されるまでは、意味のある値が読み込まれることを想定すべきではない。

ある命令がサポートされない値をCSRフィールドに書き込んだ場合、例外を発生することができるが必須ではない。ハードウェア実装は、過去に不定な値を書き込んだ場合に任意の値を返すことができるが、その読みだされる値は過去に書き込んだ値に対して確定的でなければならない。

Write Any Values, Reads Legal Values (WARL)

いくつかのRead/Write CSRフィールドは、可能なビットエンコーディングのうち一部のみが有効であるが、任意の値を書き込むことができ常に有効な値を返すことができるものがある。CSRへの書き込みに副作用が存在しない場合、書き込んだ値を読み直すことにより、そのフィールドの有効範囲を知ることができる。このようなフィールドをWARLと呼ぶ。

WARLフィールドにサポートしない値を書き込んでも、例外は発生しない。無効な値を書き込んでも、読み込み動作でほ常に確定的な有効な値が読みだされる。

つまり以下のようになる?

有効値書き込み 無効値書き込み 有効値書き込み→読み込み 無効値書き込み→読み込み
WIRI 無視(CSR全体がRead-onlyの場合例外が発生する) 無視(CSR全体がRead-onlyの場合例外が発生する) 正常読み込み -
WPRI 無視 無視 正常読み込み -
WLRL 正常書き込み 不定 正常読み込み 不定
WARL 正常書き込み 正常値に修正される 正常読み込み 正常読み込み
f:id:msyksphinz:20180417233354p:plain

RISC-Vの浮動小数点命令について

RISC-Vの自作エミュレータを作成している。 テスト自体はriscv-testsリポジトリを使えばよいのだが、パタンが落ちた時の解析がなかなか大変だ。少しずつテストパタンを確認しながら進めている。

特に浮動小数点命令について、 単純にsoftfloatライブラリを使えばよいと思っていたのだがそうでもないらしい。 RISC-V の浮動小数点命令についてしっかり理解しておかなければ、例えば単純な四則演算については簡単に実装できるかもしれないが、単精度と倍精度での移動や、変換命令などのルール、そして比較のルールなどについて引っかかる可能性がある。 これらについてまとめておく必要があるだろう。

RISC-V がカバーする浮動小数点命令

RISC-Vは仕様上32ビット、64ビット、128ビットの浮動小数点命令をカバーしている。 ちなみに、半精度(16ビット)についてはカバーしていないのだが、それは今後サポートされるかどうかはわからない。

RISC-Vの実装やツール群について、カバーしている仕様を表現する表記があるのだが(例えば、RV64IMACだと、64ビットアドレッシングモード、I:整数命令、M:ハードウェア浮動小数点命令、A:アトミック命令、C:16ビット長命令 をサポートしていることを意味する)、

をサポートしていることを意味する。例えば、RV64IMACFDだと、64ビットのアドレッシングモードを持っている命令で、整数命令などに含めて単精度浮動小数点命令と倍精度浮動小数点命令がサポートされていることを意味する。

ちなみに、RV32 / RV64などで示されるアドレッシングモードの数字だが、これは単精度・倍精度などの情報とは全く関係ない。 RISC-Vではハードウェアとしてレジスタが何ビットの長さを持っているのかを示す情報としてXLEN / FLENという情報を持っている。 XLENは整数レジスタのビット幅、FLENは浮動小数レジスタのビット幅を意味する。 なので、例えば、RV32のRISC-V実装であっても倍精度の浮動小数点命令をサポートできるし、逆に注意したいのはFLEN=64でも単精度浮動小数点命令はサポートできる(この場合は、前のエントリで記述した NaN Boxingを参照のこと。

msyksphinz.hatenablog.com

サポートしているシステムレジスタ

RISC-Vの浮動小数点命令をサポートするシステムレジスタとして、frm / fflags / fcsr が用意されている。 基本的にfcsrレジスタを参照しておけばよいだろう。 fflags と frm はそのコピーに過ぎない。

f:id:msyksphinz:20180416010340p:plain
f:id:msyksphinz:20180416010402p:plain
f:id:msyksphinz:20180416010414p:plain
f:id:msyksphinz:20180416010444p:plain

RISC-V の浮動小数点命令をエミュレートするためのsoftfloatの改造

ここが一番キモになるポイントだ。RISC-Vの浮動小数点命令をエミュレートするために、エミュレータである riscv-isa-sim ではsoftfloatを活用している。 ただし、デフォルトのsoftfloatに比べて、微妙な改造をしている。それがsoftfloatに含まれているspecialize.h だ。 この部分を、デフォルトで搭載されているX86のものから改造しなければならない。 riscv-isa-sim を参考に、specialize.h を改造した。

ベースは、riscv-isa-sim を参照すること。

github.com

デフォルトの specialize.h に対して、主に以下の部分を改造した。

diff --git a/vendor/softfloat/SoftFloat-3d/source/riscv/specialize.h b/vendor/softfloat/SoftFloat-3d/source/riscv/specialize.h
index cfcbd31..ed293ce 100644
--- a/vendor/softfloat/SoftFloat-3d/source/riscv/specialize.h
+++ b/vendor/softfloat/SoftFloat-3d/source/riscv/specialize.h
@@ -99,13 +99,16 @@ struct commonNaN {
 | location pointed to by `zPtr'.  If the NaN is a signaling NaN, the invalid
 | exception is raised.
 *----------------------------------------------------------------------------*/
-void softfloat_f16UIToCommonNaN( uint_fast16_t uiA, struct commonNaN *zPtr );
+#define softfloat_f16UIToCommonNaN( uiA, zPtr ) if ( ! ((uiA) & 0x0200) ) softfloat_raiseFlags( softfloat_flag_invalid )

 /*----------------------------------------------------------------------------
 | Converts the common NaN pointed to by `aPtr' into a 16-bit floating-point
 | NaN, and returns the bit pattern of this value as an unsigned integer.
 *----------------------------------------------------------------------------*/
-uint_fast16_t softfloat_commonNaNToF16UI( const struct commonNaN *aPtr );
+#define softfloat_commonNaNToF16UI( aPtr ) ((uint_fast16_t) defaultNaNF16UI)

 /*----------------------------------------------------------------------------
 | Interpreting `uiA' and `uiB' as the bit patterns of two 16-bit floating-
@@ -134,13 +137,15 @@ uint_fast16_t
 | location pointed to by `zPtr'.  If the NaN is a signaling NaN, the invalid
 | exception is raised.
 *----------------------------------------------------------------------------*/
-void softfloat_f32UIToCommonNaN( uint_fast32_t uiA, struct commonNaN *zPtr );
+#define softfloat_f32UIToCommonNaN( uiA, zPtr ) if ( ! ((uiA) & 0x00400000) ) softfloat_raiseFlags( softfloat_flag_invalid )

 /*----------------------------------------------------------------------------
 | Converts the common NaN pointed to by `aPtr' into a 32-bit floating-point
 | NaN, and returns the bit pattern of this value as an unsigned integer.
 *----------------------------------------------------------------------------*/
-uint_fast32_t softfloat_commonNaNToF32UI( const struct commonNaN *aPtr );
+#define softfloat_commonNaNToF32UI( aPtr ) ((uint_fast32_t) defaultNaNF32UI)

 /*----------------------------------------------------------------------------
 | Interpreting `uiA' and `uiB' as the bit patterns of two 32-bit floating-
@@ -169,13 +174,15 @@ uint_fast32_t
 | location pointed to by `zPtr'.  If the NaN is a signaling NaN, the invalid
 | exception is raised.
 *----------------------------------------------------------------------------*/
-void softfloat_f64UIToCommonNaN( uint_fast64_t uiA, struct commonNaN *zPtr );
+#define softfloat_f64UIToCommonNaN( uiA, zPtr ) if ( ! ((uiA) & UINT64_C( 0x0008000000000000 )) ) softfloat_raiseFlags( softfloat_flag_invalid )

 /*----------------------------------------------------------------------------
 | Converts the common NaN pointed to by `aPtr' into a 64-bit floating-point
 | NaN, and returns the bit pattern of this value as an unsigned integer.
 *----------------------------------------------------------------------------*/
-uint_fast64_t softfloat_commonNaNToF64UI( const struct commonNaN *aPtr );
+#define softfloat_commonNaNToF64UI( aPtr ) ((uint_fast64_t) defaultNaNF64UI)

それ以外にも、Max/Min, 比較命令についてはいくつか条件があるので気を付けなければならない。

  • Max命令の実装
  res = (isFloatNaN (op1) && isFloatNaN (op2)) ? FLOAT_STD_QNAN :
        (f32_lt_quiet (f_op2, f_op1) || isFloatNaN (op2) || (f32_eq(f_op1, f_op2) && (op2 & FLOAT_SIGN_BIT))) ? op1 :
        op2;

これ以外にも注意事項については随時追加していく。

「30日でできる!OS自作入門」を読み始めた (18. 19日目)

30日でできる! OS自作入門

30日でできる! OS自作入門

30日でできる!19日目はコマンドをさらに追加する。typeコマンドとか、実行コマンドを追加する。

typeコマンドを実装しているとき、QEMUのバグなのか?GCCのバグなのか?どうしても動かない部分があった。 なんで同じfor文なのに動かないんだ?相当苦労してしまった。

github.com

  • mtask.c
          } else if (cmdline[0]=='t' && cmdline[1]=='y' && cmdline[2]=='p' && cmdline[3]=='e' && cmdline[4]==' ') {
                        for (y = 0; y < 11; y++) {
                          s[y] = ' ';
                        }
...
                        // Find file
                        for (x = 0; x < 224;) {
                          if (finfo[x].name[0] == 0x00) {
                                break;
                          }
                          if ((finfo[x].type & 0x18) == 0) {
                for (int idx = 10; idx >= 0; idx--) {      // 何故かこのコードだと動く
                // for (int idx = 0; idx < 11; idx++) {    // 何故かこのコードでは動かない
                                  if (finfo[x].name[idx] != s[idx]) {
                    goto type_next_file;
                                  }
                                }
                break;  // Find file
              }
            type_next_file:
                          x++;
                        }
...

f:id:msyksphinz:20180415172918g:plain

最後の、アプリケーション起動もとりあえずうまくできるようになった。次はAPIだ...

「30日でできる!OS自作入門」を読み始めた (17. 18日目)

30日でできる! OS自作入門

30日でできる! OS自作入門

30日でできる!19日目はコマンドをさらに追加する。typeコマンドとか、実行コマンドを追加する。

typeコマンドを実装しているとき、QEMUのバグなのか?GCCのバグなのか?どうしても動かない部分があった。 なんで同じfor文なのに動かないんだ?相当苦労してしまった。

github.com

  • mtask.c
          } else if (cmdline[0]=='t' && cmdline[1]=='y' && cmdline[2]=='p' && cmdline[3]=='e' && cmdline[4]==' ') {
                        for (y = 0; y < 11; y++) {
                          s[y] = ' ';
                        }
...
                        // Find file
                        for (x = 0; x < 224;) {
                          if (finfo[x].name[0] == 0x00) {
                                break;
                          }
                          if ((finfo[x].type & 0x18) == 0) {
                for (int idx = 10; idx >= 0; idx--) {      // 何故かこのコードだと動く
                // for (int idx = 0; idx < 11; idx++) {    // 何故かこのコードでは動かない
                                  if (finfo[x].name[idx] != s[idx]) {
                    goto type_next_file;
                                  }
                                }
                break;  // Find file
              }
            type_next_file:
                          x++;
                        }
...

f:id:msyksphinz:20180415172918g:plain

最後の、アプリケーション起動もとりあえずうまくできるようになった。次はAPIだ...

【翻訳】RISC-V進化の振り返りと、次に起こること

2018年3月20日に riscv.org で投稿された、 Krste Asanović 教授のブログが、 RISC-V のこれまでとこれからをよく表現している。

Krste Asanović 教授は RISC-V Foundation の Chairman of the Board を務める、RISC-V Foundationの非常に偉い人だ。 ちなみに Vice Chairman にはチューリング賞を受賞した David Patterson 先生もいる。

riscv.org

せっかくなので Asanović 先生に許可を得て、日本語に翻訳したので公開する。

ただし、私は翻訳の専門家ではないので、訳文に怪しいところがあるかもしれませんがそれはご愛敬ということで... 読みやすい文章にするために、若干意訳になっているところもあります。 原文者の意図を伝えるように翻訳するのって本当に難しいなあ... 精進しなければ。

原文はこちら。

riscv.org

RISC-Vはフリーでオープンである、ということが注目されがちだが、それ以外にISAそのものとしてRISC-Vは非常に慎重に設計されていることが分かる。

またオープンであるがゆえに多くの組織が参入できること、その結果互いの競争が生じて利用者にとってメリットがあること、またRISC-VがISAとして企業から独立していることで、企業の状態に関わらずISAを維持できることがメリットであると思う。


Krste Asanović が語る、RISC-V進化の振り返りと、次に起こること

2018年3月20日

このポストはRISC-V Foundationの取締役議長のKrste Asanović によって書かれたものである。

RISC-VをHot Chips 2014にて初めてロールアウトさせたとき、私たちとバークレイの学生たちはRISC-VのTシャツをきて、 観客にRISC-Vのシリコンのデモを見てもらうためにRISC-Vのバッジを握り締めていたことを今でも思い出します。 Tシャツの着心地はあまりよくはありませんでしたが、RISC-V ISAは産業界を変える大きな流れに成長し、100を超えるメンバがRISC-V Foundationに加入しました。 そこには半導体業界最大規模の会社もいくつか含まれています。

RISC-Vの「フリーでオープンである」という点がメディアで注目されていますが、私はこのブログでは標準としてのRISC-Vについて焦点を当ててみようと思います。 RISC-Vの本当の価値は、この共通のハードウェア仕様に基づいて形成されるソフトウェアとツールのコミュニティによって作られるもので、ハードウェア開発者およびユーザはこのアーキテクチャの恩恵を、迅速に広まる巨大なソフトウェアエコシステムにより享受することが出来ます。 チップ設計者はRISC-Vを選択することで、競争をしている多くのRISC-V IPサプライヤからIPを選択できるという利点があります。 ベンダからRISC-VのIPを選択するか、オープンソースのコアを利用するか、あるいは自分で構築することが出来ます。 これは第2世代のチップ設計においてより重要なことであり、プロプライエタリなISAが抱えているベンダによりロックされていたり、そのISAが長期にわたって提供されるかどうかについて分からない、という心配をする必要がありません。 チップのカスタマーはRISC-V用に幅広く用意されたアプリケーションを使うことが出来るという利点が確約されます。 現在のところ、たとえRISC-Vを取り扱う個々の会社の企業状態がどのようなものになっても、RISC-V自身にとって影響が無いことは明らかです。

私たちは、RISC-Vをモジュール性があり、拡張性の高いISAとして設計しました。 これは同時に回避不可能な分断を発生させたり、オープンスタンダードであることのメリットを薄めてしまう可能性もはらんでおり、もしかしたら一つのプロプライエタリなISAベンダが提供する形を取ったほうが安全なのかもしれません。 しかし、歴史を振り返る限り、一つの源を持つプロプライエタリなISAが、漂流することを防ぐことはない、と言うことです。 一方でこの逆も正しそうに思えます。 独占欲を持った、血気盛んな力により、多くのベンダが利用可能な命令、命令の振る舞いの違い、そして32ビットと64ビットのアドレス空間で完全に異なるISAのサブセットの衝突を伴いながら、ISAを拡張しています。

私は、RISC-V ISA標準の団結がうまく継続していくためには、2つの力が必要だと信じています。 一つは技術的なもの、そしてもう一つは社会学的なものです。

技術的には、カスタマイズ性を残しつつISAの分裂を防ぐために、RISC-Vは小さくてシンプルなベースISAと、モジュールとしての拡張仕様は普遍な仕様とし、非常に多くの領域のコードで動作する部分については固定します。 一方でアプリケーション固有の領域については標準的なISAコアの仕様を妨害することが無いように設計します。 シンプルなベースのISAを固定することにより、開発者がハードウェアのコストや検証時間を削減するために、仕様の一部をダンプまたは変更する動機を削減することが出来ます。 プロセッサを開発している複数の異なる企業がこのシンプルなISAを評価し、RISC-Vは複雑な他のISAとそん色ないという結論に達しています。 実行時のMicro-Op Fusionにより、ハイエンドのRISC-Vプロセッサはシンプルなコアを維持したままISAの定義を拡張することなく、高機能な命令を持つプロセッサの利益を獲得することが出来るようになります。 ほとんどの場合について、一部のアプリケーションのみがカスタム拡張を利用するでしょうし、カスタム拡張を無視して、標準的なツールが標準菜ISAを使ってアプリケーションをコンパイルすることが出来ます。

社会学的には、マルチソースIP・チップ・ツールであるがゆえにベンダは互換性に反するような変更を行わなくなるはずです。 顧客は、ベンダがISAに反する改造を行うようなことを許さないからです。 また、オープンソースソフトウェアコミュニティは任意のISAを使って多くのソフトウェアを開発する力にあふれています。 これらのソフトウェアの、高品質なプライベートフォークを管理し続けるための力は、どのようなベンダでも持っていません。 一方でカスタム拡張は、各ベンダの価値を引き出すための一つの手段となります。 この拡張は一般的にはアプリケーション特有のものであり、ソフトウェア全体に対して非常に小さな部分にしか影響を及ぼしません。 幅広い領域に適用することが出来るものについては、Foundationのレベルで標準に取り込むべきですし、それらはFoundationのタスクグループで活動を行っています。

2018年に、FoundationのメンバはコアISA仕様の多くの部分を承認し、完全な形式のマシンで認識可能なISAの仕様を作成する予定です。 これが実現される前であっても、コミュニティはさまざまな実装の間で多くの相互運用性を示してきました。 Hot Chips 2014の前にISAのバージョン2.0をリリースしたとき、Berkeleyチームは強固に・一方的に、ベースISAの標準拡張の非常に一部についてが「固定された」ことを宣言しました。 仕様に含まれるいくつかの小さな、曖昧な部分については取り除かれた一方で、コミュニティによってデザインされた、非常によく作られたメモリモデルが追加され、2.0の仕様に取り込まれることが承認されました。 今後数年間にわたり、多くのロゴがTシャツに掲載されるでしょうし、デモ用の多くのシリコンが作られるでしょうが、ISAは同じまま続いていくのです。