當前位置:首頁 » 編程軟體 » 粉色的編譯器

粉色的編譯器

發布時間: 2025-01-15 14:41:36

編譯器生成的匯編語句執行順序為什麼與C代碼順序不同

不影響語義的前提下編譯器可以任意重排代碼順序;
在亂序執行(Out-of-Order)的CPU里,機器碼的執行也可以不按照你在「匯編」層面上看到的順序執行,只要不影響語義。
所以說這些中間步驟的順序,作為底層細節平時不需要那麼在意——它們多半跟原始源碼的順序是不一樣的。

現代優化編譯器優化的思路之一是「基於依賴的優化」(dependence-based optimization)。題主引用的CSAPP的例子:

int arith(int x, int y, int z) {
int t1 = x + y;
int t2 = z * 48;
int t3 = t1 & 0xFFFF;
int t4 = t2 * t3;
return t4;
}

所有涉及運算的值都是局部標量變數(local scalar variable),這是最便於編譯器做分析的情況,所有依賴都可以顯式分析。
由於整個函數沒有分支,這里也不需要討論控制依賴(control dependence),只要討論數據依賴(data dependence)就好。
把數據依賴圖畫出來是個DAG(這里正好是棵樹,特例了):

x y z 48
\ / \ /
t1 0xFFFF t2
\ / /
t3 /
\ /
t4

優化必須要滿足的約束是:每個節點求值之前,其子節點(依賴的數據源)必須要先求了值。
顯然,t1和t2之間沒有依賴關系,它們的相對求值順序怎樣重排都沒關系。

有本我很喜歡的書,裡面講的是各種基於依賴的優化:Optimizing Compilers for Modern Architectures - A Dependence-based Approach

以上是理論部分。

================================================================

下面來看例子。

我們可以用一個實際編譯器來看看CSAPP的例子編譯出來的結果:

.text
# -- Begin arith
.p2align 4,,15
.globl arith
.type arith, @function
arith:
.p2align 4,,7
/*.L0:*/ /* Block BB[54:2] preds: none, freq: 1.000 */
movl 8(%esp), %edx /* ia32_Load T[139:10] -:1:22 */
addl 4(%esp), %edx /* ia32_Add Iu[141:12] -:2:14 */
movzwl %dx, %edx /* ia32_Conv_I2I Iu[142:13] -:4:15 */
imull 12(%esp), %edx /* ia32_IMul Iu[143:14] -:5:15 */
leal (%edx,%edx,2), %eax /* ia32_Lea Iu[144:15] -:5:15 */
shll $0x4, %eax /* ia32_Shl Iu[146:17] -:5:15 */
ret /* ia32_Return X[152:23] -:6:3 */
.size arith, .-arith
# -- End arith

這里用的是libFirm。可見它跟CSAPP書里所說的匯編的順序又有所不同。這也是完全合理的。
這個編譯結果的順序是:

edx = y;
edx += x;
edx = zeroextend dx; // edx = edx & 0xFFFF
edx *= z;
eax = edx * 3;
eax <<= 4; // eax = eax * 16

也是完全符合依賴關系的約束的一種順序。
之所以用libFirm舉例是因為它的中間表示(Intermediate Representation)是一種程序依賴圖(Program Dependence Graph),可以很方便的看出控制與數據依賴。把CSAPP那裡例子對應的libFirm IR畫出來,是這個樣子的:
(這張圖跟我前面畫的數據依賴圖正好是左右翻轉的,不過意思一樣。(這張圖跟我前面畫的數據依賴圖正好是左右翻轉的,不過意思一樣。
Arg 0、1、2分別代表x、y、z。白色方塊是普通數據節點,黃色方塊是常量節點,藍色方塊是內存相關節點,紅色方塊是控制流節點,粉紅色方塊是特殊的開始/結束節點。)

某版LLVM生成的代碼:

; MoleID = '/tmp/webcompile/_16355_0.bc'
target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
target triple = "x86_64-ellcc-linux"

; Function Attrs: nounwind readnone
define i32 @arith(i32 %x, i32 %y, i32 %z) #0 {
entry:
%add = add nsw i32 %y, %x
%mul = mul nsw i32 %z, 48
%and = and i32 %add, 65535
%mul1 = mul nsw i32 %mul, %and
ret i32 %mul1
}

