この記事は 第2のドワンゴ Advent Calendar 2016 - Qiita の 7 日目 (空いていたので飛び込んだのは 10 日目ですが) です。
プリプロセッサやテンプレートを駆使した C++ ヘッダを g++ でコンパイルする時でたまに発生する string table overflow さん...。
-g がデバッグシンボルを残してるせいなのか、-g を取り除けば大丈夫らしいのだが、CMake のコンパイルフラグから -g を取り除くのにちょいと苦労した。
最初に CMakeLists.txt 内で
set(CMAKE_CXX_FLAGS "")
とか
set(ENV{CXXFLAGS} "")
で上書きしてみたものの全然消えてくれない。
cygport から呼び出していたので cmake.cygclass を見てみたら、そもそもコマンドラインオプションに直接渡してた。
cmake -Wno-dev \ ${cmdir} \ -DCMAKE_BINARY_DIR=. \ -DCMAKE_BUILD_TYPE=${buildtype} \ -DCMAKE_C_COMPILER=$(which ${CC}${exeext}) \ -DCMAKE_C_FLAGS="${CFLAGS} ${CPPFLAGS}" \ -DCMAKE_CXX_COMPILER=$(which ${CXX}${exeext}) \ -DCMAKE_CXX_FLAGS="${CXXFLAGS} ${CPPFLAGS}" \ -DCMAKE_Fortran_COMPILER=$(which ${FC}${exeext}) \ -DCMAKE_Fortran_FLAGS="${FCFLAGS} ${CPPFLAGS}" \ -DCMAKE_AR=$(which ${AR}${exeext}) \ -DCMAKE_RANLIB=$(which ${RANLIB}${exeext}) \ -DCMAKE_EXE_LINKER_FLAGS="${LDFLAGS}" \ -DCMAKE_MODULE_LINKER_FLAGS="${LDFLAGS}" \ -DCMAKE_SHARED_LINKER_FLAGS="${LDFLAGS}" \ -DCMAKE_INSTALL_PREFIX=$(__host_prefix) \ -DCMAKE_LEGACY_CYGWIN_WIN32=0 \ ${crossargs} \ "${@}" \ ${CYGCMAKE_ARGS} \ || error "cmake failed"cygport/cmake.cygclass at master · cygwinports/cygport · GitHub
なので cmake 呼び出し前に cygport の設定ファイルの方で
CXXFLAGS=""
のように無効化してみたがまだ消えない。
さらに cmake.cygclass をよく見ると
if defined _CYGPORT_RESTRICT_debuginfo_ then buildtype=Release else buildtype=RelWithDebInfo ficygport/cmake.cygclass at master · cygwinports/cygport · GitHub
とあって、CMake のデフォルト設定を見ると
$ cmake --system-information | grep CMAKE_CXX_FLAGS | grep -e '==' CMAKE_CXX_FLAGS == "" CMAKE_CXX_FLAGS_DEBUG == "-g" CMAKE_CXX_FLAGS_MINSIZEREL == "-Os -DNDEBUG" CMAKE_CXX_FLAGS_RELEASE == "-O3 -DNDEBUG" CMAKE_CXX_FLAGS_RELWITHDEBINFO == "-O2 -g -DNDEBUG"
となっているので Release になるように
_CYGPORT_RESTRICT_debuginfo_=1 # cygport 内では RESTRICT="debuginfo" で同等の効果がある
することでようやく -g が消えた。
CMake を使う時は (CMake に限ったことではないですが) オプションと環境変数をきちんと確認しましょう。