簡體   English   中英

可能要合並r1,r1嗎?

[英]Possible to mul r1,r1?

如果我有

movmr x,r1

有可能嗎?

mul r1,r1 

(x*x) 我正在嘗試有效地執行此操作以節省字節,但這是迄今為止我能想到的最好的解決方案,並且似乎無法找到是否允許這樣做。

整個方程為(x+y)(xy) ,因此我將其簡化為x^2 - y^2

此外,如果您想知道,f + d / exe是基於每個字節的。

OPC = 8位,x / y = 20位,reg = 3位。 所以movmr x,r1是4f + d和4 exe

編輯:我們正在使用基於Linux的系統

OPC | DST,SRC,XX | <= | 1byte | 1byte |

大多數ISA都沒有這種限制,任何有限制的都可以記錄下來。

通常,指令在寫入任何輸出操作數之前先讀取其所有輸入操作數,因此,如果它們重疊,就可以了。 任何限制都將始終記錄在ISA手冊/指令集參考中。

通常,您只會發現對寫入多個寄存器的指令的限制,在這種情況下,當您為兩個輸出提供相同的寄存器時,異常行為或非法指令異常是正常的。 例如, AVX512 vpgatherqq

如果目標向量zmm1與索引向量VINDEX相同,則該指令將#UD錯誤。

AVX2版本在ISA參考手冊中沒有提及這一點,但我忘記了在其他任何地方是否有反對它的規則。


一種非法的情況是ARM: MUL Rd, Rm, Rs確實Rd := Rm × Rs

在早期的ARM版本(?)中,如果Rd和Rm是同一寄存器,則該行為是不可預測的。 ARM Wiki和一些正式的ARM文檔版本)。 也許早期的微體系結構進行了一些多步微編碼計算,並將結果累加到目標寄存器中。

MUL     r1,r1,r6    ; incorrect: Rd cannot be the same as Rm
MUL     r1,r6,r1    ; correct:  r1 *= r6

更高版本的ARM文檔沒有提及此限制,因此我想它不適用於更高的體系結構嗎? 否則,谷歌找不到合適的ISA文檔。 這些似乎是ARM匯編程序的文檔。 以后的ARM體系結構版本肯定沒有此限制,但是IDK為什么后來的文檔沒有提到取消限制的時間。

davespace表示 Rs和Rm(兩個源操作數)不能相同。 這與任何其他文檔所說的都不匹配,並且從微體系結構的角度講意義不大,所以我認為這是錯誤的。


ARM的32x32 => 64位全乘umull Rhi, Rlo, Rm, Rs也有一個限制:Rhi,Rlo和Rm都必須是不同的寄存器。

UMULL  r1, r0, r0, r0     ; unpredictable, Rlo and Rm are the same. 
UMULL  r2, r1, r0, r0     ; r2:r1  =  r0*r0

整個方程為(x+y)(xy) ,因此我將其簡化為x^2 - y^2

在沒有任何周圍代碼的情況下,這種轉換使它變得更加昂貴,而不是更少。 添加/訂閱比乘法便宜:更好的吞吐量和更低的延遲。 在x86上,給定寄存器中的x和y,

; x=eax
; y=edx

lea  ecx, [rax + rdx]     ; x+y
sub  eax, edx             ; x-y
imul ecx, eax             ; (x+y) * (x-y)

Intel SnB系列的4個周期延遲。 (3循環imul ,和LEA /子可以並行運行。 http://agner.org/optimize/ )。

imul  eax, eax
imul  edx, edx
sub   eax, edx

如果eax和edx同時准備就緒,則有5個周期的延遲。 沒有現有的x86 CPU具有超過1個標量乘法執行單元,因此存在資源沖突:第二個imul必須等待一個周期才能執行。 取決於周圍的代碼,端口1可能不是吞吐量瓶頸,也許其中一個輸入或另一個輸入都可以提前一個周期准備好。

但是,如果xy是不變的,則只需2條指令,您就可以通過這種方式便宜地計算出新的(x+y) * (xy) ,CSE處理不變的平方。

這會破壞兩個輸入,因此如果之后需要x或y,則需要mov 另一個版本保留y (在edx )並將xy保留在寄存器中。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM