質問
SSEでは、プレフィックス 066h
(オペランドサイズオーバーライド) 0F2H
(repne)および 0F3h
(REPE)はOPCODEの一部です。
非SSEで 066h
32ビット(または64ビット)と16ビット操作の間の切り替え。 0F2h
と 0F3h
文字列操作に使用されます。それらを組み合わせることができます 066h
と 0F2h
(また 0F3h
)これは意味のあるものであるため、同じ命令で使用できます。 SSE命令の動作は何ですか?たとえば、(今のところmod/rmを無視しています):
0f 58
--> addps
66 0f 58
--> addpd
f2 0f 58
--> addsd
f3 0f 58
--> addss
しかし、これは何ですか?
66 f2 0f 58
そして、どうですか?
f2 66 0f 58
矛盾する2つのプレフィックスがある以下は言うまでもありません。
f2 f3 0f 58
これらの仕様は何ですか?
解決
ランダムなプレフィックスを乱暴に組み合わせた場合に期待するべきことについての仕様を見たことを覚えていないので、CPUの動作は「未定義」であり、おそらくCPU固有である可能性があると思います。 (明らかに、いくつかのことはIntelのドキュメントなどで指定されていますが、多くの場合はカバーされていません)。また、いくつかの組み合わせが将来の使用のために予約される場合があります。
私の素朴な仮定は、一般に、追加の接頭辞はノーオープであるが、保証はないということでした。たとえば、いくつかの最適化マニュアルがマルチバイトを推奨することを考えると、それは合理的に思えます NOP
(標準的に 90h
)プレフィックスによる 66h
, 、例:
db 66h, 90h; 2-byte NOP
db 66h, 66h, 90h; 3-byte NOP
db 66h, 66h, 66h, 90h; 4-byte NOP
しかし、私もそれを知っています CS
と DS
セグメントオーバーライドプレフィックスには、SSE2ブランチヒントプレフィックスとしてAquired Now機能があります(Branch Take = Predict = 3Eh
= DS
オーバーライド;予測ブランチが取られていない= 2Eh
= CS
オーバーライド)条件付きジャンプ命令に適用した場合。
とにかく、私は上記の例を見ました、常に設定します XMM1
すべてに 0
と XMM7
すべてに 0FFh
に
pxor xmm1, xmm1 ; xmm1 <- 0s
pcmpeqw xmm7, xmm7 ; xmm7 <- FFs
そして、問題のコード、 xmm1, xmm7
議論。私が観察したのは(Win64 SystemとIntel T7300 Core 2 Duoの32ビットコード)でした。
1)変化は観察されません addsd
追加することによって 66h
プレフィックス
db 66h
addsd xmm1, xmm7 ;total sequence = 66 F2 0F 58 CF
2)変化は観察されません addss
追加することによって 0F2h
プレフィックス
db 0f2h
addss xmm1,xmm7 ;total sequence = F2 F3 0F 58 CF
3)しかし、私はプレフィックスによって変化を観察しました addpd
に 0F2h
:
db 0f2h
addpd xmm1, xmm7 ;total sequence = F2 66 0F 58 CF
この場合、XMM1の結果は 0000000000000000FFFFFFFFFFFFFFFFh
それ以外の FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFh
.
そう 私の結論は、仮定をして、「未定義の」行動を期待するべきではないということです. 。しかし、あなたがアグナー・フォグにいくつかの手がかりを見つけることができれば、私は驚かないでしょう マニュアル.