SPEC CPU 2006 のインストールと実行
¶ 前書き
SPEC CPU は The Standard Performance Evaluation Corporation(SPEC)が策定した CPU 性能評価指標(Benchmark)です。近年の指標には SPEC CPU 2006 と SPEC CPU 2017 があり、公信力が非常に高いため、多くの研究で評価指標として使われています。
この指標を入手するには、ネット上で無料で手に入るものではなく、SPEC から購入する必要があり高価です。使う必要がある場合は、研究室や共同研究者経由で何とか入手することになります。最近、SPEC CPU 2006/2017 を使った論文を再現する必要があり、研究室にたまたま 2006 版がありました。ただ、使う過程で落とし穴が多かったので記録しておきます。
¶ 環境
私は Docker で環境を作ってテストしました。
本記事は Ubuntu 16.04 をベースに、公式 Docker Image から構築しています。SPEC CPU は v1.1(2008)を使用します。この年代は少しレトロなので、GCC は 4/5/6 あたりのバージョンを推奨します。サーバー CPU は Intel® Xeon® Silver 4110 CPU @ 2.10GHz です。
可能なら、環境をむやみに変えないことを強くおすすめします。こういう巨大なものは、環境が変わるだけで簡単にいろいろハマります。
¶ ソースの準備
SPEC CPU 2006 は元々ディスクの ISO として提供され、ファイル名は SPEC_CPU2006_v1.1.iso です。そのため公式手順では ISO をマウントして作業します。
ただし私は Docker を使っていてマウントが難しかったので、単純に解凍して使いました。
$ sudo apt-get install p7zip-full p7zip-rar
$ mkdir target_dir && cd target_dir
$ mv spec.iso target_dir && 7z x spec.iso
¶ ツールのビルド
ISO にはいくつかのプラットフォーム向けの実行ファイルが含まれていますが、Ubuntu の場合は自分でビルドする必要があります。
$ cd tools/src
$ ./buildtools
ビルド中にいくつかエラーが出るので、順番に解決していきます。
¶ 想定されるエラー
¶ Conflicting types for ‘getline’
エラーメッセージ:
In file included from md5sum.c:38:0:
lib/getline.h:31:1: error: conflicting types for 'getline'
getline PARAMS ((char **_lineptr, size_t *_n, FILE *_stream));
^
getline と getdelim が getline.h と stdio.h の両方で宣言されているのが原因です。次の 2 行を追加します:
+# if __GLIBC__ < 2
int
getline PARAMS ((char **_lineptr, size_t *_n, FILE *_stream));
int
getdelim PARAMS ((char **_lineptr, size_t *_n, int _delimiter, FILE *_stream));
+#endif
¶ Undefined reference to pow
エラーメッセージ:
libperl.a(pp.o): In function `Perl_pp_pow':
pp.c:(.text+0x2a76): undefined reference to `pow'
ビルド時に libm をリンクします:
$ PERLFLAGS="-A libs=-lm -A libs=-ldl" ./buildtools
¶ You haven’t done a “make depend” yet!
エラーメッセージ:
You haven't done a "make depend" yet!
make[1]: *** [hash.o] Error 1
これは /bin/sh が変更されていることが原因です。次を実行してください。ビルド後は必要に応じて元に戻せます。
$ sudo rm /bin/sh
$ sudo ln -s /bin/bash /bin/sh
¶ asm/page.h file not found
エラーメッセージ:
SysV.xs:7:25: fatal error: asm/page.h: No such file or directory
SysV.xs を次のように変更します:
#include <sys/types.h>
#ifdef __linux__
-# include <asm/page.h>
+#define PAGE_SIZE 4096
#endif
¶ perl test fail
上記の問題をすべて解決した後でも、$ PERLFLAGS="-A libs=-lm -A libs=-ldl" ./buildtools を実行すると、900 個中 9 個程度のテストが失敗します(すべて perl 関連)。これは無視できるので、ここでは無視します。
ビルド後に次のように聞かれます:
Hey! Some of the Perl tests failed! If you think this is okay, enter y now:
ここでは y を入力してください。 ただし時間制限があり、反応が遅いと NO 扱いで進んでしまいます。 私は一度これで全ビルドをやり直す羽目になりました。本当に時間がかかります。
すべて成功すると次の表示が出ます:
Tools built successfully. Go to the top of the tree and
source the shrc file. Then you should be ready.
¶ 実行
¶ 設定ファイル
理論上は config 配下に複数のサンプル .cfg があり、環境に合うものを選べます。また config/flags 配下にもサンプルの flags 設定ファイルがあるはずですが、例外もあります。たとえば私が入手したものには含まれていなかったので、環境に合う設定ファイルを SPEC 公式サイト から取得する必要があります。
¶ 設定の有効化
$ source ./shrc
¶ 実行
ベンチマークは runspec で実行します。前の手順で source したときに、環境変数として取り込まれます。
例として mcf を実行する場合、私の設定ファイルは Example-linux-ia64-gcc.cfg で、次のように実行できます:
$ runspec --iterations 1 --size ref \
--action onlyrun \
--config Example-linux-ia64-gcc.cfg \
--noreportable mcf
実行結果は次のようになります:
Reading config file '/work/spec/config/Example-linux-ia64-gcc.cfg'
Benchmarks selected: 429.mcf
Compiling Binaries
Up to date 429.mcf base ia64-gcc42 default
Setting Up Run Directories
Setting up 429.mcf ref base ia64-gcc42 default: existing (run_base_ref_ia64-gcc42.0000)
Running Benchmarks
Running 429.mcf ref base ia64-gcc42 default
/work/spec/bin/specinvoke -d /work/spec/benchspec/CPU2006/429.mcf/run/run_base_ref_ia64-gcc42.0000 -e speccmds.err -o speccmds.stdout -f speccmds.cmd -C
Run Complete
The log for this run is in /work/spec/result/CPU2006.018.log
runspec finished at Tue Jun 16 01:21:05 2020; 379 total seconds elapsed
結果を得た後は、さらにシステムの性能分析を行えますが、それは本記事の範囲外とします。
¶ 結論
本記事では Ubuntu 16.04 上で SPEC CPU 2006 v1.1 をインストールして実行する方法を紹介しました。いくつかのエラーが発生することを前提に、その解決方法を記録しました。
¶ 参考資料