php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login

Patch detect-windows-10-not-working-yet for PHP options/info functions Bug #69642

Patch version 2015-05-15 20:25 UTC

Return to Bug #69642 | Download this patch
Patch Revisions:

Developer: wenz

diff --git a/ext/standard/info.c b/ext/standard/info.c
index 9490aae..b99c6cb 100644
--- a/ext/standard/info.c
+++ b/ext/standard/info.c
@@ -42,8 +42,11 @@
 
 #ifdef PHP_WIN32
 typedef void (WINAPI *PGNSI)(LPSYSTEM_INFO);
+typedef DWORD (WINAPI *PGFVIS)(LPCTSTR, LPDWORD);
+typedef BOOL (WINAPI *PGFVI)(LPCTSTR, DWORD, DWORD, LPVOID);
+typedef BOOL (WINAPI *PVQV)(LPCVOID, LPCTSTR, LPVOID, PUINT);
 typedef BOOL (WINAPI *PGPI)(DWORD, DWORD, DWORD, DWORD, PDWORD);
-# include "winver.h"
+#include "winver.h"
 
 #endif
 
@@ -295,6 +298,9 @@ char* php_get_windows_name()
 	SYSTEM_INFO si;
 	PGNSI pGNSI;
 	PGPI pGPI;
+	PGFVIS pGFVIS;
+	PGFVI pGFVI;
+	PVQV pVQV;
 	DWORD dwType;
 	char *major = NULL, *sub = NULL, *retval;
 
@@ -322,37 +328,65 @@ char* php_get_windows_name()
 					major = "Windows Server 2008 R2";
 				}
 			} else if ( osvi.dwMinorVersion == 2 ) {
-				/* could be Windows 8/Windows Server 2012, could be Windows 8.1/Windows Server 2012 R2 */
-				OSVERSIONINFOEX osvi81;
-				DWORDLONG dwlConditionMask = 0;
-				int op = VER_GREATER_EQUAL;
-
-				ZeroMemory(&osvi81, sizeof(OSVERSIONINFOEX));
-				osvi81.dwOSVersionInfoSize = sizeof(OSVERSIONINFOEX);
-				osvi81.dwMajorVersion = 6;
-				osvi81.dwMinorVersion = 3;
-				osvi81.wServicePackMajor = 0;
-
-				VER_SET_CONDITION(dwlConditionMask, VER_MAJORVERSION, op);
-				VER_SET_CONDITION(dwlConditionMask, VER_MINORVERSION, op);
-				VER_SET_CONDITION(dwlConditionMask, VER_SERVICEPACKMAJOR, op);
-
-				if (VerifyVersionInfo(&osvi81,
-					VER_MAJORVERSION | VER_MINORVERSION | VER_SERVICEPACKMAJOR,
-					dwlConditionMask)) {
-					osvi.dwMinorVersion = 3; /* Windows 8.1/Windows Server 2012 R2 */
-					if( osvi.wProductType == VER_NT_WORKSTATION )  {
-						major = "Windows 8.1";
-					} else {
-						major = "Windows Server 2012 R2";
-					}
-				} else {
-					if( osvi.wProductType == VER_NT_WORKSTATION )  {
-						major = "Windows 8";
-					} else {
-						major = "Windows Server 2012";
-					}
+				/* could be Windows 8/Windows Server 2012, Windows 8.1/Windows Server 2012 R2, or Windows 10/Windows Server 2016 */
+				BOOL versionDetected = 0;
+				HANDLE hVersion = LoadLibrary("version.dll");
+				if (NULL != hVersion) {
+					pGFVIS = (PGFVIS) GetProcAddress(hVersion, "GetFileVersionInfoSize");
+					if (NULL != pGFVIS) {
+						DWORD dwlHandle;
+						DWORD dwlSize = pGFVIS("kernel32.dll", &dwlHandle);
+						if (dwlSize > 0) {
+							pGFVI = (PGFVI) GetProcAddress(hVersion, "GetFileVersionInfo");
+							if (NULL != pGFVI) {
+								BYTE* pVI;
+								ZeroMemory(&pVI, dwlSize);
+								if (pGFVI("kernel32.dll", dwlHandle, dwlSize, pVI)) {
+									VS_FIXEDFILEINFO *pFI = NULL;
+									UINT len;
+									pVQV = (PVQV) GetProcAddress(hVersion, "VerQueryValue");
+									if (NULL != pVQV) {
+										if (pVQV(pVI, "\\", (LPVOID *)&pFI, &len)) {
+											DWORD dwlVersion = pFI->dwFileVersionMS;
+											WORD majorVersion = HIWORD(dwlVersion);
+											WORD minorVersion = LOWORD(dwlVersion);
+											versionDetected = 1;
+										
+											if (majorVersion == 10 && minorVersion == 0) {
+												osvi.dwMajorVersion = 10; /* Windows 10/Windows Server 2016 */
+												osvi.dwMinorVersion = 0; 
+												if( osvi.wProductType == VER_NT_WORKSTATION )  {
+													major = "Windows 10";
+												} else {
+													major = "Windows Server 2016";
+												}
+											} else if (majorVersion == 6 && minorVersion == 3) {
+												osvi.dwMinorVersion = 3; /* Windows 8.1/Windows Server 2012 R2 */
+												if( osvi.wProductType == VER_NT_WORKSTATION )  {
+													major = "Windows 8.1";
+												} else {
+													major = "Windows Server 2012 R2";
+												}
+											} else {
+												if( osvi.wProductType == VER_NT_WORKSTATION )  {
+													major = "Windows 8";
+												} else {
+													major = "Windows Server 2012";
+												}
+											}
+				
+										}
+									} 
+								}
+							} 
+						}
+					} 
+				} 
+				
+				if (versionDetected == 0) {
+					major = "Unknown Windows version";
 				}
+				
 			} else {
 				major = "Unknown Windows version";
 			}
@@ -510,10 +544,13 @@ PHPAPI zend_string *php_get_uname(char mode)
 		php_get_windows_cpu(wincpu, sizeof(wincpu));
 		dwBuild = (DWORD)(HIWORD(dwVersion));
 
-		/* Windows "version" 6.2 could be Windows 8/Windows Server 2012, but also Windows 8.1/Windows Server 2012 R2 */
+		/* Windows "version" 6.2 could be Windows 8/Windows Server 2012, but also Windows 8.1/Windows Server 2012 R2 or Windows 10/Windows Server 2016 */
 		if (dwWindowsMajorVersion == 6 && dwWindowsMinorVersion == 2) {
 			if (strncmp(winver, "Windows 8.1", 11) == 0 || strncmp(winver, "Windows Server 2012 R2", 22) == 0) {
 				dwWindowsMinorVersion = 3;
+			} else if (strncmp(winver, "Windows 10", 10) == 0 || strncmp(winver, "Windows Server 2016", 19) == 0) {
+				dwWindowsMajorVersion = 10;
+				dwWindowsMinorVersion = 0;
 			}
 		}
 
 
PHP Copyright © 2001-2019 The PHP Group
All rights reserved.
Last updated: Fri Sep 20 01:01:28 2019 UTC