#include #include volatile int start[4];
volatile int done[4];
void *work(void *param)
printf("thread %i started\n", id);
double total = 0;
for(int i = 0; i < 100000000; i++)
printf("thread %i done\n", id);
done[id] = 1;
}int main()
for(int i = 0; i < 4; i++)
for(int i = 0; i < 4; i++) }
for(int i = 0; i < 4; i++)
}
有優化及無優化的輸出:
有優化的情況下,編譯器合併設定變數start和讀取變數done的兩個迴圈的**,產生的**和下面類似。
兩個迴圈不含函式呼叫,所以編譯器認為對volatile變數的訪問無***。因此,編譯器認為合併兩個迴圈是
安全的。
編譯器優化的**:
int main()
for(int i = 0; i < 4; i++) }
for(int i = 0; i < 4; i++)
}
使用gcc的asm("":::"memory"),可以使編譯器對迴圈正確排序。這條語句避免了迴圈合併,且不會像**增加
額外指令。
使用gcc的asm語句時操作順序正確:
int main()
for(int i = 0; i < 4; i++)
asm volatile("":::"memory");
for(int i = 0; i < 4; i++) }
for(int i = 0; i < 4; i++)
}
windows也為這一目的提供了內部函式。函式_readbarrier()、_writebarrier()和_readwritebarrier()在檔案中定義。這些內部函式告訴編譯器不要對這些操作重新排序。_readbarrier()呼叫確保所有讀操作在該點完成,_writebarrier()呼叫確保所有寫操作在該點完成。這些指令僅強制編譯器排序,但不生成任何指令。 Mac OS X作業系統的編譯器
在xcode中,可以使用三個編譯器 gcc4.2,llvm gcc 4.2,llvm complier clang 介面如下圖 gcc 還有乙個gcc 4.0版本提供 以上兩個圖上中的 llvm complier 2.0 和 clang 是同乙個東西。在macos上用xcode開發c c 程式,可以...
Mac OS X作業系統的編譯器
在xcode中,可以使用三個編譯器 gcc4.2,llvm gcc 4.2,llvm complier clang 介面如下圖 gcc 還有乙個gcc 4.0版本提供 以上兩個圖上中的 llvm complier 2.0 和 clang 是同乙個東西。在macos上用xcode開發c c 程式,可以...
VC編譯器與GCC編譯器的區別
今天無意寫了一段 發現了vc編譯器與gun的gcc編譯器還是存在區別的。畢竟gcc支援的是標準c。include struct node int main 上述 在gcc下是編譯失敗的,提示的錯誤 uknown typename node 但是放到vc編譯器下則順利編譯通過。於是按照標準c寫了另外乙...