/*
Module : Dtwinver.cpp
Purpose: Implementation of a comprehensive function to perform OS version detection
Created: PJN / 11-05-1996
History: PJN / 24-02-1997 A number of updates including support for NT 3.1,
single mode dos in Windows 95 and better Windows
version detecion under real mode dos.
PJN / 13-09-1998 1. Added explicit support for Windows 98
2. Updated documentation to use HTML.
3. Minor update to the web page describing it.
PJN / 22-06-1999 1. UNICODE enabled the code.
2. Removed need for the dwOSVersionInfoSize variable
3. Added support for detecting Build Number of 95 and 98 from DOS code path.
4. Now ships as standard with VC 5 workspace files
5. Added explicit support for Windows 95 SP 1
6. Added explicit support for Windows 95 OSR 2
7. Added explicit support for Windows 98 Second Edition
8. Added explicit support for Windows 2000
9. Added explicit support for Windows CE
10. Added explicit support for Windows Terminal Server's
11. Added explicit support for NT Stand Alone Server's.
12. Added explicit support for NT Primary Domain Controller's
13. Added explicit support for NT Backup Domain Controller's
PJN / 23-07-1999 Tested out support for Windows 98 SE, minor changes required
PJN / 26-07-1999 Added explicit support for Windows 98 SP 1
PJN / 28-07-1999 1. Fixed a problem when application is build in non-huge/large
memory model in Win16
2. Added explicit support for returning NT and Win9x service pack information
from Win32 and Win16 code paths
3. Updated test program to not bother reporting on any info which does not
exist. e.g. if there is no service pack installed, then we don't bother
displaying any info about service packs
4. Added explicit support for NT Enterprise Edition
Copyright (c) 1996 - 1999 by PJ Naughter.
All rights reserved.
*/
///////////////////////////////// Includes //////////////////////////////////
#include <windows.h>
#ifdef _WIN32
#include <tchar.h>
#else
#include <ctype.h>
#include <stdlib.h>
#endif
#include <string.h>
#include <stdarg.h>
#include "Dtwinver.h"
///////////////////////////////// Local function / variables /////////////////
#ifndef _WIN32
//taken from Win32 SDK winbase.h file
#define VER_PLATFORM_WIN32s 0
#define VER_PLATFORM_WIN32_WINDOWS 1
#define VER_PLATFORM_WIN32_NT 2
#define VER_PLATFORM_WIN32_CE 3
#elif !defined(UNDER_CE)
BOOL WhichNTProduct(DWORD& dwVersion);
#endif //ifndef _WIN32
#if defined(_WIN32)
//Taken from Windows CE winbase.h file
#ifndef VER_PLATFORM_WIN32_CE
#define VER_PLATFORM_WIN32_CE 3
#endif
#endif //defined(_WIN32)
#if defined(_WIN32) && !defined(UNDER_CE)
// Function pointers to stuff in Kernel (32 bit)
typedef BOOL (WINAPI *lpfnGetVersionEx) (LPOSVERSIONINFO);
//Functions to detect if we are running on Terminal Server
BOOL ValidateProductSuite(LPCTSTR lpszSuiteToValidate);
BOOL IsTerminalServicesEnabled();
BOOL IsEnterpriseServer();
WORD GetNTServicePackFromRegistry();
WORD GetNTServicePackFromCSDString(LPCTSTR pszCSDVersion);
#endif
#if defined(_WINDOWS) && !defined(_WIN32) //required for universal thunks
#define HINSTANCE32 DWORD
#define HFILE32 DWORD
#define HWND32 DWORD
// #defines for WOWCallProc32() parameter conversion
#define PARAM_01 0x00000001
// #defines for dwCapBits
#define WOW_LOADLIBRARY 0x0001
#define WOW_FREELIBRARY 0x0002
#define WOW_GETPROCADDRESS 0x0004
#define WOW_CALLPROC 0x0008
#define WOW_VDMPTR32 0x0010
#define WOW_VDMPTR16 0x0020
#define WOW_HWND32 0x0040
// Wrappers for functions in Kernel (16 bit)
HINSTANCE32 WINAPI WOWLoadLibraryEx32 (LPSTR, HFILE32, DWORD);
BOOL WINAPI WOWFreeLibrary32 (HINSTANCE32);
FARPROC WINAPI WOWGetProcAddress32 (HINSTANCE32, LPCSTR);
DWORD WINAPI WOWGetVDMPointer32 (LPVOID, UINT);
DWORD FAR CDECL WOWCallProc32 (FARPROC, DWORD, DWORD, ...);
UINT WINAPI WOWCreateVDMPointer16(DWORD, DWORD);
UINT WINAPI WOWDeleteVDMPointer16(UINT);
HWND32 WINAPI WOWHwndToHwnd32 (HWND);
//////////////// OSVERSIONINFO taken from Win32 sdk header file
typedef struct _OSVERSIONINFO
{
DWORD dwOSVersionInfoSize;
DWORD dwMajorVersion;
DWORD dwMinorVersion;
DWORD dwBuildNumber;
DWORD dwPlatformId;
char szCSDVersion[128];
} OSVERSIONINFO, *POSVERSIONINFO, FAR *LPOSVERSIONINFO;
// Function pointers to stuff in Kernel (16 bit)
typedef HINSTANCE32 (WINAPI *lpfnLoadLibraryEx32W) (LPSTR, HFILE32, DWORD);
typedef BOOL (WINAPI *lpfnFreeLibrary32W) (HINSTANCE32);
typedef FARPROC (WINAPI *lpfnGetProcAddress32W)(HINSTANCE32, LPCSTR);
typedef DWORD (WINAPI *lpfnGetVDMPointer32W) (LPVOID, UINT);
typedef DWORD (WINAPI *lpfnCallProc32W) (FARPROC, DWORD, DWORD);
typedef WORD (WINAPI *lpfnWNetGetCaps) (WORD);
DWORD dwCapBits;
lpfnLoadLibraryEx32W LoadLibraryEx32W;
lpfnFreeLibrary32W FreeLibrary32W;
lpfnGetProcAddress32W GetProcAddress32W;
lpfnGetVDMPointer32W GetVDMPointer32W;
lpfnCallProc32W CallProc32W;
BOOL WFWLoaded();
#endif //defined(_WINDOWS) && !defined(_WIN32)
#ifdef _DOS
WORD WinVer;
BYTE bRunningWindows;
void GetWinInfo();
#endif //ifdef _DOS
////////////////////////////////// Implementation /////////////////////////////
BOOL GetOSVersion(LPOS_VERSION_INFO lpVersionInformation)
{
//By Default assume no service pack is installed
lpVersionInformation->wEmulatedServicePack = 0;
lpVersionInformation->wUnderlyingServicePack = 0;
#ifdef UNDER_CE
OSVERSIONINFO osvi;
memset(&osvi, 0, sizeof(OSVERSIONINFO));
osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
if (!GetVersionEx(&osvi))
return FALSE;
lpVersionInformation->dwEmulatedMajorVersion = osvi.dwMajorVersion;
lpVersionInformation->dwEmulatedMinorVersion = osvi.dwMinorVersion;
lpVersionInformation->dwEmulatedBuildNumber = LOWORD(osvi.dwBuildNumber); //ignore HIWORD
_tcscpy(lpVersionInformation->szEmulatedCSDVersion, osvi.szCSDVersion);
//Explicitely map the win32 dwPlatformId to our own values
if (osvi.dwPlatformId == VER_PLATFORM_WIN32s)
lpVersionInformation->dwEmulatedPlatformId = PLATFORM_WIN32S;
else if (osvi.dwPlatformId == VER_PLATFORM_WIN32_WINDOWS)
lpVersionInformation->dwEmulatedPlatformId = PLATFORM_WINDOWS;
else if (osvi.dwPlatformId == VER_PLATFORM_WIN32_NT)
lpVersionInformation->dwEmulatedPlatformId = PLATFORM_NT_WORKSTATION; //As a default assume NT Workstation
else if (osvi.dwPlatformId == VER_PLATFORM_WIN32_CE)
lpVersionInformation->dwEmulatedPlatformId = PLATFORM_WINDOWS_CE;
else
return FALSE;
//underlying OS is the same
lpVersionInformation->dwUnderlyingMajorVersion = lpVersionInformation->dwEmulatedMajorVersion;
lpVersionInformation->dwUnderlyingMinor