見出し画像

[C++]VisualStudio2017でビルド通ってVisualStudio2019でビルド通らない

コード書いとる?

思いがけずコンパイラの仕様変更でビルドが通らなくなる問題に遭遇したのでメモ書き。ここはnote。

何が問題か

このC++コード、VisualStudio2017だとビルド通るんだぜ...

void f(int a) {}
void f(float a) {}


int main()
{
 long v = 0;
 f(v);             // clangだとintは32bit、longは64bitなので、オーバーロード解決が曖昧になってエラー
                   // だがVisualStudio2017だとintもlongも32bit幅なのでビルドが通る...
}

これまでなんとなくint型が32bitならlong型は64bitと思ってたんですが、実はそうではなかった...

それはまあいいんですが、VisualStudio2017でビルド通って、VisualStudio2019でビルド通らなくなるのはどうなんだw

Win32の構造体POINTはlong型の値を内包してますが、これをint型と同じつもりで使ってると、軒並み関数オーバーロードの解決に失敗しそうな予感です。

clangやgccなど、他のコンパイラと挙動を合わせようと歩み寄った結果なのだと信じます...。VisualStudio2019ではビット幅が同じでもint型とlong型は違う型...

最後に

いろいろ調べてみましたが、データ型モデルというのがあって、Windowsの64bit環境がLLP64、Linuxをはじめ他の64bitOSがLP64を採用しているのが原因なのね...。LLP64が「long long型とポインタが64bit」、LP64が「long型とポインタが64bit」という意味なんだそうな。

これは初耳でした!!(そういえば過去に、実行環境で各種型のサイズをprintfして確認してたっけ...)

long型は実行環境によってビット幅が違ってくるので、代わりにint32_tとかint64_tとか使うのが良さそうです。

ではまた次回!

この記事が気に入ったらサポートをしてみませんか?