GitHub Action for configuring Developer Command Prompt for Microsoft Visual C++.
This sets up the environment for compiling C/C++ code from command line.
Supports Windows. Does nothing on Linux and macOS.
This is a maintained fork of ilammy/msvc-dev-cmd, which has not been updated since March 2024.
It is a drop-in replacement: change ilammy/msvc-dev-cmd@v1 to rzlamrr/msvc-dev-cmd@v2. See Migrating from v1.
Basic usage for default compilation settings is like this:
jobs:
test:
steps:
- uses: actions/checkout@v7
- uses: rzlamrr/msvc-dev-cmd@v2
- name: Build something requiring CL.EXE
run: |
cmake -G "NMake Makefiles" .
nmake
# ...If you want something non-default, like using a specific version of Visual Studio, or cross-compling for a different target, you will need to configure those settings via inputs:
jobs:
test:
# Run a job for each of the specified target architectures:
strategy:
matrix:
arch:
- amd64
- amd64_x86
- amd64_arm64
steps:
- uses: actions/checkout@v7
- uses: rzlamrr/msvc-dev-cmd@v2
with:
arch: ${{ matrix.arch }}
- name: Build something requiring CL.EXE
run: |
cmake -G "NMake Makefiles" .
nmake
# ...arch– target architecture- native compilation:
x64(default, except on ARM64 runners where it isarm64) or its synonyms:amd64,win64,x86_64,x86-64x86or its synonyms:win32arm64for native compilation on ARM64 runners such aswindows-11-arm
- cross-compilation:
x86_amd64,x86_arm,x86_arm64,amd64_x86,amd64_arm,amd64_arm64
- native compilation:
sdk– Windows SDK to use- do not specify to use the default SDK
- or specify full Windows 10 SDK number (e.g,
10.0.10240.0) - or write
8.1to use Windows 8.1 SDK
toolset– select VC++ compiler toolset version- do not specify to use the default toolset
14.0for VC++ 2015 Compiler Toolset14.XXfor the latest 14.XX toolset installed (e.g,14.11)14.XX.YYYYYfor a specific full version number (e.g,14.11.25503)
uwp– settrueto build for Universal Windows Platform (i.e., for Windows Store)spectre– settrueto use Visual Studio libraries with Spectre mitigationsvsversion– the Visual Studio version to use. This can be the version number (e.g. 16.0 for 2019) or the year (e.g. "2019"); omit this input to select the latest version of Visual Studio. On GitHub-hosted runners, this input is not required because there is only one Visual Studio in the environment.
These describe what vcvarsall.bat actually configured, for use by later steps (e.g., ${{ steps.msvc.outputs.vs-version }} for a step with id: msvc).
arch– target architecture passed tovcvarsall.bat, after resolving synonyms (e.g.,Win64becomesx64)vcvarsall– path of thevcvarsall.batthat was usedinstallation-path– Visual Studio installation directory, without a trailing backslashvs-version– Visual Studio version number (e.g.,17.0for 2022,18.0for 2026)toolset-version– full version of the MSVC toolset in use (e.g.,14.51.36231)
installation-path, vs-version and toolset-version are empty for very old Visual Studio versions that do not report them.
If toolset or vsversion does not match what is installed, the error lists the Visual Studio installations found by vswhere and, for a bad toolset, the toolsets installed in the selected Visual Studio.
Note that GitHub-hosted runners come with a single Visual Studio each (e.g., windows-2022 has only 2022, windows-2025-vs2026 only 2026), so vsversion normally does not need to be set there;
see the runner images for the installed Visual Studio versions and toolsets.
All inputs work as before. What is different in v2:
- Runs on Node 24, so it needs a runner of version 2.327.0 or newer (GitHub-hosted runners are always recent enough).
- On ARM64 runners the default
archis nowarm64instead ofx64. Setarch: x64(oramd64_arm64to cross-compile) to get the old behavior there. - Visual Studio 2026 is supported (
vsversion: "2026"or"18.0"). It no longer supports targeting 32-bit ARM, soamd64_armand friends fail on it. - New outputs, and error messages that list what is installed when
toolsetorvsversiondoes not match. - Values of environment variables containing
=are no longer truncated.
Using shell: bash in Actions may shadow some of the paths added by MSVC.
In particular, link.exe (Microsoft C linker) is prone to be shadowed by /usr/bin/link (GNU filesystem link tool).
Unfortunately, this happens because GitHub Actions unconditionally prepend GNU paths when shell: bash is used,
on top of any paths set by msvc-dev-cmd, every time at the start of each new step.
Hence, there aren't many non-destructive options here.
If you experience compilation errors where link complains about unreasonable command-line arguments,
“extra operand something-something” – that's probably it.
Recommended workaround is to remove /usr/bin/link if that interferes with your builds.
If this is not acceptable, please file an issue, then we'll figure out something better.
You can invoke rzlamrr/msvc-dev-cmd multiple times during your jobs with different inputs
to reconfigure the environment for building with different settings
(e.g., to target multiple architectures).
jobs:
release:
steps:
# ...
- name: Configure build for amd64
uses: rzlamrr/msvc-dev-cmd@v2
with:
arch: amd64
- run: build # (for amd64)
- name: Configure build for x86
uses: rzlamrr/msvc-dev-cmd@v2
with:
arch: amd64_x86
- run: build # (for x86)
- name: Configure build for ARM64
uses: rzlamrr/msvc-dev-cmd@v2
with:
arch: amd64_arm64
- run: build # (for ARM64)
# ...This mostly works but it's not really recommended since Developer Command Prompt was not meant for recursive reconfiguration. That said, if it does not work for you, please file an issue.
Consider using strategy.matrix
to execute different build configuration in parallel, independent environments.
MIT, see LICENSE.