MIPSのHIおよびLOレジスタに値を保存する
-
05-07-2019 - |
質問
MIPSで特定のコードを書いていますが、結果を一時的に HI
および LO
の特殊レジスターに保存することが要件になりました(両方とも4バイト幅です)。これらの手順は自由です:
divu s,t lo <-- s div t ; hi <-- s mod t
multu s,t hi / lo < -- s * t ;
したがって、 divu
は除算の結果を LO
に、残りを HI
に保存し、 multu
は LO
(下位4バイト)と HI
(上位4バイト)の乗算。
後で、 HI
および LO
レジスタから結果を取得するには、次のようにします。
mfhi $v0
mflo $v1
すでに LO
に計算結果を保存する方法を見つけました:
ori $v0,multu $a0,0x80000000 # Shift $a0 by 32 bits and store into HI/LO
,1 # Store result from $a0 into LO
divu $a0,$v0
-
divu
は除算の結果をLOに格納するため、結果を1で除算してそこに到達します。
ただし、 HI
への保存はより複雑です。 1つの方法は、 multu
命令に値を32ビット(4バイト)シフトさせることです:
しかし、結果は HI
の値が本来あるべき場所の1ビット右になります(したがって、私の値が 0100 1000
ならば HI
には 0010 0100
)が含まれます。
HI
レジスタに何かを保存する方法を知っていますか?
解決
Nils Pipenbrinckの回答を拡張したい:
プログラマ向けMIPS32 arquitechtureから
mthi
形式:MIPS32(MIPS I)
MTHI rs
目的: GPRを特別な目的のHIレジスタにコピーするには
Description: HI ← rs
GPR rsの内容が特殊レジスターHIにロードされます。
制限:
DIV、DIVU、MULT、またはMULTUによってHI / LOペアに書き込まれた計算結果は、MFHIまたはMFLOによって読み取られる必要があります 新しい結果をHIまたはLOに書き込む前に。 MTHI命令がこれらの算術命令の1つに続いて、MFLOまたはMFHIの前に実行される場合 命令、LOの内容は予測不能です。次の例は、この違法な状況を示しています。
MUL r2,r4 # start operation that will eventually write to HI,LO
... # code not containing mfhi or mflo
MTHI r6
... # code not containing mflo
# this mflo would get an UNPREDICTABLE value
MFLO r3
履歴情報:
MIPS I-IIIでは、前述の2つの命令のいずれかがMFHIである場合、そのMFHIの結果は予測不能です。 HIまたはLO特殊レジスターの読み取りは、それらに書き込む後続の命令から2つ分離する必要があります 以上の指示。 MIPS 32以降を含むMIPS IV以降では、この制限は存在しません。
mtlo
形式:MIPS32(MIPS I)
MTLO rs
目的: GPRを特別な目的のLOレジスタにコピーするには 説明:
LO ← rs
GPR rsの内容が特殊レジスターLOにロードされます。
制限: DIV、DIVU、MULT、またはMULTUによってHI / LOペアに書き込まれた計算結果は、新しい結果をHIまたはLOに書き込む前に、MFHIまたはMFLOで読み取る必要があります。
これらの算術命令の1つに続いて、MFLOまたはMFHI命令の前にMTLO命令が実行された場合、HIの内容は予測不能です。 次の例は、この違法な状況を示しています。
MUL r2,r4 # start operation that will eventually write to HI,LO
... # code not containing mfhi or mflo
MTLO r6
... # code not containing mfhi
# this mfhi would get an UNPREDICTABLE value
MFHI r3
履歴情報:
MIPS I-IIIでは、前述の2つの命令のいずれかがMFHIである場合、そのMFHIの結果は予測不能です。 HIまたはLO特殊レジスターの読み取りは、それらに書き込む後続の命令から2つ分離する必要があります。 以上の指示。 MIPS 32以降を含むMIPS IV以降では、この制限は存在しません。
他のヒント
MIPS命令セットには、MFLO / MFHIに対応するものがあります。
MTLO / MTHIと呼ばれ、希望どおりに動作します:
mtlo $v0 # moves the contents of v0 into the lo-register
mthi $v1 # moves the contents of v1 into the hi-register
これらの命令はまれであり、多くの場合、要約された命令セットのリファレンスには含まれていません。
ところで:プロセッサのマニュアルで、LO / HIレジスタに関連するレイテンシと危険性を確認してください。これらは非常に特殊であり、コードは書き込みと読み取りの間に少なくとも3サイクル待機する必要がある場合があります。残念ながら、この動作は、使用しているCPUによって異なります。
これを間違えることは、MIPS志望のプログラマーにとってよくある落とし穴です:-)