October 2020



Installing multiple build types In CMake generated Visual Studio projects

One of the issues a build manager faces is the differing behavior of makefile and solution based build systems; particularly when it comes to installation procedure. What we’re talking about specifically is the behavior of gmake on Linux versus Visual Studio on Windows.

The CMake build type is set at configure time on Linux, but at build time on Windows. One of the issues that arises from this dichotomous mechanism is how “install” targets are handled for multiple build types. Install locations are fairly straight forward on Linux. When one is releasing multiple configurations, then the compilation products simply go some place like:


The issue with cmake generated Visual Studio solutions is that CMAKE_BUILD_TYPE is undefined for solution based systems. The build type is a compile-time choice  in Visual Studio, and unknown when the solution file is generated.

So why is this an issue? Consider that you are making a release of your software, and you have two (user defined) configurations to include in the release — Debug-assert, and Debug-no-assert. In Linux, the build type is set at configure time, so we have no problem. You will configure before each build and tell cmake the build type. Now installation is a one liner that never varies, like so:

That same code won’t work in Visual Studio however. In Visual Studio , you set the build type at compile time (through the GUI), and so there is no way for the build system to know the configuration type — right? Not so fast! Cmake generates the Visual Studio project, then the generated project invokes Cmake,  handing it $(OutDir). Cmake then sets the variable BUILD_TYPE equal to $(OutDir) and uses it throughout the course of the install procedure. In the generated INSTALL.vcproj file, you’ll see a line similar to the following in the section for each configuration type:
CommandLine="C:\Program Files (x86)\CMake 2.8\bin\cmake.exe; -DBUILD_TYPE=$(OutDir) -P cmake_install.cmake"
Well Cmake is happy now, but what about you?  How in the hell do you refer to a Visual Studio configuration type that doesn’t exist until compile time? That answer is of course undocumented, but fairly simple. What you want to do is hand the install command the literal string “${BUILD_TYPE}”.
In Cmake, the backslash is analogous to := in gmake — that is — it defers expansion of the variable it precedes. cmake_install.cmake is then passed  the literal string ${BUILD_TYPE}. You have what you want. Cmake has what it wants. At least in theory, everyone is happy.

Continue Reading

Creating a Visual Studio aware console window

What good is findstr without a command prompt, and what good is a command prompt that is unaware of your development environment?

When you install Visual Studio 20xx, it adds a menu item for a “devenv” (my term, not Microsoft’s) command window. That’s great, but not terribly convenient. Terribly convenient but not particularly great is the “Open command window here” context menu item in the Windows Explorer. What we really need is a devenv window that we can launch from the Explorer context menu, like this:


You’ll need two files; A registry patch, and a batch file to massage the command window. The download link below contains the files for Visual Studio versions 2008-2013.

  • Download and expand the archive.
  • Right click on the appropriate reg file and select “merge”.
  • Place the corresponding batch file somewhere in your default system path — windowssystem32 for example.
Now when you select “Open VS20xx env window here” from the Explorer context menu, the window that opens will contain the VS development environment. Good stuff.

File contents are listed below. The Visual Studio 2010 files are shown; all others are identical except for VS version number.

@echo off
call "C:\Program Files (x86)\Microsoft Visual Studio 10.0\VCvcvarsall.bat" amd64
pushd %1

Windows Registry Editor Version 5.00
[HKEY_CLASSES_ROOTDirectoryshellvs2010_shell] @="Open VS2010 env window here"
[HKEY_CLASSES_ROOTDirectoryshellvs2010_shellcommand] @="cmd.exe /s /k vs2010.bat "%V""

Download the archive via the link below.

Continue Reading

Setting the Visual Studio Debugger path using CMake

Debugging our just-built executables was a real source of frustration early on in our Windows programming experience. Getting all the correct libraries into the path was tedious at best, and more often than not a nightmare of hellish proportion. To be certain, copying files around and hacking environment variables to this end is just asking for it. It’s not a matter of if a critical mistake will be made, it’s a matter of when; and that’s just the command line version of events. Needless to say, we weren’t happy.

When it came time to run the code in the Windows Debugger, things were almost just as bad. Every time we wanted to debug an executable, we had to make modifications to a generated Visual Studio project file. The procedure was time consuming, tedious, and error prone. We needed a solution that would ensure the correct behavior every time, and without any human intervention. The problem was that CMake did not, and to the best of my knowledge does not currently have, any mechanism for modifying the Visual Studio Debugger path in a generated project. Still, we needed to get the job done with CMake. Maybe it couldn’t set the debugger path, but it could write out a configured file. Enter the Visual Studio .user file.

The Solution

Before we begin, I am aware that Microsoft suggests avoiding the use of .user files. Their caution stems from source code control issues however, and the files we are about to generate are intentionally volatile. We aren’t going to commit anything in the build directory to our source code repository, though the input file that follows should be placed somewhere in your source tree and committed.

Step 1:
Create a CMake input file called “project.vcxproj.user.in” with the following content:

<?xml version="1.0" encoding="utf-8"?>	 	
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">	 	
 <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">	 	

The value for PATH in the LocalDebuggerEnvironment tag is of course up to you; the above is merely a simple example using “Debug” as the Configuration Type.

Step 2:
Configure project.vcxproj.user.in for each executable in your solution/project; something like this:

foreach(src ${EXEC_SRCS}) 
	add_executable(${src} ${src}.cc) 
	configure_file(project.vcxproj.user.in ${CMAKE_BINARY_DIR}/${src}.vcxproj.user @ONLY) 

Now when you start a debugging session, the appropriate paths will be set and things should work as expected. There are likely other and perhaps better ways to accomplish this goal, with the ideal solution being to set the debugger path with some CMake property. In the meantime, we make do with the tools avalable to us.

Continue Reading