CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Results 1 to 7 of 7
  1. #1
    Join Date
    Apr 2014
    Posts
    3

    Question Need help on replacement of NtQuerySystemInformation on Win x64

    Hi,

    I am struggling to find a replacement of NtQuerySystemInformation call for 64-bit Windows OS, like on Windows Server 2008 (64-bit). Can someone help me getting overall CPU utilization (average) over all CPU cores?

    Cheers,
    Dean

    __

    Code:
    #include "StdAfx.h"
    #include "CpuMuninNodePlugin.h"
    
    #define SystemBasicInformation 0
    #define SystemPerformanceInformation 2
    #define SystemTimeInformation 3
    
    #define Li2Double(x) ((double)((x).HighPart) * 4.294967296E9 + (double)((x).LowPart))
    
    // Initialisation
    CpuMuninNodePlugin::CpuMuninNodePlugin()
    { 
      dbIdleTime = 0;
      dbSystemTime = 0;
      liOldIdleTime.QuadPart = 0;
      liOldSystemTime.QuadPart = 0;
      NtQuerySystemInformation = (PROCNTQSI)GetProcAddress(GetModuleHandle(_T("ntdll")), "NtQuerySystemInformation");
    
      // Setup first call
      CalculateCpuLoad();
    }
    
    CpuMuninNodePlugin::~CpuMuninNodePlugin()
    {
    
    }
    
    void CpuMuninNodePlugin::CalculateCpuLoad()
    {
      if (NtQuerySystemInformation != NULL) {
        LONG status;
        SYSTEM_PERFORMANCE_INFORMATION SysPerfInfo;
        SYSTEM_TIME_INFORMATION SysTimeInfo;
        SYSTEM_BASIC_INFORMATION SysBaseInfo;
    
        // get number of processors in the system
        status = NtQuerySystemInformation(SystemBasicInformation, &SysBaseInfo, sizeof(SysBaseInfo), NULL);
        if (status != NO_ERROR)
          return;
    
        // get new system time
        status = NtQuerySystemInformation(SystemTimeInformation, &SysTimeInfo, sizeof(SysTimeInfo), NULL);
        if (status!=NO_ERROR)
          return;
    
        // get new CPU's idle time
        status = NtQuerySystemInformation(SystemPerformanceInformation, &SysPerfInfo, sizeof(SysPerfInfo), NULL);
        if (status != NO_ERROR)
          return;
    
        // if it's a first call - skip it
        if (liOldIdleTime.QuadPart != 0)
        {
          // CurrentValue = NewValue - OldValue
          double diffIdleTime = Li2Double(SysPerfInfo.liIdleTime) - Li2Double(liOldIdleTime);
          double diffSystemTime = Li2Double(SysTimeInfo.liKeSystemTime) - Li2Double(liOldSystemTime);
    
          // CurrentCpuIdle = IdleTime / SystemTime
          dbIdleTime = diffIdleTime / diffSystemTime;
    
          // CurrentCpuUsage% = 100 - (CurrentCpuIdle * 100) / NumberOfProcessors
          dbIdleTime = 100.0 - dbIdleTime * 100.0 / (double)SysBaseInfo.bKeNumberProcessors + 0.5;
        }
    
        // store new CPU's idle and system time
        liOldIdleTime = SysPerfInfo.liIdleTime;
        liOldSystemTime = SysTimeInfo.liKeSystemTime;
      }
    }
    
    int CpuMuninNodePlugin::GetValues(char *buffer, int len) 
    {
      CalculateCpuLoad();
    
      _snprintf(buffer, len, 
        "cpu_user.value %f\n"
        //"cpu_system.value %f\n"
        ".\n", this->dbIdleTime);
      return 0;
    }
    
    int CpuMuninNodePlugin::GetConfig(char *buffer, int len) 
    {
      strncpy(buffer, 
        "graph_args -l 0 --vertical-label percent --upper-limit 100\n"
        "graph_title Cpu usage\n"
        "graph_category system\n"
        "graph_info This graph shows what the machine uses its cpu for.\n"
        "graph_order cpu_user\n"
        //"graph_order cpu_system cpu_user\n"
        "cpu_user.label user\n"
        "cpu_user.draw AREA\n"
        "cpu_user.info CPU used by user-space applications.\n"
        //"cpu_system.label system\n"
        //"cpu_system.draw STACK\n"
        //"cpu_system.info CPU used by kernel.\n"
        ".\n", len);
      return 0;
    }

  2. #2
    Join Date
    Nov 2000
    Location
    Voronezh, Russia
    Posts
    6,620

    Re: Need help on replacement of NtQuerySystemInformation on Win x64

    And what is the problem with NtQuerySystemInformation?
    Best regards,
    Igor

  3. #3
    Join Date
    Apr 2014
    Posts
    3

    Re: Need help on replacement of NtQuerySystemInformation on Win x64

    Hi,

    This API object does not exist in 64bit Windows OS like Windows server 2008. I get a null value. Do you know how I could fix this part of code to get overall average CPU utilisation as a single value from the OS or maybe another engine?

    I am new to C++.

  4. #4
    VictorN's Avatar
    VictorN is offline Super Moderator Power Poster
    Join Date
    Jan 2003
    Location
    Hanover Germany
    Posts
    20,396

    Re: Need help on replacement of NtQuerySystemInformation on Win x64

    Quote Originally Posted by ssddgreg View Post
    Hi,

    I am struggling to find a replacement of NtQuerySystemInformation call for 64-bit Windows OS, like on Windows Server 2008 (64-bit). Can someone help me getting overall CPU utilization (average) over all CPU cores?
    Why don't you want to use the way MSDN recommends:
    [NtQuerySystemInformation may be altered or unavailable in future versions of Windows. Applications should use the alternate functions listed in this topic.]
    ...
    SystemBasicInformation
    ... Use the GetSystemInfo function instead.
    ...
    SystemExceptionInformation
    SystemInterruptInformation
    SystemLookasideInformation
    SystemPerformanceInformation

    ....
    Use the CryptGenRandom function instead.
    ...
    Use GetSystemInfo instead.
    ...
    Use the SLGetWindowsInformation function instead.
    ...
    use GetProcessHandleCount ...
    ...
    Use GetSystemTimes instead
    ...
    Use GetSystemRegistryQuota instead
    Victor Nijegorodov

  5. #5
    Join Date
    Apr 2014
    Posts
    3

    Re: Need help on replacement of NtQuerySystemInformation on Win x64

    Quote Originally Posted by VictorN View Post
    Why don't you want to use the way MSDN recommends:
    I cannot find any substitute for CPU utilisation for the whole machine.

  6. #6
    Join Date
    Apr 2000
    Location
    Belgium (Europe)
    Posts
    4,626

    Re: Need help on replacement of NtQuerySystemInformation on Win x64

    overall CPU usage can be obtained with GetSystemTimes()
    CPU load in percent = ((systemtime - idletime) *100) / systemtime

  7. #7
    Join Date
    Apr 2000
    Location
    Belgium (Europe)
    Posts
    4,626

    Re: Need help on replacement of NtQuerySystemInformation on Win x64

    for realtime information there's WMI.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  





Click Here to Expand Forum to Full Width

Featured