#pragma once #include #include // Missing from of MinGW-w64 SDK #define PERF_WILDCARD_COUNTER 0xFFFFFFFF #define PERF_WILDCARD_INSTANCE L"*" #define PERF_AGGREGATE_INSTANCE L"_Total" #define PERF_MAX_INSTANCE_NAME 1024 typedef struct _PERF_INSTANCE_HEADER { ULONG Size; // = sizeof(PERF_INSTANCE_HEADER) + sizeof(InstanceName) + sizeof(Padding) ULONG InstanceId; // Instance ID. // Followed by: // WCHAR InstanceName[]; // Nul-terminated. // WCHAR Padding[]; // Pad to a multiple of 8 bytes } PERF_INSTANCE_HEADER, *PPERF_INSTANCE_HEADER; typedef struct _PERF_COUNTER_IDENTIFIER { GUID CounterSetGuid; // The GUID of the counterset. ULONG Status; // Win32 error code indicating success/failure of the add/delete operation. ULONG Size; // sizeof(PERF_COUNTER_IDENTIFIER) + sizeof(InstanceName) + sizeof(Padding) ULONG CounterId; // CounterId, or PERF_WILDCARD_COUNTER for all counters. ULONG InstanceId; // InstanceId, or 0xFFFFFFFF to not filter on instance ID. ULONG Index; // Set by PerfQueryCounterInfo to the position in which the corresponding counter data is returned. ULONG Reserved; // Reserved. // Followed by: // WCHAR InstanceName[]; // WCHAR Padding[]; } PERF_COUNTER_IDENTIFIER, *PPERF_COUNTER_IDENTIFIER; typedef struct _PERF_DATA_HEADER { ULONG dwTotalSize; // = sizeof(PERF_DATA_HEADER) + sizeof(PERF_COUNTER_HEADER blocks...) ULONG dwNumCounters; // The number of PERF_COUNTER_HEADER blocks. LONGLONG PerfTimeStamp; // Timestamp from a high-resolution clock. LONGLONG PerfTime100NSec; // The number of 100 nanosecond intervals since January 1, 1601, in Coordinated Universal Time (UTC). LONGLONG PerfFreq; // The frequency of a high-resolution clock. SYSTEMTIME SystemTime; // The time at which data is collected on the provider side. // Followed by: // PERF_COUNTER_HEADER blocks...; } PERF_DATA_HEADER, *PPERF_DATA_HEADER; typedef enum _PerfCounterDataType { PERF_ERROR_RETURN = 0, /* An error occurred when the performance counter value was queried. */ PERF_SINGLE_COUNTER = 1, /* Query returned a single counter from a single-instance. */ PERF_MULTIPLE_COUNTERS = 2, /* Query returned multiple counters from a single instance. */ PERF_MULTIPLE_INSTANCES = 4, /* Query returned a single counter from each of multiple instances. */ PERF_COUNTERSET = 6 /* Query returned multiple counters from each of multiple instances. */ } PerfCounterDataType; typedef struct _PERF_COUNTER_HEADER { ULONG dwStatus; // Win32 error code indicating success/failure of the query operation. PerfCounterDataType dwType; // Result type - error, single/single, multi/single, single/multi, multi/multi. ULONG dwSize; // = sizeof(PERF_COUNTER_HEADER) + sizeof(Additional data) ULONG Reserved; // Reserved. // Followed by additional data: // If dwType == PERF_ERROR_RETURN: nothing. // If dwType == PERF_SINGLE_COUNTER: PERF_COUNTER_DATA block. // If dwType == PERF_MULTIPLE_COUNTERS: PERF_MULTI_COUNTERS block + PERF_COUNTER_DATA blocks. // If dwType == PERF_MULTIPLE_INSTANCES: PERF_MULTI_INSTANCES block. // If dwType == PERF_COUNTERSET: PERF_MULTI_COUNTERS block + PERF_MULTI_INSTANCES block. } PERF_COUNTER_HEADER, *PPERF_COUNTER_HEADER; typedef struct _PERF_MULTI_INSTANCES { ULONG dwTotalSize; // = sizeof(PERF_MULTI_INSTANCES) + sizeof(instance data blocks...) ULONG dwInstances; // Number of instance data blocks. // Followed by: // Instance data blocks...; } PERF_MULTI_INSTANCES, *PPERF_MULTI_INSTANCES; typedef struct _PERF_MULTI_COUNTERS { ULONG dwSize; // sizeof(PERF_MULTI_COUNTERS) + sizeof(CounterIds) ULONG dwCounters; // Number of counter ids. // Followed by: // DWORD CounterIds[dwCounters]; } PERF_MULTI_COUNTERS, *PPERF_MULTI_COUNTERS; typedef struct _PERF_COUNTER_DATA { ULONG dwDataSize; // Size of the counter data, in bytes. ULONG dwSize; // = sizeof(PERF_COUNTER_DATA) + sizeof(Data) + sizeof(Padding) // Followed by: // BYTE Data[dwDataSize]; // BYTE Padding[]; } PERF_COUNTER_DATA, *PPERF_COUNTER_DATA; _Success_(return == ERROR_SUCCESS) ULONG WINAPI PerfEnumerateCounterSetInstances( _In_opt_z_ LPCWSTR szMachine, _In_ LPCGUID pCounterSetId, _Out_opt_bytecap_post_bytecount_(cbInstances, *pcbInstancesActual) PPERF_INSTANCE_HEADER pInstances, DWORD cbInstances, _Out_ LPDWORD pcbInstancesActual); _Success_(return == ERROR_SUCCESS) ULONG WINAPI PerfOpenQueryHandle( _In_opt_z_ LPCWSTR szMachine, _Out_ HANDLE* phQuery); _Success_(return == ERROR_SUCCESS) ULONG WINAPI PerfCloseQueryHandle( _In_ HANDLE hQuery); _Success_(return == ERROR_SUCCESS) ULONG WINAPI PerfAddCounters( _In_ HANDLE hQuery, _Inout_bytecount_(cbCounters) PPERF_COUNTER_IDENTIFIER pCounters, DWORD cbCounters); _Success_(return == ERROR_SUCCESS) ULONG WINAPI PerfDeleteCounters( _In_ HANDLE hQuery, _Inout_bytecount_(cbCounters) PPERF_COUNTER_IDENTIFIER pCounters, DWORD cbCounters); _Success_(return == ERROR_SUCCESS) ULONG WINAPI PerfQueryCounterData( _In_ HANDLE hQuery, _Out_opt_bytecap_post_bytecount_(cbCounterBlock, *pcbCounterBlockActual) PPERF_DATA_HEADER pCounterBlock, DWORD cbCounterBlock, _Out_ LPDWORD pcbCounterBlockActual);