25 #define WM_PING_UPDATE (WM_APP + 151)
27 static RECT NormalGraphTextMargin = { 5, 5, 5, 5 };
28 static RECT NormalGraphTextPadding = { 3, 3, 3, 3 };
30 static HFONT InitializeFont(
35 NONCLIENTMETRICS metrics = {
sizeof(NONCLIENTMETRICS) };
37 if (SystemParametersInfo(SPI_GETNONCLIENTMETRICS, 0, &metrics, 0))
39 metrics.lfMessageFont.lfHeight = -15;
43 fontHandle = CreateFontIndirect(&metrics.lfMessageFont);
49 GetObject((HFONT)GetStockObject(DEFAULT_GUI_FONT),
sizeof(LOGFONT), &font);
52 font.lfWeight = FW_MEDIUM;
54 fontHandle = CreateFontIndirect(&font);
57 SendMessage(hwnd, WM_SETFONT, (WPARAM)fontHandle,
TRUE);
62 static VOID PhNetworkPingUpdateGraph(
66 Context->PingGraphState.Valid =
FALSE;
67 Context->PingGraphState.TooltipIndex = -1;
71 InvalidateRect(Context->PingGraphHandle, NULL,
FALSE);
81 _In_ _Printf_format_string_ PSTR Format,
88 length = _vscprintf(Format, ArgPtr);
110 _In_ _Printf_format_string_ PSTR Format,
116 va_start(argptr, Format);
118 return PhFormatAnsiString_V(Format, argptr);
121 static ULONG PhNetworkPingThreadStart(
125 HANDLE icmpHandle = INVALID_HANDLE_VALUE;
126 ULONG icmpCurrentPingMs = 0;
127 ULONG icmpCurrentPingTtl = 0;
128 ULONG icmpReplyCount = 0;
129 ULONG icmpReplyLength = 0;
130 PVOID icmpReplyBuffer = NULL;
133 IP_OPTION_INFORMATION pingOptions =
150 if ((icmpEchoBuffer = PhFormatAnsiString(
"processhacker_%S_0x0D06F00D_x1", phVersion->
Buffer)) == NULL)
155 SOCKADDR_IN6 icmp6LocalAddr = { 0 };
156 SOCKADDR_IN6 icmp6RemoteAddr = { 0 };
157 PICMPV6_ECHO_REPLY icmp6ReplyStruct = NULL;
160 if ((icmpHandle = Icmp6CreateFile()) == INVALID_HANDLE_VALUE)
164 icmp6LocalAddr.sin6_addr = in6addr_any;
165 icmp6LocalAddr.sin6_family = AF_INET6;
172 icmpReplyLength =
ICMP_BUFFER_SIZE(
sizeof(ICMPV6_ECHO_REPLY), icmpEchoBuffer);
173 icmpReplyBuffer = PhAllocate(icmpReplyLength);
174 memset(icmpReplyBuffer, 0, icmpReplyLength);
179 icmpReplyCount = Icmp6SendEcho2(
187 (USHORT)icmpEchoBuffer->
Length,
194 icmp6ReplyStruct = (PICMPV6_ECHO_REPLY)icmpReplyBuffer;
195 if (icmpReplyCount > 0 && icmp6ReplyStruct)
197 BOOLEAN icmpPacketSignature =
FALSE;
199 if (icmp6ReplyStruct->Status != IP_SUCCESS)
205 icmp6ReplyStruct->Address.sin6_addr,
207 sizeof(icmp6ReplyStruct->Address.sin6_addr)
227 icmpCurrentPingMs = icmp6ReplyStruct->RoundTripTime;
237 IPAddr icmpLocalAddr = 0;
238 IPAddr icmpRemoteAddr = 0;
239 PICMP_ECHO_REPLY icmpReplyStruct = NULL;
242 if ((icmpHandle = IcmpCreateFile()) == INVALID_HANDLE_VALUE)
246 icmpLocalAddr = in4addr_any.s_addr;
252 icmpReplyLength =
ICMP_BUFFER_SIZE(
sizeof(ICMP_ECHO_REPLY), icmpEchoBuffer);
253 icmpReplyBuffer = PhAllocate(icmpReplyLength);
254 memset(icmpReplyBuffer, 0, icmpReplyLength);
278 icmpReplyCount = IcmpSendEcho2(
285 (USHORT)icmpEchoBuffer->
Length,
292 icmpReplyStruct = (PICMP_ECHO_REPLY)icmpReplyBuffer;
294 if (icmpReplyStruct && icmpReplyCount > 0)
296 BOOLEAN icmpPacketSignature =
FALSE;
298 if (icmpReplyStruct->Status != IP_SUCCESS)
308 if (icmpReplyStruct->DataSize == icmpEchoBuffer->
Length)
310 icmpPacketSignature = (_memicmp(
312 icmpReplyStruct->Data,
313 icmpReplyStruct->DataSize
317 icmpCurrentPingMs = icmpReplyStruct->RoundTripTime;
318 icmpCurrentPingTtl = icmpReplyStruct->Options.Ttl;
320 if (!icmpPacketSignature)
333 if (context->
PingMinMs == 0 || icmpCurrentPingMs < context->PingMinMs)
335 if (icmpCurrentPingMs > context->
PingMaxMs)
340 PhAddItemCircularBuffer_ULONG(&context->
PingHistory, icmpCurrentPingMs);
354 if (icmpHandle != INVALID_HANDLE_VALUE)
356 IcmpCloseHandle(icmpHandle);
367 return STATUS_SUCCESS;
370 static VOID NTAPI NetworkPingUpdateHandler(
371 _In_opt_ PVOID Parameter,
372 _In_opt_ PVOID Context
380 PhNetworkPingThreadStart,
385 static INT_PTR CALLBACK NetworkPingWndProc(
394 if (uMsg == WM_INITDIALOG)
397 SetProp(hwndDlg, L
"Context", (HANDLE)context);
435 WS_VISIBLE | WS_CHILD | WS_BORDER,
449 GetModuleHandle(NULL),
450 MAKEINTRESOURCE(PHAPP_IDI_PROCESSHACKER),
452 GetSystemMetrics(SM_CXICON),
453 GetSystemMetrics(SM_CYICON),
458 SendMessage(hwndDlg, WM_SETICON, ICON_SMALL, (LPARAM)context->
IconHandle);
504 NetworkPingUpdateHandler,
512 switch (LOWORD(wParam))
547 RemoveProp(hwndDlg, L
"Context");
559 case WM_CTLCOLORSTATIC:
561 HDC hDC = (HDC)wParam;
562 HWND hwndChild = (HWND)lParam;
567 SetTextColor(hDC, RGB(19, 112, 171));
571 SetBkMode(hDC, TRANSPARENT);
574 return (INT_PTR)GetSysColorBrush(COLOR_WINDOW);
580 ULONG maxGraphHeight = 0;
581 ULONG pingAvgValue = 0;
583 PhNetworkPingUpdateGraph(context);
587 maxGraphHeight = maxGraphHeight + PhGetItemCircularBuffer_ULONG(&context->
PingHistory, i);
588 pingAvgValue = maxGraphHeight / context->
PingHistory.Count;
592 L
"Average: %lums", pingAvgValue)->Buffer);
613 LPNMHDR header = (LPNMHDR)lParam;
615 switch (header->code)
690 ULONG pingMs = PhGetItemCircularBuffer_ULONG(&context->
PingHistory, getTooltipText->
Index);
722 windowHandle = CreateDialogParam(
730 ShowWindow(windowHandle, SW_SHOW);
731 SetForegroundWindow(windowHandle);
733 while (result = GetMessage(&message, NULL, 0, 0))
738 if (!IsDialogMessage(windowHandle, &message))
740 TranslateMessage(&message);
741 DispatchMessage(&message);
748 DestroyWindow(windowHandle);
750 return STATUS_SUCCESS;