2013-12-10 66 views
1

我一直在使用gcc的-O優化選項在我的項目模塊之一中發現「虛擬內存耗盡:無法分配內存」錯誤。如果我從命令行刪除-O,錯誤消失。海灣合作委員會優化級別1的子選項

我檢查GCC規範,發現下列選項與-O

 -fauto-inc-dec 
     -fcompare-elim 
     -fcprop-registers 
     -fdce 
     -fdefer-pop 
     -fdelayed-branch 
     -fdse 
     -fguess-branch-probability 
     -fif-conversion2 
     -fif-conversion 
     -fipa-pure-const 
     -fipa-profile 
     -fipa-reference 
     -fmerge-constants 
     -fsplit-wide-types 
     -ftree-bit-ccp 
     -ftree-builtin-call-dce 
     -ftree-ccp 
     -ftree-ch 
     -ftree-copyrename 
     -ftree-dce 
     -ftree-dominator-opts 
     -ftree-dse 
     -ftree-forwprop 
     -ftree-fre 
     -ftree-phiprop 
     -ftree-slsr 
     -ftree-sra 
     -ftree-pta 
     -ftree-ter 
     -funit-at-a-time 

我的新的命令行啓用現已以下選項添加

-fauto-inc-dec -fdce -fdefer-pop -fdse -fguess-branch-probability -fif-conversion2 -fif-conversion -fipa-pure-const -fipa-reference -fmerge-constants -fsplit-wide-types -ftree-builtin-call-dce -ftree-ccp -ftree-ch -ftree-copyrename -ftree-dce -ftree-dominator-opts -ftree-dse -ftree-forwprop -ftree-fre -ftree-phiprop -ftree-sra -ftree-pta -ftree-ter -funit-at-a-time -g -pipe -Wall -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector -fno-var-tracking -fno-var-tracking-assignments但我無法重現該問題。

一些選項是由我使用的(我曾經在命令行中刪除)的gcc版本無法識別

GCC -v

Using built-in specs. 
COLLECT_GCC=/usr/bin/gcc 
COLLECT_LTO_WRAPPER=/usr/libexec/gcc/i686-redhat-linux/4.5.1/lto-wrapper 
Target: i686-redhat-linux 
Configured with: ../configure --prefix=/usr --mandir=/usr/share/man --infodir=/usr/share/info --with-bugurl=http://bugzilla.redhat.com/bugzilla --enable-bootstrap --enable-shared --enable-threads=posix --enable-checking=release --with-system-zlib --enable-__cxa_atexit --disable-libunwind-exceptions --enable-gnu-unique-object --enable-linker-build-id --enable-languages=c,c++,objc,obj-c++,java,fortran,ada,lto --enable-plugin --enable-java-awt=gtk --disable-dssi --with-java-home=/usr/lib/jvm/java-1.5.0-gcj-1.5.0.0/jre --enable-libgcj-multifile --enable-java-maintainer-mode --with-ecj-jar=/usr/share/java/eclipse-ecj.jar --disable-libjava-multilib --with-ppl --with-cloog --with-tune=generic --with-arch=i686 --build=i686-redhat-linux 
Thread model: posix 
gcc version 4.5.1 20100924 (Red Hat 4.5.1-4) (GCC) 

誰能給一個想法是什麼可能會出錯?

感謝

P.S:我試圖編譯具有存在STL東西的加載代碼。

+0

你爲什麼不建造64位?另外,GCC或運行時錯誤? – egur

+0

錯誤來自鏈接時的gcc。 –

+0

當用'-o3'或'-o2'構建時會發生什麼?你是否單獨編譯每個文件('-c'標誌),然後將它們鏈接起來,還是使用GCC(compile + link)的單個命令執行?它看起來你的機器餓死了,你正在建造一些大的東西。 – egur

回答

1

您可能想要獲得特定編譯器正在使用的確切優化選項的列表。它們可以從編譯器到編譯器以及從目標到目標。

使用-Q--help=optimizers可以幫助您在這裏。例如,假設您使用以下命令編譯(和它產生斷碼):

gcc -march=armv7-a -mfloat-abi=softfp -mthumb -std=c++11 -FPIC -DNDEBUG -I. -g -c myfile.cpp 

如果此命令將創建工作代碼:

gcc -march=armv7-a -mfloat-abi=softfp -mthumb -std=c++11 -FPIC -DNDEBUG -O -I. -g -c myfile.cpp 

您可以通過將獲得不同的選項在-Q位於命令的開頭,--help=optimizers位於結尾。對於破命令:

gcc -Q -march=armv7-a -mfloat-abi=softfp -mthumb -std=c++11 -FPIC -DNDEBUG -I. -g -c myfile.cpp --help=optimizers > broken-opts 

和工作之一:

gcc -Q -march=armv7-a -mfloat-abi=softfp -mthumb -std=c++11 -FPIC -DNDEBUG -O -I. -g -c myfile.cpp --help=optimizers > working-opts 

尋找那些在broken-opts文件標記爲「[enabled]」,而是選擇「[disabled]」的working-opts文件:

diff broken-opts working-opts | grep '<' 

然後,您可以a)使用-O進行編譯並一次性禁用選項(即-fno-option-name選項-foption-name),直到找到合適的禁用選項,或者b)無需任何優化標記即可編譯並一次添加選項,直到找到「已損壞」選項。

我用帶引號的「破」選項 - 因爲在情況下,我曾經處理了,它實際上已經與MY代碼中的問題,而不是與編譯器或優化本身就是一個問題。然而,這個過程幫了我很多時間來弄清楚我的代碼中的問題在哪裏(例如,如果「斷開」選項與堆棧有關,或者與虛擬功能有關,則可以縮小您的範圍搜索有問題的代碼)。

相關問題