chibicc compiler を6800向けに改造する (11) whetstone

BASICMASTER, 昔のパソコン

簡易プロファイラができたので、ベンチマークテストを見ながら性能改善を行なっている。今回は Whetstone。

DhrystoneとWhetstoneは、1980-90年代によく使われていたベンチマークテストという印象があります。

作られたのはWhetstoneが先(1972年、ALGOL)、その後名称をもじってDhrystoneが作られました(1984年、Ada)。

現在のchibicc 6800のWhetstone

1MHz clock換算で357.5秒。2.79KWIPS、0.00279MWIPS。 2MHz換算だと、倍になって 5.56KWIPS、0.00556MWIPS。


$ emu6800 6800 whet.bin whet.map
CPU cycles = 2837
CPU cycles = 357464285

Z80 4MHzと比べるとまだまだです。HITECH-Cが古いのに速いんだよな。


乗算が時間を食っている

whetstoneで使われている初等関数(sinとかlogとか)を計算するために、内部で多項式近似を行なっている。そのため乗算が多数回行われており、速度低下の原因になっている。

実際、プロファイラで実行回数を測定すると、浮動小数点乗算の再内周ループを 160万回近く通っていた。

以下の部分。24bit仮数同士を乗算して、48bitの積を計算している。

実はここは、先日のcommitで乗算が30%ほど速くなっている。さらに速くすることには価値があるのだが、改善の良いアイディアが出てこない。

(__workをゼロページに移動すれば addは1cycずつ速くなるけど、誤差です)


__mulf32tos30:
        aslb
        rola
        rol     __work+3
__mulf32tos31:
        rol     __work+2
        rol     __work+1
        rol     __work
        bcc     __mulf32tos32
        addb    @long+3
        adca    @long+2
        psha
        ldaa    __work+3
        adca    @long+1
        staa    __work+3
        pula
        bcc     __mulf32tos32
        inc     __work+2
        bne     __mulf32tos32
        inc     __work+1
        bne     __mulf32tos32
        inc     __work
__mulf32tos32:
        dex
        bne     __mulf32tos30


乗算ルーチンの検討(ベーシックマスター開発 その23)」にて検討したように、Dr Jefyll’s methodを使うと ループ内シフトが3つ減るので、18cyc/ループだけ速くなる。

実に効果的だけど、ループ展開するようなものなので、この部分のプログラムサイズが3倍になるんだよなあ……