Gem5ではサイクルレベルでのシミュレーションが可能で、モードによってはO3トレースファイルという情報を出力してパイプラインの動作の様子を確認することができる。
もう少し統計的な情報を出力したいときは、m5out/stats.txt
というデータが便利だ。各命令に関する統計情報や、パイプラインの統計情報が示されている。
---------- Begin Simulation Statistics ---------- simSeconds 0.000019 # Number of seconds simulated (Second) simTicks 19032500 # Number of ticks simulated (Tick) finalTick 3180986000 # Number of ticks from beginning of simulation (restored from checkpoints and never reset) (Tick) simFreq 1000000000000 # The number of ticks per simulated second ((Tick/Second)) hostSeconds 1.17 # Real time elapsed on the host (Second) hostTickRate 16260795 # The number of ticks simulated per host second (ticks/s) ((Tick/Second)) hostMemory 674916 # Number of bytes of host memory used (Byte) simInsts 5983783 # Number of instructions simulated (Count) simOps 6614261 # Number of ops (including micro ops) simulated (Count) hostInstRate 5112060 # Simulator instruction rate (inst/s) ((Count/Second)) hostOpRate 5650645 # Simulator op (including micro ops) rate (op/s) ((Count/Second)) system.clk_domain.clock 1000 # Clock period in ticks (Tick) system.cpu.numCycles 38065 # Number of cpu cycles simulated (Cycle) system.cpu.numWorkItemsStarted 0 # Number of work items this cpu started (Count) system.cpu.numWorkItemsCompleted 0 # Number of work items this cpu completed (Count) system.cpu.instsAdded 25303 # Number of instructions added to the IQ (excludes non-spec) (Count) system.cpu.nonSpecInstsAdded 2 # Number of non-speculative instructions added to the IQ (Count) system.cpu.instsIssued 25255 # Number of instructions issued (Count) system.cpu.squashedInstsIssued 12 # Number of squashed instructions issued (Count) system.cpu.squashedInstsExamined 177 # Number of squashed instructions iterated over during squash; mainly for profiling (Count) system.cpu.squashedOperandsExamined 160 # Number of squashed operands that are examined and possibly removed from graph (Count) system.cpu.squashedNonSpecRemoved 1 # Number of squashed non-spec instructions that were removed (Count) system.cpu.numIssuedDist::samples 37671 # Number of insts issued each cycle (Count) system.cpu.numIssuedDist::mean 0.670410 # Number of insts issued each cycle (Count) system.cpu.numIssuedDist::stdev 0.885386 # Number of insts issued each cycle (Count) system.cpu.numIssuedDist::underflows 0 0.00% 0.00% # Number of insts issued each cycle (Count) system.cpu.numIssuedDist::0 20991 55.72% 55.72% # Number of insts issued each cycle (Count) system.cpu.numIssuedDist::1 10121 26.87% 82.59% # Number of insts issued each cycle (Count)
しかし場合によっては、ある特定の領域のみの統計情報を取りたいということも出てくるだろう。この「特定の領域」のことをROI(Region of Interest)と呼ぶのだが、これをプログラム中に設定することによって、Gem5の統計情報を取得するプログラムの領域を変更できる。
https://github.com/gem5/gem5/blob/stable/util/m5/src/abi/arm64/m5op.S
上記のコードが示している通り、特定の特殊なコードを埋め込むことにより、Gem5内の挙動を制御することができる。
- AArch64の場合
.macro m5op_func, name, func .globl \name \name: .long 0xff000110 | (\func << 16) ret .endm
- RISC-Vの場合
.macro m5op_func, name, func .globl \name \name: .long 0x0000007b | (\func << 25) ret .endm
#define M5OP_RESET_STATS 0x40 #define M5OP_DUMP_STATS 0x41
M5OP(m5_reset_stats, M5OP_RESET_STATS) \ M5OP(m5_dump_stats, M5OP_DUMP_STATS) \
つまり、この特殊なコードを埋め込むことで、Gem5の挙動を制御する。ROIの前後に、この特殊コードを埋め込む。
#ifdef GEM5 /* resetstats */ __asm__ __volatile__ ("isb; mov x0, #0; mov x1, #0; .inst 0XFF000110 | (0x40 << 16);" : : : "x0", "x1"); #endif // GEM5 matrix_multiply_neon(A, B, D, n, m, k); #ifdef GEM5 /* resetstats */ __asm__ __volatile__ ("isb; mov x0, #0; mov x1, #0; .inst 0XFF000110 | (0x41 << 16);" : : : "x0", "x1"); #endif // GEM5
本当はもうちょっとちゃんとしたマクロを埋め込んでもいいのだが、いろんなファイルをincludeするのが面倒なので、例えばAArch64なら決め打ちでインラインアセンブリを入れてしまっていいと思う。
ちなみにこの特殊コードは、もちろん実機や他のシミュレータでは動作しないので、Gem5以外でバイナリを流すときはこのコードを除去すること。
これにより、m5out/stats.txt
の情報が当該ROI内のみの情報に限定される。