2024年07月22日(月) [長年日記]
■ [windows][c++] VS2022がgtest.hを見つけられなかった
Visual Studio 2019用のC++プロジェクトをVisual Studio 2022用に更新したら、GoogleTestのヘッダを見つけられなくなってしまった。
error C1083: include ファイルを開けません。'gtest/gtest.h':No such file or directory
というエラーになる。
検索すると次のissueが見つかった。
- Issue with GoogleTest project when upgrading to VS2022 (Developer Community)
GoogleTestのNuGetパッケージが古いと発生するという回答が付いており、確かに古かったので更新(1.8.1.4 → 1.8.1.7)したら解決した。
NuGetが関係するというのはなかなか気づかないかなあ。
2024年06月13日(木) [長年日記]
■ [windows][c++] 不要な.libと.expファイルを作らないようにする
Visual Studio 2022にて、C++のアプリケーションを作るとexeファイルと一緒にlibファイルとexpファイルが作られることがある。exeファイルに対してlibやexpは不要と思われるので作りたくない。
現状でリンカーのリファレンスには書かれていないが、/NOIMPLIB と /NOEXP というオプションが使えるようで、Visual Studioからリンカーのコマンドラインの追加のオプションとしてこれらを指定したら作られなくなった。
2024年06月06日(木) [長年日記]
■ [python] Pythonの構成情報を取得する
sysconfigモジュールを使うと、Pythonのインストールパスなどを得ることができる。
例えば、Python.h が置かれているパスは次のようにして得られる。
> python Python 3.12.3 (tags/v3.12.3:f6650f9, Apr 9 2024, 14:05:25) [MSC v.1938 64 bit (AMD64)] on win32 Type "help", "copyright", "credits" or "license" for more information. >>> import sysconfig >>> print(sysconfig.get_path("include")) C:\Program Files\WindowsApps\PythonSoftwareFoundation.Python.3.12_3.12.1008.0_x64__qbz5n2kfra8p0\Include >>>
また、
python -m sysconfig
を実行するとsysconfigで得られる情報を一覧表示できる。欲しい項目だけを表示するオプションがあるといいのだけれど、そういうのは無いみたい。
2024年05月02日(木) [長年日記]
■ [c++][c][dev] C++用Makefileのサンプル (4)
Makefileを書く機会があった。Makefileは楽しい。
以前に書いたMakefileのサンプルを書き直したくなったので書く。
ソースファイルとMakefileの構成を以前と少し変えて次の通りとする。
. ├── Makefile └── src ├── app1 │ ├── aaa │ │ ├── a.cpp │ │ ├── a.h │ │ └── ccc │ │ ├── c.cpp │ │ └── c.h │ ├── bbb │ │ ├── b.cpp │ │ └── b.h │ └── main.cpp └── app2 ├── aaa │ ├── a.cpp │ ├── a.h │ └── ccc │ ├── c.cpp │ └── c.h ├── bbb │ ├── b.cpp │ └── b.h └── main.cpp
1つのMakefileでapp1とapp2という2つの実行ファイルを作れるようにしたい。
作成したMakefileは次の通り。
# GNU make用です SHELL := /bin/bash Dirs = $(shell find $(1) -type d -not -path '*/.*') Files = $(wildcard $(addsuffix /*$(strip $(2)), $(1))) SrcFiles = $(call Files, $(call Dirs, $(1)), .cpp) build_dir := build CPPFLAGS := CXXFLAGS := -Wall -O3 -ggdb3 LDFLAGS := LDLIBS := # app1 app1_bin := $(build_dir)/app1 app1_src_dir := src/app1 app1_src_files := $(call SrcFiles, $(app1_src_dir)) app1_obj_files := $(app1_src_files:%.cpp=$(build_dir)/%.o) dep_files += $(app1_obj_files:%.o=%.d) app1: CPPFLAGS += -I$(app1_src_dir) # app2 app2_bin := $(build_dir)/app2 app2_src_dir := src/app2 app2_src_files := $(call SrcFiles, $(app2_src_dir)) app2_obj_files := $(app2_src_files:%.cpp=$(build_dir)/%.o) dep_files += $(app2_obj_files:%.o=%.d) app2: CPPFLAGS += -I$(app2_src_dir) # app1とapp2に共通のソースファイルがある場合は、dep_filesから重複を除去しておきたい。 # 次の処理を生かせばできる。 #dep_files := $(sort $(dep_files)) build_subdirs := $(sort $(dir $(dep_files))) .PHONY: all all: app1 app2 .PHONY: app1 app1: $(app1_bin) .PHONY: app2 app2: $(app2_bin) .PHONY: clean clean: $(RM) -r $(build_dir) $(app1_bin): $(app1_obj_files) $(CXX) $^ -o $@ $(LDFLAGS) $(LDLIBS) $(app2_bin): $(app2_obj_files) $(CXX) $^ -o $@ $(LDFLAGS) $(LDLIBS) $(build_dir)/%.o: %.cpp | $(build_subdirs) $(CXX) $< -c -o $@ $(CPPFLAGS) $(CXXFLAGS) -MMD -MP $(build_subdirs): mkdir -p $@ -include $(dep_files)
- ソースファイル一覧は、SrcFilesという関数を作ってそれで得られるようにした。
- 「app1: CPPFLAGS += -I$(app1_src_dir)」の行はtarget-specific variablesを使用していて、同一名の変数へターゲット毎に別々の値を設定している。
- 「\$(build_dir)/%.o: %.cpp | $(build_subdirs)」の行はorder-only prerequisitesを使用していて、これにより \$(build_subdirs) 内の各ディレクトリは .o ファイルより前に作られるが \$(build_subdirs) 内のディレクトリのタイムスタンプが新しくても .o ファイルは作り直されないようになる。
- GCCの -MMD -MP といったオプションについては以前にメモした。
実行結果は次の通り。
$ make --version GNU Make 4.3 Built for x86_64-redhat-linux-gnu Copyright (C) 1988-2020 Free Software Foundation, Inc. License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html> This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law. $ make -j mkdir -p build/src/app1/ mkdir -p build/src/app1/aaa/ mkdir -p build/src/app1/aaa/ccc/ mkdir -p build/src/app1/bbb/ mkdir -p build/src/app2/ mkdir -p build/src/app2/aaa/ mkdir -p build/src/app2/aaa/ccc/ mkdir -p build/src/app2/bbb/ g++ src/app1/main.cpp -c -o build/src/app1/main.o -Isrc/app1 -Wall -O3 -ggdb3 -MMD -MP g++ src/app1/aaa/a.cpp -c -o build/src/app1/aaa/a.o -Isrc/app1 -Wall -O3 -ggdb3 -MMD -MP g++ src/app1/aaa/ccc/c.cpp -c -o build/src/app1/aaa/ccc/c.o -Isrc/app1 -Wall -O3 -ggdb3 -MMD -MP g++ src/app1/bbb/b.cpp -c -o build/src/app1/bbb/b.o -Isrc/app1 -Wall -O3 -ggdb3 -MMD -MP g++ src/app2/main.cpp -c -o build/src/app2/main.o -Isrc/app2 -Wall -O3 -ggdb3 -MMD -MP g++ src/app2/bbb/b.cpp -c -o build/src/app2/bbb/b.o -Isrc/app2 -Wall -O3 -ggdb3 -MMD -MP g++ src/app2/aaa/a.cpp -c -o build/src/app2/aaa/a.o -Isrc/app2 -Wall -O3 -ggdb3 -MMD -MP g++ src/app2/aaa/ccc/c.cpp -c -o build/src/app2/aaa/ccc/c.o -Isrc/app2 -Wall -O3 -ggdb3 -MMD -MP g++ build/src/app1/main.o build/src/app1/aaa/a.o build/src/app1/aaa/ccc/c.o build/src/app1/bbb/b.o -o build/app1 g++ build/src/app2/main.o build/src/app2/bbb/b.o build/src/app2/aaa/a.o build/src/app2/aaa/ccc/c.o -o build/app2 $ tree . . ├── Makefile ├── build │ ├── app1 │ ├── app2 │ └── src │ ├── app1 │ │ ├── aaa │ │ │ ├── a.d │ │ │ ├── a.o │ │ │ └── ccc │ │ │ ├── c.d │ │ │ └── c.o │ │ ├── bbb │ │ │ ├── b.d │ │ │ └── b.o │ │ ├── main.d │ │ └── main.o │ └── app2 │ ├── aaa │ │ ├── a.d │ │ ├── a.o │ │ └── ccc │ │ ├── c.d │ │ └── c.o │ ├── bbb │ │ ├── b.d │ │ └── b.o │ ├── main.d │ └── main.o └── src (以下略)