0

我正在研究用Visual Studio 2008編譯的一些代碼的反彙編,並且我發現在代碼中發現一些奇怪的「優化」,在調用函數時不太合理並傳遞參數。例如,下面的代碼輸出以下拆解:未知的編譯器「優化」沒有意義

代碼:

int version; 
int result = canParse(code, &version);` 

拆卸:

003CE9FA push eax    ; version 
003CE9FB push ecx    ; code 
003CE9FC mov  ecx, [esp+50h+code] ; AbcParser * 
003CEA00 mov  eax, esp 
003CEA02 mov  [eax], ecx 
003CEA04 call avmplus::AbcParser::canParse(avmplus::ScriptBuffer,int *) 

在這種情況下,push ecx使得堆棧中的部分空間然後被[esp+50h+code]覆蓋。

爲什麼編譯器會這樣做?

它不節省空間。 (需要更少的空間才能擁有mov ecx, [esp+50h+code]; push ecx。)據我所知,這並不能節省時間。 (不會執行剛剛提到的兩條指令會更快嗎?)

此外,在canParse中使用ecxeax時都會被覆蓋。

+1

也許它是更多的指令,但更少的時鐘週期? – 2011-04-21 19:32:19

+0

@drhirsch:他是對的:'mov ecx,[esp + 50h + code]; mov eax,esp; mov [eax],ecx'與mov [esp],[esp + 50h + code]相同(我知道它是非法尋址模式),因此覆蓋上次推動的東西 – BlackBear 2011-04-22 11:57:46

+0

@BlackBear:像「push dword [esp + 50h + code]「是有效的,可以替代4條指令。我也會試圖假設「優化器不完美」比「更多指令但更少循環」更可能。 – Brendan 2011-04-22 12:33:27

回答

0

正如@Radek Pro-Grammer在他的評論中所建議的那樣,即使有更多的指令看起來毫無用處,代碼可能會在更少的時鐘週期內運行。現在的處理器要複雜得多,有流水線,預取隊列,緩存,超標量設計等等,所以優化可以相當大膽。 :)