⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 performance.c

📁 获取unix系统进程信息的功能
💻 C
📖 第 1 页 / 共 2 页
字号:
#ifdef __cplusplus
extern "C" {
#endif

#ifdef WIN32
#include <windows.h>
#else
#include <unistd.h>
#endif

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

#include "performance.h"
#include "common.h"
#include "utils.h"

#ifdef WIN32
#define SystemBasicInformation       0
#define SystemPerformanceInformation 2
#define SystemTimeInformation        3
#define Li2Double(x) ((double)((x).HighPart) * 4.294967296E9 + (double)((x).LowPart))
#else
#define MEMSIZECMD "/usr/sbin/prtconf 2>/dev/null | awk 'BEGIN{count=0;}/^Memory [Ss]ize/{count=$3*1024;}END{printf \"%.0f\",count}'"
#define PHYSICAL_MEMORY_COMMAND "cat /proc/meminfo | awk 'BEGIN{total=0;free=0;}{if($1~/MemTotal/)total=$2;if($1~/MemFree/)free=$2;}END{printf \"%.0f,%.0f\",total,free}'"
#define SYSTEMSTATCMD "vmstat 1 2| awk 'BEGIN{free_flag = 0;id_flag = 0;}\
{if($0~/fre/ && $0~/id/)\
{for(i=1;i<=NF;i++){if($i~/fre/)free_flag = i;if($i~/id/)id_flag = i;}\
getline;getline;printf \"%.0f,%d\",$free_flag,100 - $id_flag;}}'"
#endif

#ifdef WIN32

typedef struct
{
    DWORD   dwUnknown1;
    ULONG   uKeMaximumIncrement;
    ULONG   uPageSize;
    ULONG   uMmNumberOfPhysicalPages;
    ULONG   uMmLowestPhysicalPage;
    ULONG   uMmHighestPhysicalPage;
    ULONG   uAllocationGranularity;
    PVOID   pLowestUserAddress;
    PVOID   pMmHighestUserAddress;
    ULONG   uKeActiveProcessors;
    BYTE    bKeNumberProcessors;
    BYTE    bUnknown2;
    WORD    wUnknown3;
} SYSTEM_BASIC_INFORMATION;

typedef struct
{
    LARGE_INTEGER   liIdleTime;
    DWORD           dwSpare[76];
} SYSTEM_PERFORMANCE_INFORMATION;

typedef struct
{
    LARGE_INTEGER liKeBootTime;
    LARGE_INTEGER liKeSystemTime;
    LARGE_INTEGER liExpTimeZoneBias;
    ULONG         uCurrentTimeZoneId;
    DWORD         dwReserved;
} SYSTEM_TIME_INFORMATION;

typedef struct {
    USHORT Length;
    USHORT MaxLen;
    USHORT *Buffer;
} UNICODE_STRING;

typedef struct _THREAD_INFO
{
    LARGE_INTEGER CreateTime;
    DWORD dwUnknown1;
    DWORD dwStartAddress;
    DWORD StartEIP;
    DWORD dwOwnerPID;
    DWORD dwThreadId;
    DWORD dwCurrentPriority;
    DWORD dwBasePriority;
    DWORD dwContextSwitches;
    DWORD Unknown;
    DWORD WaitReason;

}THREADINFO, *PTHREADINFO;

struct process_info
{
    DWORD dwOffset;
    DWORD dwThreadsCount;
    DWORD dwUnused1[6];
    LARGE_INTEGER CreateTime;
    LARGE_INTEGER UserTime;
    LARGE_INTEGER KernelTime;
    UNICODE_STRING ProcessName;

    DWORD dwBasePriority;
    DWORD dwProcessID;
    DWORD dwParentProcessId;
    DWORD dwHandleCount;
    DWORD dwUnused3[2];

    DWORD dwVirtualBytesPeak;
    DWORD dwVirtualBytes;
    ULONG dwPageFaults;
    DWORD dwWorkingSetPeak;
    DWORD dwWorkingSet;
    DWORD dwQuotaPeakPagedPoolUsage;
    DWORD dwQuotaPagedPoolUsage;
    DWORD dwQuotaPeakNonPagedPoolUsage;
    DWORD dwQuotaNonPagedPoolUsage;
    DWORD dwPageFileUsage;
    DWORD dwPageFileUsagePeak;

    DWORD dCommitCharge;
    THREADINFO ThreadSysInfo[1];
};

typedef LONG (WINAPI *PROCNTQSI)(UINT,PVOID,ULONG,PULONG);

#endif

#ifdef WIN32

int GetSysCpuUsage(float *percent, char *errbuf)
{
    LARGE_INTEGER liOldIdleTime = {0};
    LARGE_INTEGER liOldSystemTime  = {0};	
    SYSTEM_PERFORMANCE_INFORMATION SysPerfInfo;
    SYSTEM_TIME_INFORMATION        SysTimeInfo;
    SYSTEM_BASIC_INFORMATION       SysBaseInfo;
    double                         dbIdleTime;
    double                         dbSystemTime;
    LONG                           status;
    
    PROCNTQSI NtQuerySystemInformation;
    NtQuerySystemInformation = (PROCNTQSI)GetProcAddress(
        GetModuleHandle("ntdll"),
        "NtQuerySystemInformation"
        );
    if (!NtQuerySystemInformation)
    {
        strcpy(errbuf, "2:GetProcAddress() error");
        return -1;
    }

    status = NtQuerySystemInformation(SystemTimeInformation,
        &SysTimeInfo,sizeof(SysTimeInfo),NULL);
    if (status!=NO_ERROR)
    {
        strcpy(errbuf, "2:NtQuerySystemInformation(SystemTimeInformation) error");
        return -1;
    }
    status = NtQuerySystemInformation(SystemPerformanceInformation,
        &SysPerfInfo,sizeof(SysPerfInfo),NULL);
    if (status != NO_ERROR)
    {
        strcpy(errbuf, "2:NtQuerySystemInformation(SystemPerformanceInformation) error");
        return -1;
    }
    
    liOldIdleTime = SysPerfInfo.liIdleTime;
    liOldSystemTime = SysTimeInfo.liKeSystemTime;

    Sleep(500);

    status = NtQuerySystemInformation(SystemBasicInformation,
        &SysBaseInfo,sizeof(SysBaseInfo),NULL);
    if (status != NO_ERROR)
    {
        strcpy(errbuf, "2:NtQuerySystemInformation(SystemBasicInformation) error");
        return -1;
    }
    status = NtQuerySystemInformation(SystemTimeInformation,
        &SysTimeInfo,sizeof(SysTimeInfo),NULL);
    if (status!=NO_ERROR)
    {
        strcpy(errbuf, "2:NtQuerySystemInformation(SystemTimeInformation) error");
        return -1;
    }
    status = NtQuerySystemInformation(SystemPerformanceInformation,
        &SysPerfInfo,sizeof(SysPerfInfo),NULL);
    if (status != NO_ERROR)
    {
        strcpy(errbuf, "2:NtQuerySystemInformation(SystemPerformanceInformation) error");
        return -1;
    }

    dbIdleTime = Li2Double(SysPerfInfo.liIdleTime) - Li2Double(liOldIdleTime);
    dbSystemTime = Li2Double(SysTimeInfo.liKeSystemTime) - Li2Double(liOldSystemTime);
    *percent = (float)dbIdleTime / (float)dbSystemTime;
    *percent = 100.0 - *percent * 100.0 / (float)SysBaseInfo.bKeNumberProcessors + 0.5;
    if (*percent > 100)
    {
        *percent = 100.00;
    }
    if (*percent < 0)
    {
        strcpy(errbuf, "2:get cpu load error");
        return -1;
    }


    return 0;
}

int GetSysMemUsage(float *percent, char *errbuf)
{
    MEMORYSTATUSEX MemStat;
    unsigned long ulAvailPhys = 0,ulTotalPhys = 0;
    int ret;

    memset(&MemStat,0,sizeof(MemStat));
    MemStat.dwLength = sizeof(MEMORYSTATUSEX);
    ret = GlobalMemoryStatusEx(&MemStat);
    if (!ret)
    {
        strcpy(errbuf, "2:GlobalMemoryStatusEx() error");
        return -1;
    }

    ulAvailPhys = MemStat.ullAvailPhys;
    ulTotalPhys = MemStat.ullTotalPhys;
    *percent = 100 - 100*(float)ulAvailPhys/(float)ulTotalPhys;
    return 0;
}

int GetSysMemSize(unsigned long *memsize, char *errbuf)
{
    MEMORYSTATUSEX MemStat;
    int ret;

    memset(&MemStat,0,sizeof(MemStat));
    MemStat.dwLength = sizeof(MEMORYSTATUSEX);
    ret = GlobalMemoryStatusEx(&MemStat);
    if (!ret)
    {
        strcpy(errbuf, "2:GlobalMemoryStatusEx() error");
        return -1;
    }

    *memsize = MemStat.ullTotalPhys/1024;
    return 0;
}

int GetProcCpuUsage(unsigned int pid, float *percent, char *errbuf)
{
    LONG status;	
    void *pProcInfo = NULL;
    struct process_info *pProcessInfo;
    DWORD dwInfoSize = 0x80000;
    __int64 LastTotalProcessCPUUsage = 0;
    __int64 TotalProcessCPUUsage = 0;
    DWORD TotalDelta = 0;
    __int64 cpuload = 0;

    PROCNTQSI NtQuerySystemInformation;
    NtQuerySystemInformation = (PROCNTQSI)GetProcAddress(
        GetModuleHandle( "ntdll.dll" ),
        "NtQuerySystemInformation" );
    if (!NtQuerySystemInformation)
    {
        strcpy(errbuf, "2:GetProcAddress() error");
        return -1;
    }

    pProcInfo = malloc(dwInfoSize);
    if(!pProcInfo)
    {
        return -1;
    }

    memset(pProcInfo, 0, dwInfoSize);
    status = NtQuerySystemInformation(5, pProcInfo, dwInfoSize, 0);
    if (status!=NO_ERROR)
    {
        strcpy(errbuf, "2:NtQuerySystemInformation() error");
        free(pProcInfo);	
        return -1;
    }

    pProcessInfo = (struct process_info *)pProcInfo;
    while(1)
    {
        TotalProcessCPUUsage += (__int64)pProcessInfo->KernelTime.QuadPart + (__int64)pProcessInfo->UserTime.QuadPart;
        if(pid == pProcessInfo->dwProcessID)
        {
            cpuload = (__int64)pProcessInfo->KernelTime.QuadPart + (__int64)pProcessInfo->UserTime.QuadPart;
        }
        if(pProcessInfo->dwOffset == 0)
        {
            break;
        }
        pProcessInfo = (struct process_info *)((byte*)pProcessInfo + pProcessInfo->dwOffset);
    }
    LastTotalProcessCPUUsage = TotalProcessCPUUsage;

    Sleep(500);

    memset(pProcInfo, 0, dwInfoSize);
    status = NtQuerySystemInformation(5, pProcInfo, dwInfoSize, 0);
    if (status!=NO_ERROR)
    {
        strcpy(errbuf, "2:NtQuerySystemInformation() error");
        free(pProcInfo);	
        return -1;
    }

    pProcessInfo = (struct process_info *)pProcInfo;
    while(1)
    {
        TotalProcessCPUUsage += (__int64)pProcessInfo->KernelTime.QuadPart + (__int64)pProcessInfo->UserTime.QuadPart;
        if(pid == pProcessInfo->dwProcessID)
        {
            cpuload = (__int64)pProcessInfo->KernelTime.QuadPart + (__int64)pProcessInfo->UserTime.QuadPart - cpuload;
        }
        if(pProcessInfo->dwOffset == 0)
        {
            break;
        }
        pProcessInfo = (struct process_info *)((byte*)pProcessInfo + pProcessInfo->dwOffset);
    }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -