changeset 12111:5c028172c2a2

Do only one call to GetVersionEx in the common case.
author Bruno Haible <bruno@clisp.org>
date Sat, 03 Oct 2009 20:34:12 +0200
parents a141d503d085
children e375e45551a4
files ChangeLog lib/uname.c
diffstat 2 files changed, 26 insertions(+), 8 deletions(-) [+]
line wrap: on
line diff
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,9 @@
+2009-10-03  Paolo Bonzini  <bonzini@gnu.org>
+	    Bruno Haible  <bruno@clisp.org>
+
+	* lib/uname.c: Include <string.h>.
+	(uname): Do only one call to GetVersionEx in the common case.
+
 2009-10-03  Paolo Bonzini  <bonzini@gnu.org>
 	    Bruno Haible  <bruno@clisp.org>
 
--- a/lib/uname.c
+++ b/lib/uname.c
@@ -24,6 +24,7 @@
 
 #include <stdio.h>
 #include <stdlib.h>
+#include <string.h>
 #include <unistd.h>
 #include <windows.h>
 
@@ -49,16 +50,31 @@
 uname (struct utsname *buf)
 {
   OSVERSIONINFO version;
+  OSVERSIONINFOEX versionex;
+  BOOL have_versionex; /* indicates whether versionex is filled */
   const char *super_version;
 
+  /* Preparation: Fill version and, if possible, also versionex.
+     But try to call GetVersionEx only once in the common case.  */
+  versionex.dwOSVersionInfoSize = sizeof (OSVERSIONINFOEX);
+  have_versionex = GetVersionEx (&versionex);
+  if (have_versionex)
+    {
+      /* We know that OSVERSIONINFO is a subset of OSVERSIONINFOEX.  */
+      memcpy (&version, &versionex, sizeof (OSVERSIONINFO));
+    }
+  else
+    {
+      version.dwOSVersionInfoSize = sizeof (OSVERSIONINFO);
+      if (!GetVersionEx (&version))
+	abort ();
+    }
+
   /* Fill in nodename.  */
   if (gethostname (buf->nodename, sizeof (buf->nodename)) < 0)
     strcpy (buf->nodename, "localhost");
 
   /* Determine major-major Windows version.  */
-  version.dwOSVersionInfoSize = sizeof (OSVERSIONINFO);
-  if (!GetVersionEx (&version))
-    abort ();
   if (version.dwPlatformId == VER_PLATFORM_WIN32_NT)
     {
       /* Windows NT or newer.  */
@@ -135,11 +151,7 @@
 	  }
       else if (version.dwMajorVersion == 6)
 	{
-	  OSVERSIONINFOEX versionex;
-
-	  versionex.dwOSVersionInfoSize = sizeof (OSVERSIONINFOEX);
-	  if (GetVersionEx ((OSVERSIONINFO *) &versionex)
-	      && versionex.wProductType != VER_NT_WORKSTATION)
+	  if (have_versionex && versionex.wProductType != VER_NT_WORKSTATION)
 	    strcpy (buf->release, "Windows Server 2008");
 	  else
 	    switch (version.dwMinorVersion)