Determine Windows version on startup

Determine the running version of Windows and load the 4 components into
caml_win32_major, caml_win32_minor, caml_win32_build and
caml_win32_revision.

Starting from Windows 8.1, Microsoft made the entirely flawed decision
to start lying to processes about the version of Windows on which
they're running which means that the classic GetVersion and GetVersionEx
calls can no longer be used.

The code here determines the Windows version by reading the version
information block from kernel32.dll.
master
David Allsopp 2017-10-06 11:39:00 +01:00
parent 388a6347dc
commit 92f034bc49
7 changed files with 52 additions and 10 deletions

View File

@ -18,6 +18,13 @@
#ifndef CAML_OSDEPS_H
#define CAML_OSDEPS_H
#ifdef _WIN32
extern unsigned short caml_win32_major;
extern unsigned short caml_win32_minor;
extern unsigned short caml_win32_build;
extern unsigned short caml_win32_revision;
#endif
#ifdef CAML_INTERNALS
#include "misc.h"
@ -91,12 +98,14 @@ extern char_os * caml_executable_name(void);
*/
extern char_os *caml_secure_getenv(char_os const *var);
/* Windows Unicode support */
#ifdef _WIN32
extern int caml_win32_rename(const wchar_t *, const wchar_t *);
extern void caml_probe_win32_version(void);
/* Windows Unicode support */
extern int win_multi_byte_to_wide_char(const char* s, int slen, wchar_t *out, int outlen);
extern int win_wide_char_to_multi_byte(const wchar_t* s, int slen, char *out, int outlen);

View File

@ -368,6 +368,11 @@ CAMLprim value caml_sys_get_argv(value unit)
void caml_sys_init(char_os * exe_name, char_os **argv)
{
#ifdef _WIN32
/* Initialises the caml_win32_* globals on Windows with the version of
Windows which is running */
caml_probe_win32_version();
#endif
#ifdef CAML_WITH_CPLUGINS
caml_cplugins_init(exe_name, argv);
#endif

View File

@ -57,6 +57,11 @@ typedef unsigned int uintptr_t;
#define _UINTPTR_T_DEFINED
#endif
unsigned short caml_win32_major = 0;
unsigned short caml_win32_minor = 0;
unsigned short caml_win32_build = 0;
unsigned short caml_win32_revision = 0;
CAMLnoreturn_start
static void caml_win32_sys_error (int errnum)
CAMLnoreturn_end;
@ -869,3 +874,26 @@ CAMLexport caml_stat_string caml_stat_strdup_of_utf16(const wchar_t *s)
return out;
}
void caml_probe_win32_version(void)
{
/* Determine the version of Windows we're running, and cache it */
WCHAR fileName[MAX_PATH];
DWORD size =
GetModuleFileName(GetModuleHandle(L"kernel32"), fileName, MAX_PATH);
DWORD dwHandle = 0;
BYTE* versionInfo;
fileName[size] = 0;
size = GetFileVersionInfoSize(fileName, &dwHandle);
versionInfo = (BYTE*)malloc(size * sizeof(BYTE));
if (GetFileVersionInfo(fileName, 0, size, versionInfo)) {
UINT len = 0;
VS_FIXEDFILEINFO* vsfi = NULL;
VerQueryValue(versionInfo, L"\\", (void**)&vsfi, &len);
caml_win32_major = HIWORD(vsfi->dwFileVersionMS);
caml_win32_minor = LOWORD(vsfi->dwFileVersionMS);
caml_win32_build = HIWORD(vsfi->dwFileVersionLS);
caml_win32_revision = LOWORD(vsfi->dwFileVersionLS);
}
free(versionInfo);
}

View File

@ -122,8 +122,8 @@ BYTECCDBGCOMPOPTS=-g
LDFLAGS=-municode
### Libraries needed
BYTECCLIBS=-lws2_32
NATIVECCLIBS=-lws2_32
BYTECCLIBS=-lws2_32 -lversion
NATIVECCLIBS=-lws2_32 -lversion
### How to invoke the C preprocessor
CPP=cpp

View File

@ -122,8 +122,8 @@ BYTECCDBGCOMPOPTS=-g
LDFLAGS=-municode
### Libraries needed
BYTECCLIBS=-lws2_32
NATIVECCLIBS=-lws2_32
BYTECCLIBS=-lws2_32 -lversion
NATIVECCLIBS=-lws2_32 -lversion
### How to invoke the C preprocessor
CPP=cpp

View File

@ -113,8 +113,8 @@ BYTECCDBGCOMPOPTS=-Zi
LDFLAGS=/ENTRY:wmainCRTStartup
### Libraries needed
BYTECCLIBS=advapi32.lib ws2_32.lib
NATIVECCLIBS=advapi32.lib ws2_32.lib
BYTECCLIBS=advapi32.lib ws2_32.lib version.lib
NATIVECCLIBS=advapi32.lib ws2_32.lib version.lib
### How to invoke the C preprocessor
CPP=cl -nologo -EP

View File

@ -115,8 +115,8 @@ LDFLAGS=/ENTRY:wmainCRTStartup
### Libraries needed
#EXTRALIBS=bufferoverflowu.lib # for the old PSDK compiler only
EXTRALIBS=
BYTECCLIBS=advapi32.lib ws2_32.lib
NATIVECCLIBS=advapi32.lib ws2_32.lib
BYTECCLIBS=advapi32.lib ws2_32.lib version.lib
NATIVECCLIBS=advapi32.lib ws2_32.lib version.lib
### How to invoke the C preprocessor
CPP=$(CC) -nologo -EP