Node.js  v8.x
Node.js is a JavaScript runtime built on Chrome's V8 JavaScript engine
node_win32_perfctr_provider.cc
Go to the documentation of this file.
1 // Copyright Joyent, Inc. and other Node contributors.
2 //
3 // Permission is hereby granted, free of charge, to any person obtaining a
4 // copy of this software and associated documentation files (the
5 // "Software"), to deal in the Software without restriction, including
6 // without limitation the rights to use, copy, modify, merge, publish,
7 // distribute, sublicense, and/or sell copies of the Software, and to permit
8 // persons to whom the Software is furnished to do so, subject to the
9 // following conditions:
10 //
11 // The above copyright notice and this permission notice shall be included
12 // in all copies or substantial portions of the Software.
13 //
14 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
15 // OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN
17 // NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
18 // DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
19 // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
20 // USE OR OTHER DEALINGS IN THE SOFTWARE.
21 
22 #define __INIT_node_perfctr_provider_IMP
23 #include "node_counters.h"
25 
26 #include <perflib.h>
27 
28 #include "node_perfctr_provider.h"
29 
30 
31 typedef ULONG (WINAPI *PerfStartProviderExFunc)(
32  __in LPGUID ProviderGuid,
33  __in_opt PPERF_PROVIDER_CONTEXT ProviderContext,
34  __out PHANDLE Provider);
35 
36 typedef ULONG (WINAPI *PerfStopProviderFunc)(
37  __in HANDLE ProviderHandle);
38 
39 typedef ULONG (WINAPI *PerfSetCounterSetInfoFunc)(
40  __in HANDLE ProviderHandle,
41  __inout_bcount(TemplateSize) PPERF_COUNTERSET_INFO Template,
42  __in ULONG TemplateSize);
43 
44 typedef PPERF_COUNTERSET_INSTANCE (WINAPI *PerfCreateInstanceFunc)(
45  __in HANDLE ProviderHandle,
46  __in LPCGUID CounterSetGuid,
47  __in PCWSTR Name,
48  __in ULONG Id);
49 
50 typedef ULONG (WINAPI *PerfDeleteInstanceFunc)(
51  __in HANDLE Provider,
52  __in PPERF_COUNTERSET_INSTANCE InstanceBlock);
53 
54 typedef ULONG (WINAPI *PerfSetULongCounterValueFunc)(
55  __in HANDLE Provider,
56  __inout PPERF_COUNTERSET_INSTANCE Instance,
57  __in ULONG CounterId,
58  __in ULONG Value);
59 
60 typedef ULONG (WINAPI *PerfSetULongLongCounterValueFunc)(
61  __in HANDLE Provider,
62  __inout PPERF_COUNTERSET_INSTANCE Instance,
63  __in ULONG CounterId,
64  __in ULONGLONG Value);
65 
66 typedef ULONG (WINAPI *PerfIncrementULongCounterValueFunc)(
67  __in HANDLE Provider,
68  __inout PPERF_COUNTERSET_INSTANCE Instance,
69  __in ULONG CounterId,
70  __in ULONG Value);
71 
73  __in HANDLE Provider,
74  __inout PPERF_COUNTERSET_INSTANCE Instance,
75  __in ULONG CounterId,
76  __in ULONGLONG Value);
77 
78 typedef ULONG (WINAPI *PerfDecrementULongCounterValueFunc)(
79  __in HANDLE Provider,
80  __inout PPERF_COUNTERSET_INSTANCE Instance,
81  __in ULONG CounterId,
82  __in ULONG Value);
83 
85  __in HANDLE Provider,
86  __inout PPERF_COUNTERSET_INSTANCE Instance,
87  __in ULONG CounterId,
88  __in ULONGLONG Value);
89 
90 
91 HMODULE advapimod;
103 
104 PPERF_COUNTERSET_INSTANCE perfctr_instance;
105 
106 
107 #define NODE_COUNTER_HTTP_SERVER_REQUEST 1
108 #define NODE_COUNTER_HTTP_SERVER_RESPONSE 2
109 #define NODE_COUNTER_HTTP_CLIENT_REQUEST 3
110 #define NODE_COUNTER_HTTP_CLIENT_RESPONSE 4
111 #define NODE_COUNTER_SERVER_CONNS 5
112 #define NODE_COUNTER_NET_BYTES_SENT 6
113 #define NODE_COUNTER_NET_BYTES_RECV 7
114 #define NODE_COUNTER_GC_PERCENTTIME 8
115 #define NODE_COUNTER_PIPE_BYTES_SENT 9
116 #define NODE_COUNTER_PIPE_BYTES_RECV 10
117 
118 
119 namespace node {
120 
121 
122 EXTERN_C DECLSPEC_SELECTANY HANDLE NodeCounterProvider = nullptr;
123 
125  ULONG status;
126  PERF_PROVIDER_CONTEXT providerContext;
127 
128  // create instance name using pid
129 #define INST_MAX_LEN 32
130 #define INST_PREFIX_LEN 5
131 #define INST_PREFIX L"node_"
132 
133  wchar_t Inst[INST_MAX_LEN];
134  DWORD pid = GetCurrentProcessId();
135  wcscpy_s(Inst, INST_MAX_LEN, INST_PREFIX);
136  _itow_s(pid, Inst + INST_PREFIX_LEN, INST_MAX_LEN - INST_PREFIX_LEN, 10);
137 
138  advapimod = LoadLibraryW(L"advapi32.dll");
139  if (advapimod) {
141  GetProcAddress(advapimod, "PerfStartProviderEx");
143  GetProcAddress(advapimod, "PerfStopProvider");
145  GetProcAddress(advapimod, "PerfSetCounterSetInfo");
147  GetProcAddress(advapimod, "PerfCreateInstance");
149  GetProcAddress(advapimod, "PerfDeleteInstance");
151  GetProcAddress(advapimod, "PerfSetULongCounterValue");
153  GetProcAddress(advapimod, "PerfSetULongLongCounterValue");
155  GetProcAddress(advapimod, "PerfIncrementULongCounterValue");
157  GetProcAddress(advapimod, "PerfIncrementULongLongCounterValue");
159  GetProcAddress(advapimod, "PerfDecrementULongCounterValue");
161  GetProcAddress(advapimod, "PerfDecrementULongLongCounterValue");
162 
163  ZeroMemory(&providerContext, sizeof(providerContext));
164  providerContext.ContextSize = sizeof(providerContext);
165 
166  if (!perfctr_startProvider ||
169  NodeCounterProvider = nullptr;
170  return;
171  }
172 
173  status = perfctr_startProvider(&NodeCounterSetGuid,
174  &providerContext,
175  &NodeCounterProvider);
176  if (status != ERROR_SUCCESS) {
177  NodeCounterProvider = nullptr;
178  return;
179  }
180 
181  status = perfctr_setCounterSetInfo(NodeCounterProvider,
182  &NodeCounterSetInfo.CounterSet,
183  sizeof(NodeCounterSetInfo));
184  if (status != ERROR_SUCCESS) {
185  perfctr_stopProvider(NodeCounterProvider);
186  NodeCounterProvider = nullptr;
187  return;
188  }
189 
190  perfctr_instance = perfctr_createInstance(NodeCounterProvider,
191  &NodeCounterSetGuid,
192  Inst,
193  1);
194  if (perfctr_instance == nullptr) {
195  perfctr_stopProvider(NodeCounterProvider);
196  NodeCounterProvider = nullptr;
197  }
198  }
199 }
200 
201 
203  if (NodeCounterProvider != nullptr &&
204  perfctr_stopProvider != nullptr) {
205  perfctr_stopProvider(NodeCounterProvider);
206  NodeCounterProvider = nullptr;
207  }
208 
209  if (advapimod) {
210  FreeLibrary(advapimod);
211  advapimod = nullptr;
212  }
213 }
214 
215 
217  if (NodeCounterProvider != nullptr &&
218  perfctr_incrementULongValue != nullptr) {
219  perfctr_incrementULongValue(NodeCounterProvider,
222  1);
223  }
224 }
225 
226 
228  if (NodeCounterProvider != nullptr &&
229  perfctr_incrementULongValue != nullptr) {
230  perfctr_incrementULongValue(NodeCounterProvider,
233  1);
234  }
235 }
236 
237 
239  if (NodeCounterProvider != nullptr &&
240  perfctr_incrementULongValue != nullptr) {
241  perfctr_incrementULongValue(NodeCounterProvider,
244  1);
245  }
246 }
247 
248 
250  if (NodeCounterProvider != nullptr &&
251  perfctr_incrementULongValue != nullptr) {
252  perfctr_incrementULongValue(NodeCounterProvider,
255  1);
256  }
257 }
258 
259 
261  if (NodeCounterProvider != nullptr &&
262  perfctr_incrementULongValue != nullptr) {
263  perfctr_incrementULongValue(NodeCounterProvider,
266  1);
267  }
268 }
269 
270 
272  if (NodeCounterProvider != nullptr &&
273  perfctr_decrementULongValue != nullptr) {
274  perfctr_decrementULongValue(NodeCounterProvider,
277  1);
278  }
279 }
280 
281 
282 void NODE_COUNT_NET_BYTES_SENT(int bytes) {
283  if (NodeCounterProvider != nullptr &&
284  perfctr_incrementULongLongValue != nullptr) {
285  perfctr_incrementULongLongValue(NodeCounterProvider,
288  static_cast<ULONGLONG>(bytes));
289  }
290 }
291 
292 
293 void NODE_COUNT_NET_BYTES_RECV(int bytes) {
294  if (NodeCounterProvider != nullptr &&
295  perfctr_incrementULongLongValue != nullptr) {
296  perfctr_incrementULongLongValue(NodeCounterProvider,
299  static_cast<ULONGLONG>(bytes));
300  }
301 }
302 
303 
305  LARGE_INTEGER timegc;
306  if (QueryPerformanceCounter(&timegc)) {
307  return timegc.QuadPart;
308  } else {
309  return static_cast<uint64_t>(GetTickCount());
310  }
311 }
312 
313 
314 void NODE_COUNT_GC_PERCENTTIME(unsigned int percent) {
315  if (NodeCounterProvider != nullptr && perfctr_setULongValue != nullptr) {
316  perfctr_setULongValue(NodeCounterProvider,
319  percent);
320  }
321 }
322 
323 
324 void NODE_COUNT_PIPE_BYTES_SENT(int bytes) {
325  if (NodeCounterProvider != nullptr &&
326  perfctr_incrementULongLongValue != nullptr) {
327  perfctr_incrementULongLongValue(NodeCounterProvider,
330  static_cast<ULONGLONG>(bytes));
331  }
332 }
333 
334 
335 void NODE_COUNT_PIPE_BYTES_RECV(int bytes) {
336  if (NodeCounterProvider != nullptr &&
337  perfctr_incrementULongLongValue != nullptr) {
338  perfctr_incrementULongLongValue(NodeCounterProvider,
341  static_cast<ULONGLONG>(bytes));
342  }
343 }
344 
345 } // namespace node
ULONG(WINAPI * PerfDecrementULongLongCounterValueFunc)(__in HANDLE Provider, __inout PPERF_COUNTERSET_INSTANCE Instance, __in ULONG CounterId, __in ULONGLONG Value)
void NODE_COUNT_HTTP_SERVER_RESPONSE()
#define NODE_COUNTER_HTTP_CLIENT_RESPONSE
PerfIncrementULongLongCounterValueFunc perfctr_incrementULongLongValue
PerfSetULongCounterValueFunc perfctr_setULongValue
void NODE_COUNT_NET_BYTES_SENT(int bytes)
PPERF_COUNTERSET_INSTANCE(WINAPI * PerfCreateInstanceFunc)(__in HANDLE ProviderHandle, __in LPCGUID CounterSetGuid, __in PCWSTR Name, __in ULONG Id)
ULONG(WINAPI * PerfSetULongCounterValueFunc)(__in HANDLE Provider, __inout PPERF_COUNTERSET_INSTANCE Instance, __in ULONG CounterId, __in ULONG Value)
ULONG(WINAPI * PerfSetCounterSetInfoFunc)(__in HANDLE ProviderHandle, __inout_bcount(TemplateSize) PPERF_COUNTERSET_INFO Template, __in ULONG TemplateSize)
#define NODE_COUNTER_NET_BYTES_RECV
ULONG(WINAPI * PerfDeleteInstanceFunc)(__in HANDLE Provider, __in PPERF_COUNTERSET_INSTANCE InstanceBlock)
void NODE_COUNT_PIPE_BYTES_SENT(int bytes)
void NODE_COUNT_SERVER_CONN_OPEN()
#define INST_PREFIX
PerfDeleteInstanceFunc perfctr_deleteInstance
void NODE_COUNT_HTTP_CLIENT_RESPONSE()
PPERF_COUNTERSET_INSTANCE perfctr_instance
#define NODE_COUNTER_HTTP_SERVER_RESPONSE
int status
Definition: cares_wrap.cc:479
void NODE_COUNT_HTTP_SERVER_REQUEST()
void NODE_COUNT_SERVER_CONN_CLOSE()
#define INST_MAX_LEN
ULONG(WINAPI * PerfStopProviderFunc)(__in HANDLE ProviderHandle)
#define NODE_COUNTER_HTTP_SERVER_REQUEST
HMODULE advapimod
#define NODE_COUNTER_GC_PERCENTTIME
ULONG(WINAPI * PerfIncrementULongCounterValueFunc)(__in HANDLE Provider, __inout PPERF_COUNTERSET_INSTANCE Instance, __in ULONG CounterId, __in ULONG Value)
PerfStopProviderFunc perfctr_stopProvider
PerfIncrementULongCounterValueFunc perfctr_incrementULongValue
#define NODE_COUNTER_SERVER_CONNS
PerfSetULongLongCounterValueFunc perfctr_setULongLongValue
void NODE_COUNT_NET_BYTES_RECV(int bytes)
ULONG(WINAPI * PerfDecrementULongCounterValueFunc)(__in HANDLE Provider, __inout PPERF_COUNTERSET_INSTANCE Instance, __in ULONG CounterId, __in ULONG Value)
PerfDecrementULongCounterValueFunc perfctr_decrementULongValue
PerfDecrementULongLongCounterValueFunc perfctr_decrementULongLongValue
ULONG(WINAPI * PerfIncrementULongLongCounterValueFunc)(__in HANDLE Provider, __inout PPERF_COUNTERSET_INSTANCE Instance, __in ULONG CounterId, __in ULONGLONG Value)
void NODE_COUNT_GC_PERCENTTIME(unsigned int percent)
EXTERN_C DECLSPEC_SELECTANY HANDLE NodeCounterProvider
#define NODE_COUNTER_PIPE_BYTES_RECV
ULONG(WINAPI * PerfSetULongLongCounterValueFunc)(__in HANDLE Provider, __inout PPERF_COUNTERSET_INSTANCE Instance, __in ULONG CounterId, __in ULONGLONG Value)
PerfSetCounterSetInfoFunc perfctr_setCounterSetInfo
#define NODE_COUNTER_PIPE_BYTES_SENT
void NODE_COUNT_PIPE_BYTES_RECV(int bytes)
PerfCreateInstanceFunc perfctr_createInstance
uint64_t NODE_COUNT_GET_GC_RAWTIME()
#define NODE_COUNTER_NET_BYTES_SENT
ULONG(WINAPI * PerfStartProviderExFunc)(__in LPGUID ProviderGuid, __in_opt PPERF_PROVIDER_CONTEXT ProviderContext, __out PHANDLE Provider)
void NODE_COUNT_HTTP_CLIENT_REQUEST()
#define NODE_COUNTER_HTTP_CLIENT_REQUEST
#define INST_PREFIX_LEN
PerfStartProviderExFunc perfctr_startProvider