Winamp & Shoutcast Forums

Winamp & Shoutcast Forums (http://forums.winamp.com/index.php)
-   NSIS Discussion (http://forums.winamp.com/forumdisplay.php?f=65)
-   -   Get # of cores AND logical processors (http://forums.winamp.com/showthread.php?t=321596)

redxii 12th August 2010 07:46

Get # of cores AND logical processors
 
This is probably what I am looking for: http://msdn.microsoft.com/en-us/library/ms683194.aspx

This is actually way over my head, I don't understand a damn thing about using System plug-in even after reading the readme. I want to get the number of cores when hyperthreading is involved. It should say I have 2 cores/processors and not 4.

CPUDesc was last compiled in 2003, and it's not unicode.

MSG 12th August 2010 08:27

(You can use the CallAnsiPlugin plug-in to execute ansi plugins on unicode NSIS.)

redxii 12th August 2010 17:24

Well, it also counts hyperthreading as a cpu.. even Atom processors are hyperthreaded.

f0rt 13th August 2010 16:28

I took the challenge and came up with the following script.

PHP Code:

OutFile "cpuinfo.exe"

!include "LogicLib.nsh"

!define FALSE                     0 
!define TRUE                      1

!define ERROR_INSUFFICIENT_BUFFER 122

Size of SYSTEM_LOGICAL_PROCESSOR_INFORMATION on 32-bit systems
!define SYS_LOG_PROC_INFO_SIZE    24
Offset of Relationship in the SYSTEM_LOGICAL_PROCESSOR_INFORMATION structure
!define RELATIONSHIP_OFFSET       4
Enum value of Relationship identifying Processor Core
!define RELATIONPROCESSORCORE     0

Count the number of bits set in given value
Parametersvalue
Returnsnumber of bits set in given value
Function countbits
   Exch 
$0
   Push 
$1
   Push 
$2

   
Set initial value for number of bits set in $0
   StrCpy 
$1 0

   
${While} $0
      
Clear least significant bit set
      IntOp 
$$1
      IntOp 
$$& $2
      
Increment number of bits set
      IntOp 
$$1
   
${EndWhile}

   ; Return 
number of bits set
   StrCpy 
$$1

   Pop 
$2
   Pop 
$1
   Exch 
$0
FunctionEnd

Evaluate processor information
Paramatersbufferlength
Returnsnumber of cores
Function evalcpuinfo
   Exch 
$length
   Exch
   Exch 
$buffer
   Push 
$2
   Push 
$3
   Push 
$4
   Push 
$Processor Cores
   Push 
$Logical Processors

   
Set buffer offset at the end of the buffer
   StrCpy 
$$0

   
Initialize number of Processor Cores and Logical Processors
   StrCpy 
$5 0
   StrCpy 
$6 0

   
Iterate through buffer starting from end
   
${While} $>= ${SYS_LOG_PROC_INFO_SIZE}
       ; 
Calculate start address of an element
       IntOp 
$$- ${SYS_LOG_PROC_INFO_SIZE}
       
IntOp $$+ $2
       
Get ProcessorMask value from element
       System
::Call "*$3(i.r4)"
       
Push $4
       IntOp 
$$+ ${RELATIONSHIP_OFFSET}
       ; 
Get Relationship value from element
       System
::Call "*$3(i.r4)"
       
${If} $== ${RELATIONPROCESSORCORE}
           ; 
Increment Processor cores
           IntOp 
$$1
           
Determine number of Logical Processor by counting the bits
           
set in the value of ProcessorMask
           Call countbits
           Pop 
$4
           
Sum up Logical Processors
           IntOp 
$$+ $4
       
${Else}
           
Pop $4
       
${EndIf}
   ${EndWhile}
 
   ; 
Set processor information as return value
   StrCpy 
$"Processor Core(s): $5 Logical Processor(s): $6"
 
   
Pop $6
   Pop 
$5
   Pop 
$4
   Pop 
$3
   Pop 
$2
   Pop 
$1
   Exch 
$0
FunctionEnd

Get processor information
Returnsnumber of Processor Cores and Logical Processors
Function getcpuinfo
  Push 
$0
  Push 
$1
  Push 
$2
  Push 
$3
  Push 
$4

  
GetLogicalProcessorInformation is only available on 
  
Windows XP SP3 or its successors.

  ; 
Initialize buffer and its length
  StrCpy 
$1 0
  StrCpy 
$2 0

  
Determine required length of buffer
  System
::Call "kernel32::GetLogicalProcessorInformation(ir1, *ir2r2) i.r3 ? e"
  
Pop $4
  
${If} $== ${FALSE}
     ${If} $
== ${ERROR_INSUFFICIENT_BUFFER}
         ; 
Allocate buffer
         System
::Alloc $2
         Pop 
$1
         
${If} $!= 0
             
Get processor information
             System
::Call "kernel32::GetLogicalProcessorInformation(ir1, *ir2r2) i.r3 ? e"
             
Pop $4
             
${If} $!= ${TRUE}
                 
StrCpy $"Error: $4"
             
${Else}
                 
Push $buffer
                 Push 
$length
                 Call evalcpuinfo
                 Pop 
$0
             
${EndIf}
             ; 
Deallocate buffer
             System
::Free $1
         
${Else}
             
StrCpy $"Error: memory allocation failed!"
         
${EndIf}
     ${Else}
         
StrCpy $"Error: $4"
     
${EndIf}
  ${Else}
     
StrCpy $"GetLogicalProcessorInformation is not available on your system!"
  
${EndIf}
  
  
Pop $4
  Pop 
$3
  Pop 
$2
  Pop 
$1
  Exch 
$0
FunctionEnd

Function .onInit
  InitPluginsDir
  Call getcpuinfo
  Pop 
$0
  MessageBox MB_OK 
"$0"
  
Quit
FunctionEnd

Section 
SectionEnd 


redxii 13th August 2010 19:29

Works for me, 64-bit Win 7, reports 2 cores/4 logical . Anyone else want to test it out?

redxii 13th August 2010 22:12

I tried on my AMD Turion X2 laptop and it reported correctly, and had someone test his and it reported correctly on his Core i7.

You should wiki it since I am sure other people will find it of use.

MSG 14th August 2010 07:33

"Processor core(s): 1 Logical Processor(s): 2" for my C2D E6750 on Windows Server 2003 SP2 (actual OS).
"GetLogicalProcessorInformation is not available on your system!" for same CPU on Windows 98 SE virtual machine.
"GetLogicalProcessorInformation is not available on your system!" for same CPU on Windows 2000 pro VM. (Is there an alternative here?)
"Processor core(s): 2 Logical Processor(s): 2" for same CPU on Windows Vista VM.
"Processor core(s): 2 Logical Processor(s): 2" for same CPU on Windows 7 pro x64 VM.
"Processor core(s): 2 Logical Processor(s): 2" for same CPU on Windows XP pro x64 VM.

VMs are run on VMWare Workstation. Obviously there are still some kinks that need to be solved, but the help on the SYSTEM_LOGICAL_PROCESSOR_INFORMATION struct is rather confusing... If I'm reading it correctly, Windows Server 2003 and Windows XP Professional x64 Edition should both return the same thing. So maybe it's VMWare that's simulating the two C2D cores as two physical CPUs?

redxii 14th August 2010 07:53

Using unicode anyway, Win 2000 users in this particular application is a very very small minority, the market share of Win 2000 isn't even half a percent. The particular program being packaged does not support 9x/ME/NT.

Every system I tested had Win 7 64-bit.


All times are GMT. The time now is 17:26.

Copyright © 1999 - 2010 Nullsoft. All Rights Reserved.