""
[C++] Modulesのコンパイル(MSVC ver)とBMIについて
この記事は C++ Advent Calendar 2021 1日目(初日!)の記事です。
少し前からC++に Modules がやってきました
C++20 対応のメジャーどころのコンパイラ(MSVC/gcc/Clang など)で使うことができます
個人的にはビックウェーブが来たーーーと思ってまして、つねづねポチポチと Modules について調べていました
それを少しまとめたいと思います
モジュールの説明
昔ながらのプリコンパイルヘッダの概念を、今風にした感じでしょうか
ヘッダファイルをインクルードしていたものを Modules に置き換えることが出来ます
ヘッダファイルだと、
インクルードの順番に気を付けたり
コンパイル時間が長くなったり
インクルードガード書いたりと
ゆーてローテク文字列だったのですが、
それがバイナリとして公式に提供されました
Modulesを記載するファイル
各コンパイラによって(推奨)拡張子が異なります
MSVC (cl.exe)
- Foo.ixx
- Foo.ixx
Clang
- Foo.cppm
GCC
- Foo.cc
- Foo.cp
- Foo.cxx
- Foo.cpp
- Foo.c++
- Foo.C
(参考)
- MSVC
Overview of modules in C++ - GCC
GCC and File Extensions - Development with GNU/Linux https://blog.feabhas.com/2021/08/c20-modules-with-gcc11/
以下、、MSVCで話を進めます
(コンパイラによって異なる所が多いので)
モジュールファイルについて
MSVC の場合、モジュールにしたいファイルは .ixx という拡張子を付けます
(Clangだと .cppm、GCCだと .cxx とかになります)
サンプルはこんな感じ
hello.ixx
|
|
利用する側はこんな感じで↓↓↓ import すれば使えます
(従来は #include "hello.h" とか書いていた場所です!)
|
|
サンプルだけ見ると、なんてことのないコードですね
メイン関数は #include してた箇所を inport に変更しただけです
モジュールをバイナリ化する
モジュールを記載する .ixx ファイルは、.ifc にプリコンパイルでバイナリ化されます
ややこしいのが、コンパイラによってこのあたりの呼び名が異なってて、こんな感じ
| MSVC | Clang | |
|---|---|---|
| モジュールファイル名 → | .ixx |
.cppm |
| モジュールファイルをプリコンパイルしたもの→ | .ifc |
.pcm |
ちなみに「モジュールファイルをプリコンパイルしたもの」を BMI と呼び、
Binary Module Interface の略になります
この BMI ファイルを各 cpp ファイルなどが import することになります
(参考)
- Practical Cpp Modules - CppCon 2019
https://github.com/CppCon/CppCon2019/blob/master/Presentations/practical_cpp_modules/practical_cpp_modules_boris_kolpackov_cppcon_2019.pdf
VC++でのコンパイル方法
単純のため、まずはコマンドラインでやってみます
利用したVC++バージョンはこちら

コマンドは2つ
|
|
1つ目のコマンドでモジュールをプリコンパイルし、
2つ目のコマンドで obj をリンク、そして main.exe の出力をします
<1. モジュールのプリコンパイル>
C:\my\dev\sample_module01>cl /c /std:c++20 hello.ixx
Microsoft (R) C/C++ Optimizing Compiler Version 19.30.30705 for x86
Copyright (C) Microsoft Corporation. All rights reserved.
hello.ixx
これで、hello.obj と MyHello.ifc が出来ました
(余談)cl.exe はモジュールのコンパイル時に同時に2つ(
.objと.ifc)のファイルを出力してくれて楽ですClang は別々のコマンドで出力するので、cl.exe とは少し作り方が異なっています
.pcm( VC++で言うところの.ifc) を出力した後、それを元に.o( VC++の.obj) を出力します
このあたりはまだ次回に投稿したいです
<2. 実行ファイル生成>
C:\my\dev\sample_module01>cl /std:c++20 /EHsc /reference MyHello=MyHello.ifc main.cpp hello.obj
Microsoft (R) C/C++ Optimizing Compiler Version 19.30.30705 for x86
Copyright (C) Microsoft Corporation. All rights reserved.
main.cpp
Microsoft (R) Incremental Linker Version 14.30.30705.0
Copyright (C) Microsoft Corporation. All rights reserved.
/out:main.exe
main.obj
hello.obj
main.exe が出来ました
実行してみます
C:\my\dev\sample_module01>main.exe
42
問題なし(^^♪
(備考)コンパイルオプションの注意点
VC++のコマンドラインオプションが
- モジュールを作ったとき
- モジュールを使うとき
これらの間で一致していないとき、ワーニングが出ました(C5050)
main.cpp(7): warning C5050: Possible incompatible environment while importing module ‘MyHello’: _CPPUNWIND is defined in current command line and not in module command line
そのため今回、hello.ixx 内では <iostream> は利用していないのですが、/EHsc オプションを付けています
(参考)
- Using C++ Modules in MSVC from the Command Line Part 1: Primary Module Interfaces - C++ Team Blog
https://devblogs.microsoft.com/cppblog/using-cpp-modules-in-msvc-from-the-command-line-part-1/
BMIってなによ?
プリコンパイルされた Binary Module Interface って何なのでしょうか?
この中身は一体?
さんざん調べましたが、大した情報が載ってないですね。。。
これ、BMIというのは Modules を扱うための概念のようです
これはコンパイルの過程のものなので、各コンパイラベンダーが作る箇所であり、明確に公開情報として詳細が提示されているわけではなさそうです
現時点では概念がちらほらと記載されているだけのようでした
実際に、プリコンパイルで作られた .ifc や .pcm の中身は
- プリプロセスで利用した情報とか
- ASTのダンプ
- Objみたいなもの
がひとまとめにされてるようです
という記述を見つけましたが、出展元が判らなくなったので、思い出したら追記します。。。
(2021/12/4追記)
CppCon2019の資料が参考になりました!
Practical Cpp Modules - CppCon 2019
https://github.com/CppCon/CppCon2019/blob/master/Presentations/practical_cpp_modules/practical_cpp_modulesboris_kolpackovcppcon_2019.pdf
もちろん、コンパイラによって、さらにバージョンによっても形式は様々なんでしょう
モジュールの配布ってどうやるの?
モジュールのバイナリを配布することはできないです
共有する場合はあくまでソースコードと共に配布になります
また、作られた BMI、つまり .ifc や .pcm ファイルは不変的なバイナリではないみたいです
ライブラリのように配布はできないのですね。。。
(余談)Modules の提案を推し進めている Gabriel Dos Reisさん は、Common Module Interface Format を作りたいみたいですが…
具体的に今の段階では、配布目的のものは出ていないようです
(参考)
- C++ Modules: What You Should Know
https://github.com/cppp-france/CPPP-19/blob/master/C%2B%2B_modules_what_you_should_know-Gabriel_Dos_Reis/C%2B%2B_modules_what_you_should_know-Gabriel_Dos_Reis.pdf
所感
まだ2021年12月の時点では、Modules 機能が完全に動作するコンパイラもないみたいですし
そもそも各コンパイラによって記載方法や推奨が異なるので、なんとも道半ばな印象はあります
Modules を利用するための手順やお作法も多く、また情報も限られているので、取り組みにくいですね
マイクロソフトの VC++チームブログ は、コンパイラベンダーとして結構 Moduleds の具体的な情報を出しているように感じました
(Clangももうちょっと頑張って。。。あとGCC。。。おまえはやる気あるのか。。。)
Modules に関して取り組まれている人たちの歴史はとても長く
かつ現在のヘッダファイルがベストだとは思えないので
個人的に一押ししたい機能だと改めて思いました
所感その2
C++ Advent Calendar!
ずいぶん昔に一度だけ参加したことがあったのですが、それからなーんにもしてませんでした
今回、意を決して投稿できて良かったです
かなりよく調べたつもりですけど、間違いなどあったら気軽に @hr_sao まで教えていただけると嬉しいです
C++楽しい~♪
[C++]Compiler Explorerの出力結果の表示方法
Compiler Explorer というオンラインコンパイルサービスがあります
- Compiler Explorer
https://godbolt.org/
書いたC++コードのアセンブリ出力結果をリナルタイムに表示してくれるサービスです

すごーーー👀
初めてこのサービスを見た時には感激しました〜
さておき、
わたし、これで実行結果を見る方法を知らなかったんですね…ハズカシー(*ノдノ)
「Output」を押すと出力結果ウィンドウは出てきますが
このリターン値だけじゃなくて、 std::cout の結果も欲しいんですけど…👀

ちょっと調べてみたらすぐに判明しました><。
Outputの設定項目に Execute the code のチェックボックスがあるので、それを選択すれば表示されます

出力はこんな感じですね〜

便利です〜
[C++] 実行環境の差異によるintワーニングが出ない書き方
C++のワーニングを放置していたのですが、そっと @srz_zumix さんが教えてくれてました
忘れないうちに”φ(・ェ・o)~メモメモ
x86環境とx64環境が混在してる場合にエラーが出やすい
こんなやつとか出ます…
|
|
これは x86環境だと warning は出ないのですが x64 環境想定でコンパイルすると、ワーニングが出ます
(Clangの例)
warning: Implicit conversion loses integer precision: ‘std::__1::vector>::size_type’ (aka ‘unsigned long’) to ‘u_int32_t’ (aka ‘unsigned int’) [-Wshorten-64-to-32]
( ̄□ ̄;
ええ、ええ、判っていますとも…
int 型が処理系によって異なるのは…
そこで、やっつけで修正するならこれ
|
|
なのですが、もっとスマートは方法があります
|
|
エレガントになりました…!素晴らしい(^^♪
警告のコンパイラー対応表がある
[C++] 警告のコンパイラー対応表を作り始めました - ブログズミ
https://srz-zumix.blogspot.com/2020/09/c.html
@srz_zumix さんが最近始められたプロジェクトらしいです
ワーニング対応表欲しいな…と思っていたところなので、結構良いかもしれない…
そして今日もC++修練は続く…
[c++] 2次元配列的な書き方
自分メモ
2次元配列
C++11 以前では、2次元配列はこんな感じで書いていました
|
|
これでも悪くは無いのですが、生配列を扱うと範囲外アクセスに気が付かない可能性が出てきます
そこで C++11 から境界チェックが出来る配列の std::array が登場しました
これを使えば、C-styleの配列のノリで扱うことが可能です
- std::array - cpprefjp
https://cpprefjp.github.io/reference/array/array.html
さらに2次元配列にしたければ std::array を std::vector に入れることで実現可能です
|
|
悪くなさそう
動作確認
|
|
結果
xy_raw[0][1]: 10
xy_raw[1][2]: 40
xy_array[2][0]: 40
コンパイル時に教えてくれるので助かります
参考
コンパイル結果:
https://repl.it/repls/StudiousImaginativeParallelcomputingC++ - Vector of Float Arrays - stackoverflow https://stackoverflow.com/questions/33711878/c-vector-of-float-arrays
[C++] std::optionalの使い方を紹介しました
少し前ですが、std::optional について nakameguro_feature.cpp vol.13 で発表したので、その資料を置いときます
- nakameguro_feature.cpp vol.13
https://ebisu-effective-modern-cpp.connpass.com/event/111469/
私的感想としては、optional を使うと
値取得に失敗しても、例外を書くことなく if で処理出来る のが、なんだか良いなぁと思った次第でした
あと、optional の無効状態をどう表すか?
reset() / std::nullopt / {} のどれよ?
という話は、参加者の人たちの意見も GitHub の検索結果と同じで
reset() に軍配があがっていました(‘ω’)
こういう意見交換の場は、本当に恵まれてるなぁ~しみじみ
次回は 3 / 28 (木)開催で、vol.18 です!
- nakameguro_feature.cpp vol.18
https://ebisu-effective-modern-cpp.connpass.com/event/125272/
お時間ある方は、ぜひお立ち寄りください~!
[Android] 謎のエラー「Unable to start debugging.」が出たときの対応
Androidデバッグで実行時エラー
環境
- Windows10 x64
- Visual Studio 2017
- Project type: Native-Activity Application (Android)
ある時…Visual Studio で作っている Android プロジェクトが、実行時エラーになりました

Unable to start debugging. Check your debugger settings by opening project properties and navigating to ‘Configuration Properties–> Debugging’
デバック出来ないからね!プロジェクトの設定見てね!的な意味みたいですが
デバッグモードで動かしてるし…
一体どこの何の事を言ってるのか判らない…><。
リリースモードならOKなのかしら?と思っても、同様のエラー”(-“”-)”
解決案(わたしはこれでは解決しませんでしたが)
検索しても、実のある回答は特に出てこず…
唯一、解決っぽいのが、NVIDIAさんのフォーラムに載ってました
- CodeWorks for Android 1R4: Unable to start debugging - NVIDIA DEVELOPER
https://devtalk.nvidia.com/default/topic/957019/codeworks-for-android-1r4-unable-to-start-debugging/
元ネタリンクはMicrosoftさんのGitHub情報みたいです
- MEF - GitHub Microsoft/VSProjectSystem
https://github.com/Microsoft/VSProjectSystem/blob/master/doc/overview/mef.md#mef-inside-visual-studio
簡単に言うと、VSの Developer Command Prompt を使って、キャッシュクリアしてみたら?というもの
やってみました
Developer Command Prompt を検索して立ち上げる

以下のコマンドを打つ
Devenv /UpdateConfiguration
Devenv /ClearCache

もっともらしい対策なんですけど、わたしの実行時エラーは解決しませんでした
何がダメなのだろ…((+_+))
わたしが解決した方法
で、実際の解決策ですが…
すみません、散々あーだこーだ書いてますが
スタートアッププロジェクトの設定もれ でした…( ;∀;)
いやはや、お恥ずかしい…

Androidプロジェクトが参照する、別のプロジェクト達が
同じソリューションファイルの中に複数存在しています
なのに、Androidプロジェクトを起動プロジェクトに設定しておらず…
ポカミスとはまさにこの事!( ;∀;)
なぜこれに気が付かなかったのか…相当焦ってて、周りが見えてなかったみたいです
二度と同じ過ちを繰り返さないように…><。
あと、同様のエラーで困ってる人の何かしらの参考になればと思います><。
[C++] VisualStusio2015でClangを使う設定
今日は Clang with Microsoft CodeGen の設定などについて、メモしておきます
先人たちが既に色々と試している内容と対して変わりませんが、そもそも日本語の情報も少ないので、何かの足しになればと思います
“Clang with Microsoft CodeGen” is here!
最近はすっかり、クロスプラットフォームやオープンソースに力を入れているマイクロソフト社のツールセットの中に、Clang対応ってのがあります
2015年の年末にですが、Clang が正式に Visual Studio 2015 Update1 で利用できるよ~
とVC++チームブログで発表されていました
Clang with Microsoft CodeGen in VS 2015 Update 1 - Visual C++ Team Blog
https://blogs.msdn.microsoft.com/vcblog/2015/12/04/clang-with-microsoft-codegen-in-vs-2015-update-1/Clang with Microsoft CodeGen (March 2016) released- Visual C++ Team Blog
https://blogs.msdn.microsoft.com/vcblog/2016/03/31/clang-with-microsoft-codegen-march-2016-released/
良いですねー(^^)
現在のVS2015には Clang with Microsoft CodeGen というツールセットが提供されており、目玉はなんといっても、Clang のデバックを Visual Studioのエディターで確認できるところでしょうか!
他にも、Clang でコンパイルしたobjと VC でコンパイルしたobjがリンクできるところもすごいです
既存資産をフル活用出来そうですね
(2016/5/15現在、Visual Studio 2015 Update2 が最新です)
https://www.visualstudio.com/ja-jp/news/vs2015-update2-vs.aspx
LLVM側にも記事が上がっています
- Getting Started with the LLVM System using Microsoft Visual Studio - LLVM本家
http://llvm.org/docs/GettingStartedVS.html
日本でも既に先人が試されているので、読んでみると良いと思います
Clang/C2をコマンドプロンプトで使ってみる - イグトランスの頭の中(のかけら)
http://dev.activebasic.com/egtra/2015/12/09/850/Clang with Microsoft CodeGenがでたので試す - C++初心者Advent Calendar 2015 9日目
http://qiita.com/yumetodo/items/bd41f31f39dd590e8c80
ちなみに、この Clang with Microsoft CodeGen は VC++チームブログにも “a.k.a. Clang/C2” と記載されており、別名を Clang/C2 というようです
また、今回対応している Clang 側のバージョンは 3.7 です
clang.exe の場所
Clang
|
|
ちなみにVC++
|
|
どちらでも、コマンドプロンプトでコンパイル可能です
VSでのコンパイラの切り替え設定
Visual Stidon 2015 上で “Alt + F7” を押すか
プロジェクト > [プロジェクト名]のプロパティ
で設定UIを表示させます
構成プロパティ > 全般 > プラットフォームツールセット
この項目を “Clang 3.7 with Microsoft CodeGen (v140_clang_3_7)” に変更するだけです

結構簡単\(^o^)/
ソリューション作成は何でもOK
上記の様に、コンパイラが簡単に切り替えられるので、空のプロジェクトでも、Win32コンソールアプリケーションでもOKです
一応、Clangっぽいプロジェクトはあるんですけど、いきなり dll というのもなんだか敷居が高いので、

exe を作りたいだけなら、Win32コンソールアプリケーションで良いと思います
[余談]文字コードはUTF8の方が良い(様な気がする)
最初に書いておくと、Sift-JIS でも Clang/C2 でコンパイルは通ります
…なのですが、一応、なんとなく
個々の環境によって異なるのかもしれませんが
わたしがVS2015で作成した cpp ファイルは、デフォルトで Sift-JIS になります
既に、VC++チームブログ にはこんな感じで↓↓↓
If source files in the project you are trying to convert are UTF-16 encoded, you will need to resave them as UTF-8 when Clang gives you an error about UTF-16 encoded source with BOM.
UTF-16はだめらしいです
Sift-JIS は無関係かもしれませんが、一応…
サンプルコード
cpprefjp を参照して、サンプルコードを書いてみました
VC2015 Update2 では未対応だけど、Clang 3.7 は対応しているというコードです
|
|
Visual Studio 2015 (v140) でコンパイルすると、エラー

VS2015 ではまだ、constexpr関数内の変数宣言がエラーになる様です
Clang 3.7 with Microsoft CodeGen (v140_clang_3_7) でのコンパイル

Clang はOKです
いい感じに動作しました!
VC++も Clang も、VS上でデバック出来るのは良いですね
噂には聞いていましたが、自分で動作させてみると、感激するもんがあります
今はまだプレビューらしいので、早く安定化して欲しいですね~
[勉強会] ebisu_effective_modern.cpp vol.3やりますよ
ebisu_effective_modern.cppって?
東京の恵比寿でC++について、みんなの意見を聞きながら本を読み進める勉強会を開いています
昔、大阪でC++の読書会を開催していたのですが、それが結構役に立って面白かったので、東京でも開催してみよう!と思い、始めてみました
ebisu_effective_modern.cpp vol.3
2016/3/31 (木) 20:00-21:30 東京恵比寿
http://ebisu-effective-modern-cpp.connpass.com/event/29324/ちなみに大阪はこちらで絶賛開催中ですよ~!
大阪C++読書会
http://cpp-osaka.connpass.com/
ネタが無いと勉強や会話もしずらいので、
「Effective Modern C ーC11/14プログラムを進化させる42項目」 を元に進めています
今回は、5章 右辺値参照、ムーブセマンティックス、完全転送 について…
前回の vol.2 では、基本的なムーブの動きを簡単に抑えた程度になったので、あまり深いところまでは進めませんでした
書籍の内容にぐいぐい追いつけるように頑張りますよ~
興味ある方はどうぞ、お気軽にお越しください(^^)/
[C++11] 参考リンク情報
C++11について調べているときに参考になった情報源のメモ
- C++11/14/17 Features In VS 2015 Preview - Visual C++ Team Blog
http://blogs.msdn.com/b/vcblog/archive/2014/11/17/c-11-14-17-features-in-vs-2015-preview.aspx
VS2013とVS2015 previewで利用できる機能一覧が乗っている
C++11 - the new ISO C++ standard (和訳版)
http:// www32.ocn.ne.jp/~ons/text/CPP0xFAQ.html.ja(現在リンク切れ)
ビャーネさんのC++11に対するコメント
原文はこちら→http://www.stroustrup.com/C++11FAQ.htmlC++11 の機能 (Modern C++) のサポート
http://msdn.microsoft.com/ja-jp/library/hh567368.aspx
VC++でのC++11の機能一覧
[C++/CX] MVP Community Camp 2014大阪で「VC++まわりの非同期処理」セッションしました
MVP Community Camp 2014大阪にて、VC++系のセッションをさせて頂きました
MVP Community Camp 2014大阪会場
http://atnd.org/event/E0024087 (リンク先は削除されている模様です)
当日利用した資料はこちら!
pptx版はこちら ←セッション時の私的メモが欄外に載っています
PDF版はこちら
序盤はわたしの追体験発表みたいになってしまいました
同じような疑問を持っている人や、その人なりの解釈の手助けになる様であればと思って記載しています
後半部分は、VC++での非同期処理の触りだけになっていますが
非同期での例外や中断など、C++/CXのWIndowsストアアプリでは興味深い仕組みが色々あるので
この続きになる情報も、もっと自分なりに勉強して発信していきたいなー