attributes #0 = { nounwind readnone "less-precise-fpmad"="false" "no-frame-pointer-elim"="false" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="false" }

!llvm.ident = !{!0}

!0 = !{!"ecc 0.1.10 based on clang version 3.7.0 (trunk) (based on LLVM 3.7.0svn)"}

最終生成的x86匯編:

.text
.file "/tmp/webcompile/_15964_0.c"
.globl arith
.align 16, 0x90
.type arith,@function
arith: # @arith
# BB#0: # %entry
movl 8(%esp), %eax
addl 4(%esp), %eax
movzwl %ax, %eax
imull 12(%esp), %eax
shll $4, %eax
leal (%eax,%eax,2), %eax
retl
.Ltmp0:
.size arith, .Ltmp0-arith

.ident "ecc 0.1.10 based on clang version 3.7.0 (trunk) (based on LLVM 3.7.0svn)"
.section ".note.GNU-stack","",@progbits

GCC 4.9.2 x86-64:

arith(int, int, int):
leal (%rdx,%rdx,2), %eax
addl %edi, %esi
movzwl %si, %esi
sall $4, %eax
imull %esi, %eax
ret

Zing VM Server Compiler x86-64:

# edi: x
# esi: y
# edx: z
movl %edx, %eax
shll $0x4, %eax
leal (%rsi, %rdi, 1), %ecx
shll $0x5, %edx
addl %edx, $eax
movzwl %ecx, %edx
imull %edx, %eax

❷ 現在千元機性價比排行

1、realme X2。6+64GB截止2020年4月是1399元。

realme X2這款手機不但性能強,價格也很便宜。在去年安兔兔的千元機皇排行榜上,這款手機也是榮登榜首,可見這款手機的性價比力度。AMOLED屏幕,驍龍730G處理器。4000mAh電池配上30W超級閃充。後置6400萬像素四攝。

一款性能十分均衡,沒有短板的千元機。唯一的缺點可能就是系統,realme UI日常用起來可能不太習慣。



2、vivo Z5。6+64GB截止2020年4月是1398元。

雖然這部手機發布已經七八個月的時間,不過我們依然不能忽略這款手機的超高性價比。Z系列作為vivo的線上性價比系列,也是出過很多不錯的手機。這款vivo Z5採用AMOLED水滴屏設計。後置4800萬像素三攝,前置3200萬像素鏡頭。

這次的Z5主打的也是一個長續航。4500mAh大電池配上22.5W快充。七八個小時的長續航也是沒有問題。


❸ 問道字體顏色代碼

  • 字體顏色代碼有:

    白色 #FFFFFF;紅色 #FF0000;綠色 #00FF00;藍色 #0000FF;牡丹紅 #FF00FF;

    青色 #00FFFF;黃色 #FFFF00;黑色 #000000;海藍 #70DB93;巧克力色 #5C3317等。

❹ devc如何輸出粉色

無法輸出粉色。devc中輸出或者輸入字體和背景的顏色,C=淡紅色,D=淡紫色,E=淡黃色,F=亮白色,無法輸出粉色。Dev是一個開發工具,它包括多頁面窗口、工程編輯器,在工程編輯器中集合了編輯器、編譯器、連接程序和執行程序,它也提供高亮度語法顯示的,以減少編輯錯誤。

熱點內容
手動安裝交叉編譯鏈 發布:2025-01-15 18:15:30 瀏覽:563
java調用clinux 發布:2025-01-15 18:13:02 瀏覽:293
如何給孩子配置一份保險 發布:2025-01-15 18:07:53 瀏覽:456
思科模擬器ftp配置 發布:2025-01-15 18:01:53 瀏覽:196
wd軟體如何修改密碼 發布:2025-01-15 17:59:57 瀏覽:715
公共代理伺服器地址 發布:2025-01-15 17:59:53 瀏覽:818
android文件圖片 發布:2025-01-15 17:39:44 瀏覽:206
linux的路徑怎麼寫 發布:2025-01-15 17:18:49 瀏覽:185
php解壓程序 發布:2025-01-15 17:06:22 瀏覽:142
刷助力腳本 發布:2025-01-15 17:02:31 瀏覽:520