MS Visual Studio - ccache/ccache GitHub Wiki
ccache supports caching the output of the Microsoft Visual Studio Compiler (MSVC) since version 4.6.
Install ccache from the download page. Alternatively, install via Chocolatey, but bear in mind that ccache then gets run via a shim executable which slows down execution somewhat.
Make a copy of (or link to) ccache.exe
called cl.exe
.
Example:
copy ccache.exe C:\some\folder\cl.exe
Then configure your IDE or build system to use C:\some\folder\cl.exe
as the compiler.
If you're using Chocolatey you can copy the executable from C:\ProgramData\chocolatey\lib\ccache\tools\ccache-*
, e.g.:
copy C:\ProgramData\chocolatey\lib\ccache\tools\ccache-4.7.4-windows-x86_64\ccache.exe C:\some\folder\cl.exe
Important: If you're using ccache installed via Chocolatey, don't copy C:\ProgramData\chocolatey\bin\ccache.exe
since that's a shim executable that can't be used with another name.
Create a wrapper file
@echo off
%~dp0\ccache.exe cl.exe %*
Then set CC
and CXX
to the wrapper script:
set CC=full_path_of_ccache_cl_wrapper.bat
set CXX=full_path_of_ccache_cl_wrapper.bat
: You may need set VCPKG_KEEP_ENV_VARS, see below
do your work here
Reference: https://learn.microsoft.com/en-us/vcpkg/users/config-environment#vcpkg_keep_env_vars
Install ccache according to Alternative 1: Masquerade as the compiler above. Assuming the path is C:\ProgramData\chocolatey\bin
, either:
-
Use
msbuild /p:CLToolPath=C:\ProgramData\chocolatey\bin /p:UseMultiToolTask=true ...
, or -
Create a file called
Directory.Build.props
adjacent to or above your project file with the following contents:<Project> <PropertyGroup> <CLToolPath>C:\ProgramData\chocolatey\bin\</CLToolPath> </PropertyGroup> <!-- The following will set the needed properties described in Tips above. --> <!-- Creation of a precompiled header will have to be disabled separately. --> <PropertyGroup> <UseMultiToolTask>true</UseMultiToolTask> </PropertyGroup> <ItemDefinitionGroup> <ClCompile> <DebugInformationFormat>OldStyle</DebugInformationFormat> <ForcedIncludeFiles /> <ObjectFileName>$(IntDir)%(FileName).obj</ObjectFileName> <PrecompiledHeader>NotUsing</PrecompiledHeader> </ClCompile> </ItemDefinitionGroup> </Project>
Using Directory.Build.props
is preferable since it's possible to specify all recommended settings there.
Important:
- Ccache versions older than 4.7 require the masquerading ccache executable (renamed to
cl.exe
) to be outside of the system PATH. Note that Chocolatey provides an option to insertC:\ProgramData\chocolatey\bin
(the path used in examples) into the system PATH during installation. In such cases you may use a direct ccache path, for exampleC:\ProgramData\chocolatey\lib\ccache\tools\ccache-4.6.3-windows-x86_64
or upgrade to version 4.7 or later. -
/p:CLToolExe
cannot be used. Always use/p:CLToolPath
alone when invoking msbuild.
Other tips:
- Do not use
/Zi
debugging (/Z7
is okay).- If you use a project file, do not use
DebugInformationFormat=ProgramDatabase
(OldStyle
is okay).
- If you use a project file, do not use
- Do not use
/Yc
to write pre-compiled headers (PCH). - Do not use any forced included files (
/FI
). - Compile a single file at a time by using
msbuild /p:UseMultiToolTask=true
.- If you use a project file, include
%(Filename)
within<ObjectFileName>
.
- If you use a project file, include
- If using incremental builds, make sure that the cache is located within
%APPDATA
or%TEMP%
. Visual Studio tracks compilation inputs and outputs via syscall hooks and will treat ccache's auxiliary outputs, such as statistics and temporary output files, as relevant to the build. When these files are updated or removed, Visual Studio will consider the project inputs dirty and trigger unnecessary rebuilds.
When using CMake, you can add the following CMake code to enable ccache
and set the appropriate value for CMAKE_MSVC_DEBUG_INFORMATION_FORMAT:
find_program(ccache_exe ccache)
if(ccache_exe)
file(COPY_FILE
${ccache_exe} ${CMAKE_BINARY_DIR}/cl.exe
ONLY_IF_DIFFERENT)
# By default Visual Studio generators will use /Zi which is not compatible
# with ccache, so tell Visual Studio to use /Z7 instead.
message(STATUS "Setting MSVC debug information format to 'Embedded'")
set(CMAKE_MSVC_DEBUG_INFORMATION_FORMAT "$<$<CONFIG:Debug,RelWithDebInfo>:Embedded>")
set(CMAKE_VS_GLOBALS
"CLToolExe=cl.exe"
"CLToolPath=${CMAKE_BINARY_DIR}"
"UseMultiToolTask=true"
"DebugInformationFormat=OldStyle"
)
endif()
- https://github.com/mbitsnbites/buildcache/blob/master/doc/usage.md
- https://devblogs.microsoft.com/cppblog/improved-parallelism-in-msbuild/
- https://docs.microsoft.com/en-us/cpp/build/reference/mp-build-with-multiple-processes?view=msvc-170&viewFallbackFrom=vs-2019
- https://docs.microsoft.com/en-us/cpp/build/reference/compiler-options-listed-by-category?view=msvc-170
- https://docs.microsoft.com/en-us/visualstudio/msbuild/msbuild-command-line-reference?view=vs-2022