anon
anon

Reputation: 377

Getting OS build version from Win32 Api C++

I am trying to find the build version of Windows Server 2016 machines, for example RS1 or RS3. There was an API to do this - GetVersionEx() - but is now deprecated.

MSDN says to use Version Helper Functions instead.

I want the build version, for ex: 1607 for RS1.

Is there an API to get this?

Upvotes: 5

Views: 17363

Answers (1)

Adrian McCarthy
Adrian McCarthy

Reputation: 48038

Option 0: (per RbMm) Use [RtlGetVersion] from the driver development kit.

Option 1: [Updated] Grab the version number of a system DLL like kernel32.dll. MSDN used to bless this approach, saying:

To obtain the full version number for the operating system, call the GetFileVersionInfo function on one of the system DLLs, such as Kernel32.dll, then call VerQueryValue to obtain the \StringFileInfo\\ProductVersion subblock of the file version information. [From an Internet Archive snapshot of MSDN circa 2017]

That would look something like this:

// Quick hack without error checking.
#include <cassert>
#include <iomanip>
#include <iostream>
#include <vector>
#include <Windows.h>

int main() {
  const auto system = L"kernel32.dll";
  DWORD dummy;
  const auto cbInfo =
      ::GetFileVersionInfoSizeExW(FILE_VER_GET_NEUTRAL, system, &dummy);
  std::vector<char> buffer(cbInfo);
  ::GetFileVersionInfoExW(FILE_VER_GET_NEUTRAL, system, dummy,
                          buffer.size(), &buffer[0]);
  void *p = nullptr;
  UINT size = 0;
  ::VerQueryValueW(buffer.data(), L"\\", &p, &size);
  assert(size >= sizeof(VS_FIXEDFILEINFO));
  assert(p != nullptr);
  auto pFixed = static_cast<const VS_FIXEDFILEINFO *>(p);
  std::cout << HIWORD(pFixed->dwFileVersionMS) << '.'
            << LOWORD(pFixed->dwFileVersionMS) << '.'
            << HIWORD(pFixed->dwFileVersionLS) << '.'
            << LOWORD(pFixed->dwFileVersionLS) << '\n';

  return 0;
}

Note that the original MSDN link now redirects to a newer documentation set that doesn't mention this approach. I suppose that means this is no longer a supported technique, and, presumably, all the compatibility hacks for older code might prevent an application from getting the actual answer.

Option 2: Query the registry, specifically:

HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion

which has values for CurrentMajorVersionNumber, CurrentMinorVersionNumber, and CurrentBuildNumber.

I can't find official documentation for these values, so this may not be MSDN-approved or future-proof.

Option 3: Use GetProductInfo if available and fall back to GetVersionInfo if it's not.

Upvotes: 11

Related Questions