web-dev-qa-db-ja.com

オブジェクトファイルのセクションが多すぎます

一般にboost :: serializationとテンプレートを多用しています。すべてが順調に進んでいるようです。

例外として、Windowsビルドで問題が発生しました。オブジェクトファイルが大きすぎると問題が発生するようです。 MinGW/Msysをg ++ 4.7.0で使用しています。

c:/mingw/bin/../lib/gcc/mingw32/4.7.0/../../../../mingw32/bin/as.exe: CMakeFiles/source.dir/sourcecode.cpp.obj: too many sections (33396)
C:\Users\username\AppData\Local\Temp\ccnAocvD.s: Assembler messages:
C:\Users\username\AppData\Local\Temp\ccnAocvD.s: Fatal error: can't write CMakeFiles/source.dir/sourcecode.cpp.obj: File too big

マスターグーグルはこのアーカイブされたメッセージを明らかにしました http://sourceforge.net/mailarchive/forum.php?thread_name=CA%2Bsc5mkLvj%3DW9w2%3DsY%3Dc_N%3DEwnsQuPDEX%3DiBcbsbxS3CuE_5Bg%40mail.gmail.com&forum_name

その中で、それは別の人がほぼ同じ障害を打ったことを示しています。これは、Visual Studioの/bigobjオプションのオプションを指していましたが、これは必要なことを行うように見えます。ただし、Visual Studioに移行することはできません。

1つの提案は、アセンブラオプションに--hash-sizeを追加することでした。これは助けにはなりませんでした。

私が間違っていない場合、問題はオブジェクトファイルのエントリが2 ^ 16に制限されているという事実にあります。実際、エラーメッセージによると、これは署名付きの2 ^ 16エントリだと思いますが、それはピーナッツです。 Visual Studioの/bigobjオプションは、これを2 ^ 32に変更します。メーリングリストの結果は、gccに相当するオプションを知りませんでした。さらなるグーグルの結果はこれに関連しているようには見えません。

この時点で、この制限を回避するためにコード(リフ)をリファクタリングする必要があります。しかし、私は依然として、テンプレートが多すぎると問題が何度も発生する可能性があることを懸念しています(すでに3つのソースファイルで発生しています)。

したがって、私の質問はこうです。 Microsoftの/bigobjオプションに相当するgccはありますか?私がまだ見つけていない3つ目のオプションはありますか?

35
inetknght

解決策は、GCCのバージョンがそのオプションをサポートしている場合、オプション-Wa,-mbig-objを追加することです。おそらく、リンカステップではなく、コンパイルステップ中にのみ必要です。

コンパイラがそのオプションをサポートしていない場合は、mingw-w64および MSYS2 の使用を検討する必要があります。

46
David Grayson

エラー"%B: too many sections (%d)"は、bfd/coffcode.hにある関数coff_compute_section_file_positions()に起因します。 (COFF形式の)出力.objファイルに32766を超えるセクションが含まれている場合に生成されます。このエラーを回避する方法はありません。少なくとも、WindowsのPE/COFFオブジェクト形式を使用する場合はそうです。 COFFファイルは、ファイルヘッダーの "NumberOfSections"に2バイトのみを使用します。

as(GNUアセンブラー)が65536-minus-1ではなく32768-minus-2でセクションの数を制限する理由がわかりません(セクション0は予約されています) );ただし、どちらの方法でも、テンプレートおよびを多用している場合、コンパイラはCOMDATセクションを介してテンプレートを実装します。

すでにお気づきのように、/bigobjをMicrosoftのコンパイラに渡すと、最大2つの変更されたCOFF形式が出力されます。31 「誰にとっても十分なはずです」セクション。ただし、変更された形式は正式には文書化されておらず、サブジェクトに関する非公式のドキュメント(ブログの投稿またはwhat-have-you)は表示されないため、MSVCのコピーを持つ誰かが/bigobjの仕様を書き込めるまでは、 GNUツールにアクセスする可能性はほとんどありません。

私見、Windowsビルドを作成しようとしている場合は、弾丸をかじってMSVCを使用する必要があります。マイクロソフト以外の誰も、PE/COFF形式との闘いに時間を費やすことに特に動機づけられていません。

10
Quuxplusone

MinGW-w64でPocoライブラリをコンパイルしたときに同じ問題に直面しましたが、1つの実装ファイルに対してデバッグオブジェクトが巨大であることがわかりました。

あなたは 前述 あなたはcppファイルを分割することができ、それは機能しますが、誰かのソースコードに直面したとき、何かを壊すことなくそれを行うことはできません。

解決策として、コンパイラの最適化をオンにすることができます。-O1から-O3まで、各ステップで小さなオブジェクトファイルを構築し、問題を解決する可能性があります。はい、デバッグビルドでは望ましくない場合があります -Ogを試すことができます

4
user1464445

私はこの問題でいくつかの更新を見つけました、それはx64ウィンドウの新しいbinutilsで修正されているようです、 https://sourceware.org/ml/binutils/2014-03/msg00114.html と-を参照してください http://sourceforge.net/p/mingw-w64/bugs/341/ 。ただし、この修正は必要な32ビットバージョンには適用されないため、テストしませんでした。

4
Vladimir Still