You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

324 lines
10 KiB

#define __INIT_node_perfctr_provider_IMP
#include "node_counters.h"
#include "node_win32_perfctr_provider.h"
#include <perflib.h>
#include "node_perfctr_provider.h"
typedef ULONG (WINAPI *PerfStartProviderExFunc)(
__in LPGUID ProviderGuid,
__in_opt PPERF_PROVIDER_CONTEXT ProviderContext,
__out PHANDLE Provider);
typedef ULONG (WINAPI *PerfStopProviderFunc)(
__in HANDLE ProviderHandle);
typedef ULONG (WINAPI *PerfSetCounterSetInfoFunc)(
__in HANDLE ProviderHandle,
__inout_bcount(TemplateSize) PPERF_COUNTERSET_INFO Template,
__in ULONG TemplateSize);
typedef PPERF_COUNTERSET_INSTANCE (WINAPI *PerfCreateInstanceFunc)(
__in HANDLE ProviderHandle,
__in LPCGUID CounterSetGuid,
__in PCWSTR Name,
__in ULONG Id);
typedef ULONG (WINAPI *PerfDeleteInstanceFunc)(
__in HANDLE Provider,
__in PPERF_COUNTERSET_INSTANCE InstanceBlock);
typedef ULONG (WINAPI *PerfSetULongCounterValueFunc)(
__in HANDLE Provider,
__inout PPERF_COUNTERSET_INSTANCE Instance,
__in ULONG CounterId,
__in ULONG Value);
typedef ULONG (WINAPI *PerfSetULongLongCounterValueFunc)(
__in HANDLE Provider,
__inout PPERF_COUNTERSET_INSTANCE Instance,
__in ULONG CounterId,
__in ULONGLONG Value);
typedef ULONG (WINAPI *PerfIncrementULongCounterValueFunc)(
__in HANDLE Provider,
__inout PPERF_COUNTERSET_INSTANCE Instance,
__in ULONG CounterId,
__in ULONG Value);
typedef ULONG (WINAPI *PerfIncrementULongLongCounterValueFunc)(
__in HANDLE Provider,
__inout PPERF_COUNTERSET_INSTANCE Instance,
__in ULONG CounterId,
__in ULONGLONG Value);
typedef ULONG (WINAPI *PerfDecrementULongCounterValueFunc)(
__in HANDLE Provider,
__inout PPERF_COUNTERSET_INSTANCE Instance,
__in ULONG CounterId,
__in ULONG Value);
typedef ULONG (WINAPI *PerfDecrementULongLongCounterValueFunc)(
__in HANDLE Provider,
__inout PPERF_COUNTERSET_INSTANCE Instance,
__in ULONG CounterId,
__in ULONGLONG Value);
HMODULE advapimod;
PerfStartProviderExFunc perfctr_startProvider;
PerfStopProviderFunc perfctr_stopProvider;
PerfSetCounterSetInfoFunc perfctr_setCounterSetInfo;
PerfCreateInstanceFunc perfctr_createInstance;
PerfDeleteInstanceFunc perfctr_deleteInstance;
PerfSetULongCounterValueFunc perfctr_setULongValue;
PerfSetULongLongCounterValueFunc perfctr_setULongLongValue;
PerfIncrementULongCounterValueFunc perfctr_incrementULongValue;
PerfIncrementULongLongCounterValueFunc perfctr_incrementULongLongValue;
PerfDecrementULongCounterValueFunc perfctr_decrementULongValue;
PerfDecrementULongLongCounterValueFunc perfctr_decrementULongLongValue;
PPERF_COUNTERSET_INSTANCE perfctr_instance;
#define NODE_COUNTER_HTTP_SERVER_REQUEST 1
#define NODE_COUNTER_HTTP_SERVER_RESPONSE 2
#define NODE_COUNTER_HTTP_CLIENT_REQUEST 3
#define NODE_COUNTER_HTTP_CLIENT_RESPONSE 4
#define NODE_COUNTER_SERVER_CONNS 5
#define NODE_COUNTER_NET_BYTES_SENT 6
#define NODE_COUNTER_NET_BYTES_RECV 7
#define NODE_COUNTER_GC_PERCENTTIME 8
#define NODE_COUNTER_PIPE_BYTES_SENT 9
#define NODE_COUNTER_PIPE_BYTES_RECV 10
namespace node {
EXTERN_C DECLSPEC_SELECTANY HANDLE NodeCounterProvider = nullptr;
void InitPerfCountersWin32() {
ULONG status;
PERF_PROVIDER_CONTEXT providerContext;
// create instance name using pid
#define INST_MAX_LEN 32
#define INST_PREFIX_LEN 5
#define INST_PREFIX L"node_"
wchar_t Inst[INST_MAX_LEN];
DWORD pid = GetCurrentProcessId();
wcscpy_s(Inst, INST_MAX_LEN, INST_PREFIX);
_itow_s(pid, Inst + INST_PREFIX_LEN, INST_MAX_LEN - INST_PREFIX_LEN, 10);
advapimod = LoadLibraryW(L"advapi32.dll");
if (advapimod) {
perfctr_startProvider = (PerfStartProviderExFunc)
GetProcAddress(advapimod, "PerfStartProviderEx");
perfctr_stopProvider = (PerfStopProviderFunc)
GetProcAddress(advapimod, "PerfStopProvider");
perfctr_setCounterSetInfo = (PerfSetCounterSetInfoFunc)
GetProcAddress(advapimod, "PerfSetCounterSetInfo");
perfctr_createInstance = (PerfCreateInstanceFunc)
GetProcAddress(advapimod, "PerfCreateInstance");
perfctr_deleteInstance = (PerfDeleteInstanceFunc)
GetProcAddress(advapimod, "PerfDeleteInstance");
perfctr_setULongValue = (PerfSetULongCounterValueFunc)
GetProcAddress(advapimod, "PerfSetULongCounterValue");
perfctr_setULongLongValue = (PerfSetULongLongCounterValueFunc)
GetProcAddress(advapimod, "PerfSetULongLongCounterValue");
perfctr_incrementULongValue = (PerfIncrementULongCounterValueFunc)
GetProcAddress(advapimod, "PerfIncrementULongCounterValue");
perfctr_incrementULongLongValue = (PerfIncrementULongLongCounterValueFunc)
GetProcAddress(advapimod, "PerfIncrementULongLongCounterValue");
perfctr_decrementULongValue = (PerfDecrementULongCounterValueFunc)
GetProcAddress(advapimod, "PerfDecrementULongCounterValue");
perfctr_decrementULongLongValue = (PerfDecrementULongLongCounterValueFunc)
GetProcAddress(advapimod, "PerfDecrementULongLongCounterValue");
ZeroMemory(&providerContext, sizeof(providerContext));
providerContext.ContextSize = sizeof(providerContext);
if (!perfctr_startProvider ||
!perfctr_setCounterSetInfo ||
!perfctr_createInstance) {
NodeCounterProvider = nullptr;
return;
}
status = perfctr_startProvider(&NodeCounterSetGuid,
&providerContext,
&NodeCounterProvider);
if (status != ERROR_SUCCESS) {
NodeCounterProvider = nullptr;
return;
}
status = perfctr_setCounterSetInfo(NodeCounterProvider,
&NodeCounterSetInfo.CounterSet,
sizeof(NodeCounterSetInfo));
if (status != ERROR_SUCCESS) {
perfctr_stopProvider(NodeCounterProvider);
NodeCounterProvider = nullptr;
return;
}
perfctr_instance = perfctr_createInstance(NodeCounterProvider,
&NodeCounterSetGuid,
Inst,
1);
if (perfctr_instance == nullptr) {
perfctr_stopProvider(NodeCounterProvider);
NodeCounterProvider = nullptr;
}
}
}
void TermPerfCountersWin32() {
if (NodeCounterProvider != nullptr &&
perfctr_stopProvider != nullptr) {
perfctr_stopProvider(NodeCounterProvider);
NodeCounterProvider = nullptr;
}
if (advapimod) {
FreeLibrary(advapimod);
advapimod = nullptr;
}
}
void NODE_COUNT_HTTP_SERVER_REQUEST() {
if (NodeCounterProvider != nullptr &&
perfctr_incrementULongValue != nullptr) {
perfctr_incrementULongValue(NodeCounterProvider,
perfctr_instance,
NODE_COUNTER_HTTP_SERVER_REQUEST,
1);
}
}
void NODE_COUNT_HTTP_SERVER_RESPONSE() {
if (NodeCounterProvider != nullptr &&
perfctr_incrementULongValue != nullptr) {
perfctr_incrementULongValue(NodeCounterProvider,
perfctr_instance,
NODE_COUNTER_HTTP_SERVER_RESPONSE,
1);
}
}
void NODE_COUNT_HTTP_CLIENT_REQUEST() {
if (NodeCounterProvider != nullptr &&
perfctr_incrementULongValue != nullptr) {
perfctr_incrementULongValue(NodeCounterProvider,
perfctr_instance,
NODE_COUNTER_HTTP_CLIENT_REQUEST,
1);
}
}
void NODE_COUNT_HTTP_CLIENT_RESPONSE() {
if (NodeCounterProvider != nullptr &&
perfctr_incrementULongValue != nullptr) {
perfctr_incrementULongValue(NodeCounterProvider,
perfctr_instance,
NODE_COUNTER_HTTP_CLIENT_RESPONSE,
1);
}
}
void NODE_COUNT_SERVER_CONN_OPEN() {
if (NodeCounterProvider != nullptr &&
perfctr_incrementULongValue != nullptr) {
perfctr_incrementULongValue(NodeCounterProvider,
perfctr_instance,
NODE_COUNTER_SERVER_CONNS,
1);
}
}
void NODE_COUNT_SERVER_CONN_CLOSE() {
if (NodeCounterProvider != nullptr &&
perfctr_decrementULongValue != nullptr) {
perfctr_decrementULongValue(NodeCounterProvider,
perfctr_instance,
NODE_COUNTER_SERVER_CONNS,
1);
}
}
void NODE_COUNT_NET_BYTES_SENT(int bytes) {
if (NodeCounterProvider != nullptr &&
perfctr_incrementULongLongValue != nullptr) {
perfctr_incrementULongLongValue(NodeCounterProvider,
perfctr_instance,
NODE_COUNTER_NET_BYTES_SENT,
static_cast<ULONGLONG>(bytes));
}
}
void NODE_COUNT_NET_BYTES_RECV(int bytes) {
if (NodeCounterProvider != nullptr &&
perfctr_incrementULongLongValue != nullptr) {
perfctr_incrementULongLongValue(NodeCounterProvider,
perfctr_instance,
NODE_COUNTER_NET_BYTES_RECV,
static_cast<ULONGLONG>(bytes));
}
}
uint64_t NODE_COUNT_GET_GC_RAWTIME() {
LARGE_INTEGER timegc;
if (QueryPerformanceCounter(&timegc)) {
return timegc.QuadPart;
} else {
return static_cast<uint64_t>(GetTickCount());
}
}
void NODE_COUNT_GC_PERCENTTIME(unsigned int percent) {
if (NodeCounterProvider != nullptr && perfctr_setULongValue != nullptr) {
perfctr_setULongValue(NodeCounterProvider,
perfctr_instance,
NODE_COUNTER_GC_PERCENTTIME,
percent);
}
}
void NODE_COUNT_PIPE_BYTES_SENT(int bytes) {
if (NodeCounterProvider != nullptr &&
perfctr_incrementULongLongValue != nullptr) {
perfctr_incrementULongLongValue(NodeCounterProvider,
perfctr_instance,
NODE_COUNTER_PIPE_BYTES_SENT,
static_cast<ULONGLONG>(bytes));
}
}
void NODE_COUNT_PIPE_BYTES_RECV(int bytes) {
if (NodeCounterProvider != nullptr &&
perfctr_incrementULongLongValue != nullptr) {
perfctr_incrementULongLongValue(NodeCounterProvider,
perfctr_instance,
NODE_COUNTER_PIPE_BYTES_RECV,
static_cast<ULONGLONG>(bytes));
}
}
} // namespace node