Source code of Windows XP (NT5)
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.

1178 lines
34 KiB

  1. /******************************************************************************
  2. P V I E W D A T A
  3. Name: pviewdat.c
  4. Description:
  5. This module collects the data to be displayed in pview.
  6. ******************************************************************************/
  7. #include <windows.h>
  8. #include <winperf.h>
  9. #include "perfdata.h"
  10. #include "pviewdat.h"
  11. #include "pviewdlg.h"
  12. #include <stdio.h>
  13. #include <stdlib.h>
  14. #include <string.h>
  15. #include <tchar.h>
  16. #define NODATA TEXT("--------")
  17. void FormatTimeFields
  18. (double fTime,
  19. PTIME_FIELD pTimeFld);
  20. DWORD PutCounterDWKB
  21. (HWND hWnd,
  22. DWORD dwItemID,
  23. PPERF_INSTANCE pInst,
  24. PPERF_OBJECT pObj,
  25. DWORD dwCounterIdx);
  26. DWORD PutCounterHEX
  27. (HWND hWnd,
  28. DWORD dwItemID,
  29. PPERF_INSTANCE pInst,
  30. PPERF_OBJECT pObj,
  31. DWORD dwCounterIdx);
  32. DWORD PutCounterDW
  33. (HWND hWnd,
  34. DWORD dwItemID,
  35. PPERF_INSTANCE pInst,
  36. PPERF_OBJECT pObj,
  37. DWORD dwCounterIdx);
  38. void PaintAddressSpace
  39. (HWND hMemDlg,
  40. PPERF_INSTANCE pInst,
  41. PPERF_OBJECT pObj,
  42. DWORD TotalID,
  43. DWORD NoAccessID,
  44. DWORD NoAccessIndex,
  45. DWORD ReadOnlyID,
  46. DWORD ReadOnlyIndex,
  47. DWORD ReadWriteID,
  48. DWORD ReadWriteIndex,
  49. DWORD WriteCopyID,
  50. DWORD WriteCopyIndex,
  51. DWORD ExecuteID,
  52. DWORD ExecuteIndex1,
  53. DWORD ExecuteIndex2,
  54. DWORD ExecuteIndex3,
  55. DWORD ExecuteIndex4);
  56. void PaintMemDlgAddrData
  57. (HWND hMemDlg,
  58. PPERF_INSTANCE pInst,
  59. PPERF_OBJECT pObj);
  60. void PaintMemDlgVMData
  61. (HWND hMemDlg,
  62. PPERF_INSTANCE pInst,
  63. PPERF_OBJECT pObj);
  64. void PaintPviewDlgMemoryData
  65. (HWND hPviewDlg,
  66. PPERF_INSTANCE pInst,
  67. PPERF_OBJECT pObj);
  68. void RefreshMemoryDlgImageList
  69. (HWND hImageList,
  70. DWORD ParentIndex,
  71. PPERF_OBJECT pImageObj);
  72. WORD ProcessPriority
  73. (PPERF_OBJECT pObject,
  74. PPERF_INSTANCE pInstance);
  75. void SetProcessListText
  76. (PPERF_INSTANCE pInst,
  77. PPERF_COUNTER pCPU,
  78. PPERF_COUNTER pPRIV,
  79. PPERF_COUNTER pProcID,
  80. double fTime,
  81. LPTSTR str);
  82. void SetThreadListText
  83. (PPERF_INSTANCE pInst,
  84. PPERF_COUNTER pCPU,
  85. PPERF_COUNTER pPRIV,
  86. double fTime,
  87. LPTSTR str);
  88. //*********************************************************************
  89. //
  90. // FormatTimeFields
  91. //
  92. // Formats a double value to time fields.
  93. //
  94. void FormatTimeFields (double fTime,
  95. PTIME_FIELD pTimeFld)
  96. {
  97. INT i;
  98. double f;
  99. f = fTime/3600;
  100. pTimeFld->Hours = i = (int)f;
  101. f = f - i;
  102. pTimeFld->Mins = i = (int)(f = f * 60);
  103. f = f - i;
  104. pTimeFld->Secs = i = (int)(f = f * 60);
  105. f = f - i;
  106. pTimeFld->mSecs = (int)(f * 1000);
  107. }
  108. //*********************************************************************
  109. //
  110. // PutCounterDWKB
  111. //
  112. // Display a DWORD counter's data in KB units.
  113. //
  114. DWORD PutCounterDWKB (HWND hWnd,
  115. DWORD dwItemID,
  116. PPERF_INSTANCE pInst,
  117. PPERF_OBJECT pObj,
  118. DWORD dwCounterIdx)
  119. {
  120. PPERF_COUNTER pCounter;
  121. DWORD *pdwData;
  122. TCHAR szTemp[20];
  123. if (pCounter = FindCounter (pObj, dwCounterIdx)) {
  124. pdwData = (DWORD *) CounterData (pInst, pCounter);
  125. if (pdwData) {
  126. wsprintf (szTemp, TEXT("%ld KB"), *pdwData/1024);
  127. SetDlgItemText (hWnd, dwItemID, szTemp);
  128. return *pdwData;
  129. } else {
  130. return 0;
  131. }
  132. } else {
  133. SetDlgItemText (hWnd, dwItemID, NODATA);
  134. return 0;
  135. }
  136. }
  137. //*********************************************************************
  138. //
  139. // PutCounterHEX
  140. //
  141. // Display a DWORD counter's data in hex.
  142. //
  143. DWORD PutCounterHEX (HWND hWnd,
  144. DWORD dwItemID,
  145. PPERF_INSTANCE pInst,
  146. PPERF_OBJECT pObj,
  147. DWORD dwCounterIdx)
  148. {
  149. PPERF_COUNTER pCounter;
  150. DWORD *pdwData;
  151. TCHAR szTemp[20];
  152. if (pCounter = FindCounter (pObj, dwCounterIdx)) {
  153. pdwData = (DWORD *) CounterData (pInst, pCounter);
  154. if (pdwData) {
  155. wsprintf (szTemp, TEXT("0x%08x"), *pdwData);
  156. SetDlgItemText (hWnd, dwItemID, szTemp);
  157. return *pdwData;
  158. } else {
  159. return 0;
  160. }
  161. } else {
  162. SetDlgItemText (hWnd, dwItemID, NODATA);
  163. return 0;
  164. }
  165. }
  166. //*********************************************************************
  167. //
  168. // PutCounterDWKB
  169. //
  170. // Display a DWORD counter's data.
  171. //
  172. DWORD PutCounterDW (HWND hWnd,
  173. DWORD dwItemID,
  174. PPERF_INSTANCE pInst,
  175. PPERF_OBJECT pObj,
  176. DWORD dwCounterIdx)
  177. {
  178. PPERF_COUNTER pCounter;
  179. DWORD *pdwData;
  180. if (pCounter = FindCounter (pObj, dwCounterIdx)) {
  181. pdwData = (DWORD *) CounterData (pInst, pCounter);
  182. if (pdwData) {
  183. SetDlgItemInt (hWnd, dwItemID, *pdwData, FALSE);
  184. return *pdwData;
  185. } else {
  186. return 0;
  187. }
  188. } else {
  189. SetDlgItemText (hWnd, dwItemID, NODATA);
  190. return 0;
  191. }
  192. }
  193. //*********************************************************************
  194. //
  195. // PaintAddressSpace
  196. //
  197. //
  198. void PaintAddressSpace (HWND hMemDlg,
  199. PPERF_INSTANCE pInst,
  200. PPERF_OBJECT pObj,
  201. DWORD TotalID,
  202. DWORD NoAccessID,
  203. DWORD NoAccessIndex,
  204. DWORD ReadOnlyID,
  205. DWORD ReadOnlyIndex,
  206. DWORD ReadWriteID,
  207. DWORD ReadWriteIndex,
  208. DWORD WriteCopyID,
  209. DWORD WriteCopyIndex,
  210. DWORD ExecuteID,
  211. DWORD ExecuteIndex1,
  212. DWORD ExecuteIndex2,
  213. DWORD ExecuteIndex3,
  214. DWORD ExecuteIndex4)
  215. {
  216. PPERF_COUNTER pCounter;
  217. DWORD *pdwData;
  218. TCHAR szTemp[20];
  219. DWORD dwTotal = 0;
  220. DWORD dwExecute = 0;
  221. BOOL bCounter = FALSE;
  222. dwTotal += PutCounterDWKB (hMemDlg, NoAccessID, pInst, pObj, NoAccessIndex);
  223. dwTotal += PutCounterDWKB (hMemDlg, ReadOnlyID, pInst, pObj, ReadOnlyIndex);
  224. dwTotal += PutCounterDWKB (hMemDlg, ReadWriteID, pInst, pObj, ReadWriteIndex);
  225. dwTotal += PutCounterDWKB (hMemDlg, WriteCopyID, pInst, pObj, WriteCopyIndex);
  226. // execute is the sum of the following
  227. //
  228. if (pCounter = FindCounter (pObj, ExecuteIndex1)) {
  229. pdwData = (DWORD *) CounterData (pInst, pCounter);
  230. if (pdwData) {
  231. dwTotal += *pdwData;
  232. dwExecute += *pdwData;
  233. bCounter = TRUE;
  234. }
  235. }
  236. if (pCounter = FindCounter (pObj, ExecuteIndex2)) {
  237. pdwData = (DWORD *) CounterData (pInst, pCounter);
  238. if (pdwData) {
  239. dwTotal += *pdwData;
  240. dwExecute += *pdwData;
  241. bCounter = TRUE;
  242. }
  243. }
  244. if (pCounter = FindCounter (pObj, ExecuteIndex3)) {
  245. pdwData = (DWORD *) CounterData (pInst, pCounter);
  246. if (pdwData) {
  247. dwTotal += *pdwData;
  248. dwExecute += *pdwData;
  249. bCounter = TRUE;
  250. }
  251. }
  252. if (pCounter = FindCounter (pObj, ExecuteIndex4)) {
  253. pdwData = (DWORD *) CounterData (pInst, pCounter);
  254. if (pdwData) {
  255. dwTotal += *pdwData;
  256. dwExecute += *pdwData;
  257. bCounter = TRUE;
  258. }
  259. }
  260. if (bCounter) {
  261. wsprintf (szTemp, TEXT("%ld KB"), dwExecute/1024);
  262. SetDlgItemText (hMemDlg, ExecuteID, szTemp);
  263. } else
  264. SetDlgItemText (hMemDlg, ExecuteID, NODATA);
  265. wsprintf (szTemp, TEXT("%ld KB"), dwTotal/1024);
  266. SetDlgItemText (hMemDlg, TotalID, szTemp);
  267. }
  268. //*********************************************************************
  269. //
  270. // PaintMemDlgAddrData
  271. //
  272. // Paint the memory dialog address space data.
  273. //
  274. void PaintMemDlgAddrData(HWND hMemDlg,
  275. PPERF_INSTANCE pInst,
  276. PPERF_OBJECT pObj)
  277. {
  278. PaintAddressSpace (hMemDlg, pInst, pObj,
  279. MEMORY_TOTALPRIVATE_COMMIT,
  280. MEMORY_PRIVATE_NOACCESS, PX_PROCESS_PRIVATE_NOACCESS,
  281. MEMORY_PRIVATE_READONLY, PX_PROCESS_PRIVATE_READONLY,
  282. MEMORY_PRIVATE_READWRITE, PX_PROCESS_PRIVATE_READWRITE,
  283. MEMORY_PRIVATE_WRITECOPY, PX_PROCESS_PRIVATE_WRITECOPY,
  284. MEMORY_PRIVATE_EXECUTE, PX_PROCESS_PRIVATE_EXECUTABLE,
  285. PX_PROCESS_PRIVATE_EXE_READONLY,
  286. PX_PROCESS_PRIVATE_EXE_READWRITE,
  287. PX_PROCESS_PRIVATE_EXE_WRITECOPY);
  288. PaintAddressSpace (hMemDlg, pInst, pObj,
  289. MEMORY_TOTALMAPPED_COMMIT,
  290. MEMORY_MAPPED_NOACCESS, PX_PROCESS_MAPPED_NOACCESS,
  291. MEMORY_MAPPED_READONLY, PX_PROCESS_MAPPED_READONLY,
  292. MEMORY_MAPPED_READWRITE, PX_PROCESS_MAPPED_READWRITE,
  293. MEMORY_MAPPED_WRITECOPY, PX_PROCESS_MAPPED_WRITECOPY,
  294. MEMORY_MAPPED_EXECUTE, PX_PROCESS_MAPPED_EXECUTABLE,
  295. PX_PROCESS_MAPPED_EXE_READONLY,
  296. PX_PROCESS_MAPPED_EXE_READWRITE,
  297. PX_PROCESS_MAPPED_EXE_WRITECOPY);
  298. PaintAddressSpace (hMemDlg, pInst, pObj,
  299. MEMORY_TOTALIMAGE_COMMIT,
  300. MEMORY_IMAGE_NOACCESS, PX_PROCESS_IMAGE_NOACCESS,
  301. MEMORY_IMAGE_READONLY, PX_PROCESS_IMAGE_READONLY,
  302. MEMORY_IMAGE_READWRITE, PX_PROCESS_IMAGE_READWRITE,
  303. MEMORY_IMAGE_WRITECOPY, PX_PROCESS_IMAGE_WRITECOPY,
  304. MEMORY_IMAGE_EXECUTE, PX_PROCESS_IMAGE_EXECUTABLE,
  305. PX_PROCESS_IMAGE_EXE_READONLY,
  306. PX_PROCESS_IMAGE_EXE_READWRITE,
  307. PX_PROCESS_IMAGE_EXE_WRITECOPY);
  308. }
  309. //*********************************************************************
  310. //
  311. // PaintMemDlgVMData
  312. //
  313. // Paint the memory dialog Virtual Memory data.
  314. //
  315. void PaintMemDlgVMData (HWND hMemDlg,
  316. PPERF_INSTANCE pInst,
  317. PPERF_OBJECT pObj)
  318. {
  319. PutCounterDWKB (hMemDlg, MEMORY_WS, pInst, pObj, PX_PROCESS_WORKING_SET);
  320. PutCounterDWKB (hMemDlg, MEMORY_PEAK_WS, pInst, pObj, PX_PROCESS_PEAK_WS);
  321. PutCounterDWKB (hMemDlg, MEMORY_PRIVATE_PAGE, pInst, pObj, PX_PROCESS_PRIVATE_PAGE);
  322. PutCounterDWKB (hMemDlg, MEMORY_VSIZE, pInst, pObj, PX_PROCESS_VIRTUAL_SIZE);
  323. PutCounterDWKB (hMemDlg, MEMORY_PEAK_VSIZE, pInst, pObj, PX_PROCESS_PEAK_VS);
  324. PutCounterDWKB (hMemDlg, MEMORY_PFCOUNT, pInst, pObj, PX_PROCESS_FAULT_COUNT);
  325. }
  326. //*********************************************************************
  327. //
  328. // PaintPviewDlgMemoryData
  329. //
  330. // Paint the memory data for pview dialog.
  331. //
  332. void PaintPviewDlgMemoryData (HWND hPviewDlg,
  333. PPERF_INSTANCE pInst,
  334. PPERF_OBJECT pObj)
  335. {
  336. PPERF_COUNTER pCounter;
  337. TCHAR str[20];
  338. DWORD *pdwData;
  339. DWORD dwData = 0;
  340. BOOL bCounter = FALSE;
  341. if (pCounter = FindCounter (pObj, PX_PROCESS_PRIVATE_NOACCESS)) {
  342. pdwData = (DWORD *) CounterData (pInst, pCounter);
  343. if (pdwData) {
  344. dwData += *pdwData;
  345. bCounter = TRUE;
  346. }
  347. }
  348. if (pCounter = FindCounter (pObj, PX_PROCESS_PRIVATE_READONLY)) {
  349. pdwData = (DWORD *) CounterData (pInst, pCounter);
  350. if (pdwData) {
  351. dwData += *pdwData;
  352. bCounter = TRUE;
  353. }
  354. }
  355. if (pCounter = FindCounter (pObj, PX_PROCESS_PRIVATE_READWRITE)) {
  356. pdwData = (DWORD *) CounterData (pInst, pCounter);
  357. if (pdwData) {
  358. dwData += *pdwData;
  359. bCounter = TRUE;
  360. }
  361. }
  362. if (pCounter = FindCounter (pObj, PX_PROCESS_PRIVATE_WRITECOPY)) {
  363. pdwData = (DWORD *) CounterData (pInst, pCounter);
  364. if (pdwData) {
  365. dwData += *pdwData;
  366. bCounter = TRUE;
  367. }
  368. }
  369. if (pCounter = FindCounter (pObj, PX_PROCESS_PRIVATE_EXECUTABLE)) {
  370. pdwData = (DWORD *) CounterData (pInst, pCounter);
  371. if (pdwData) {
  372. dwData += *pdwData;
  373. bCounter = TRUE;
  374. }
  375. }
  376. if (pCounter = FindCounter (pObj, PX_PROCESS_PRIVATE_EXE_READONLY)) {
  377. pdwData = (DWORD *) CounterData (pInst, pCounter);
  378. if (pdwData) {
  379. dwData += *pdwData;
  380. bCounter = TRUE;
  381. }
  382. }
  383. if (pCounter = FindCounter (pObj, PX_PROCESS_PRIVATE_EXE_READWRITE)) {
  384. pdwData = (DWORD *) CounterData (pInst, pCounter);
  385. if (pdwData) {
  386. dwData += *pdwData;
  387. bCounter = TRUE;
  388. }
  389. }
  390. if (pCounter = FindCounter (pObj, PX_PROCESS_PRIVATE_EXE_WRITECOPY)) {
  391. pdwData = (DWORD *) CounterData (pInst, pCounter);
  392. if (pdwData) {
  393. dwData += *pdwData;
  394. bCounter = TRUE;
  395. }
  396. }
  397. if (bCounter) {
  398. wsprintf (str, TEXT("%ld KB"), dwData/1024);
  399. SetDlgItemText (hPviewDlg, PVIEW_TOTALPRIVATE_COMMIT, str);
  400. } else
  401. SetDlgItemText (hPviewDlg, PVIEW_TOTALPRIVATE_COMMIT, NODATA);
  402. }
  403. //*********************************************************************
  404. //
  405. // RefreshMemoryDlg
  406. //
  407. // Refresh the memory detail dialog.
  408. //
  409. BOOL RefreshMemoryDlg (HWND hMemDlg,
  410. PPERF_INSTANCE pProcessInstance,
  411. PPERF_OBJECT pProcessObject,
  412. PPERF_OBJECT pAddressObject,
  413. PPERF_OBJECT pImageObject)
  414. {
  415. DWORD *pProcessID1;
  416. DWORD *pProcessID2;
  417. PPERF_COUNTER pCounter1;
  418. PPERF_COUNTER pCounter2;
  419. PPERF_INSTANCE pAddressInstance;
  420. HWND hImageList;
  421. TCHAR szTemp[40];
  422. BOOL bStat = FALSE;
  423. INT InstIndex = 0;
  424. if ((pCounter1 = FindCounter (pProcessObject, PX_PROCESS_ID)) &&
  425. (pCounter2 = FindCounter (pAddressObject, PX_PROCESS_ID))) {
  426. pProcessID1 = (DWORD *) CounterData (pProcessInstance, pCounter1);
  427. if (pProcessID1) {
  428. wsprintf (szTemp, TEXT("%s (%#x)"), InstanceName (pProcessInstance), *pProcessID1);
  429. SetDlgItemText (hMemDlg, MEMORY_PROCESS_ID, szTemp);
  430. pAddressInstance = FirstInstance (pAddressObject);
  431. while (pAddressInstance && InstIndex < pAddressObject->NumInstances) {
  432. pProcessID2 = (DWORD *) CounterData (pAddressInstance, pCounter2);
  433. if (pProcessID2) {
  434. if (*pProcessID1 == *pProcessID2) {
  435. PaintMemDlgAddrData (hMemDlg, pAddressInstance, pAddressObject);
  436. PaintMemDlgVMData (hMemDlg, pProcessInstance, pProcessObject);
  437. hImageList = GetDlgItem (hMemDlg, MEMORY_IMAGE);
  438. RefreshMemoryDlgImageList (hImageList, InstIndex, pImageObject);
  439. bStat = TRUE;
  440. break;
  441. }
  442. }
  443. pAddressInstance = NextInstance (pAddressInstance);
  444. InstIndex++;
  445. }
  446. }
  447. }
  448. return bStat;
  449. }
  450. //*********************************************************************
  451. //
  452. // RefreshMemoryDlgImageList
  453. //
  454. // Refresh the image list for memory dialog.
  455. //
  456. void RefreshMemoryDlgImageList (HWND hImageList,
  457. DWORD ParentIndex,
  458. PPERF_OBJECT pImageObj)
  459. {
  460. PPERF_INSTANCE pImageInst;
  461. INT_PTR ListIndex;
  462. INT_PTR InstIndex = 0;
  463. ListIndex = SendMessage (hImageList, CB_ADDSTRING, 0, (DWORD_PTR)TEXT(" Total Commit"));
  464. SendMessage (hImageList, CB_SETITEMDATA, ListIndex, 0xFFFFFFFF);
  465. if (pImageObj) {
  466. pImageInst = FirstInstance (pImageObj);
  467. while (pImageInst && InstIndex < pImageObj->NumInstances) {
  468. if (ParentIndex == pImageInst->ParentObjectInstance) {
  469. ListIndex = SendMessage (hImageList,
  470. CB_ADDSTRING,
  471. 0,
  472. (LPARAM)InstanceName(pImageInst));
  473. SendMessage (hImageList, CB_SETITEMDATA, ListIndex, InstIndex);
  474. }
  475. pImageInst = NextInstance (pImageInst);
  476. InstIndex++;
  477. }
  478. }
  479. }
  480. //*********************************************************************
  481. //
  482. // RefreshMemoryDlgImage
  483. //
  484. //
  485. void RefreshMemoryDlgImage (HWND hMemDlg,
  486. DWORD dwIndex,
  487. PPERF_OBJECT pImageObject)
  488. {
  489. PPERF_INSTANCE pInst;
  490. if (pInst = FindInstanceN (pImageObject, dwIndex))
  491. PaintAddressSpace (hMemDlg, pInst, pImageObject,
  492. MEMORY_TOTALIMAGE_COMMIT,
  493. MEMORY_IMAGE_NOACCESS, PX_IMAGE_NOACCESS,
  494. MEMORY_IMAGE_READONLY, PX_IMAGE_READONLY,
  495. MEMORY_IMAGE_READWRITE, PX_IMAGE_READWRITE,
  496. MEMORY_IMAGE_WRITECOPY, PX_IMAGE_WRITECOPY,
  497. MEMORY_IMAGE_EXECUTE, PX_IMAGE_EXECUTABLE,
  498. PX_IMAGE_EXE_READONLY,
  499. PX_IMAGE_EXE_READWRITE,
  500. PX_IMAGE_EXE_WRITECOPY);
  501. }
  502. //*********************************************************************
  503. //
  504. // RefreshPviewDlgMemoryData
  505. //
  506. // Update the memory data for pview dialog. This should be done
  507. // after the ghCostlyData is collected and is not refreshing.
  508. //
  509. void RefreshPviewDlgMemoryData (HWND hPviewDlg,
  510. PPERF_INSTANCE pProcessInstance,
  511. PPERF_OBJECT pProcessObject,
  512. PPERF_OBJECT pAddressObject)
  513. {
  514. DWORD *pProcessID1;
  515. DWORD *pProcessID2;
  516. PPERF_COUNTER pCounter1;
  517. PPERF_COUNTER pCounter2;
  518. PPERF_INSTANCE pAddressInstance;
  519. INT i = 0;
  520. if ((pCounter1 = FindCounter (pProcessObject, PX_PROCESS_ID)) &&
  521. (pCounter2 = FindCounter (pAddressObject, PX_PROCESS_ID))) {
  522. pProcessID1 = (DWORD *) CounterData (pProcessInstance, pCounter1);
  523. if (pProcessID1) {
  524. pAddressInstance = FirstInstance (pAddressObject);
  525. while (pAddressInstance && i < pAddressObject->NumInstances) {
  526. pProcessID2 = (DWORD *) CounterData (pAddressInstance, pCounter2);
  527. if (pProcessID2){
  528. if (*pProcessID1 == *pProcessID2) {
  529. PaintPviewDlgMemoryData (hPviewDlg, pAddressInstance, pAddressObject);
  530. break;
  531. }
  532. pAddressInstance = NextInstance (pAddressInstance);
  533. i++;
  534. }
  535. }
  536. }
  537. }
  538. }
  539. //*********************************************************************
  540. //
  541. // RefreshPviewDlgThreadPC
  542. //
  543. // Update the thread PC value. This should be done after the ghCostlyData
  544. // is collected and is no refreshing.
  545. //
  546. void RefreshPviewDlgThreadPC (HWND hPviewDlg,
  547. LPTSTR szProcessName,
  548. LPTSTR szThreadName,
  549. PPERF_OBJECT pThreadDetailsObject,
  550. PPERF_DATA pCostlyData)
  551. {
  552. PPERF_COUNTER pCounter;
  553. PPERF_INSTANCE pInstance;
  554. PPERF_INSTANCE pParent;
  555. LPTSTR szInstanceName;
  556. LPTSTR szParentName;
  557. TCHAR str[20];
  558. DWORD *pdwData;
  559. INT i = 0;
  560. if (pCounter = FindCounter (pThreadDetailsObject, PX_THREAD_PC)) {
  561. pInstance = FirstInstance (pThreadDetailsObject);
  562. while (pInstance && i < pThreadDetailsObject->NumInstances) {
  563. if (!(szInstanceName = InstanceName (pInstance)))
  564. // can't find name
  565. ;
  566. else if (lstrcmp (szThreadName, szInstanceName))
  567. // the thread name is different
  568. ;
  569. else if (!(pParent = FindInstanceParent (pInstance, pCostlyData)))
  570. // can't find parent
  571. ;
  572. else if (!(szParentName = InstanceName (pParent)))
  573. // can't find parent's name
  574. ;
  575. else if (!lstrcmp (szProcessName, szParentName)) {
  576. // Parent's name matches, this is the right one.
  577. //
  578. pdwData = CounterData (pInstance, pCounter);
  579. if (pdwData) {
  580. wsprintf (str, TEXT("0x%08x"), *pdwData);
  581. SetDlgItemText (hPviewDlg, PVIEW_THREAD_PC, str);
  582. }
  583. return;
  584. }
  585. pInstance = NextInstance (pInstance);
  586. i++;
  587. }
  588. }
  589. // We are here only because we can't find the data to display.
  590. //
  591. SetDlgItemText (hPviewDlg, PVIEW_THREAD_PC, NODATA);
  592. }
  593. //*********************************************************************
  594. //
  595. // ProcessPriority
  596. //
  597. // Returns the process priority dialog item id.
  598. //
  599. WORD ProcessPriority (PPERF_OBJECT pObject,
  600. PPERF_INSTANCE pInstance)
  601. {
  602. PPERF_COUNTER pCounter;
  603. DWORD *pdwData;
  604. if (pCounter = FindCounter (pObject, PX_PROCESS_PRIO)) {
  605. pdwData = (DWORD *) CounterData (pInstance, pCounter);
  606. if (pdwData) {
  607. if (*pdwData < 7)
  608. return PVIEW_PRIORITY_IDL;
  609. else if (*pdwData < 10)
  610. return PVIEW_PRIORITY_NORMAL;
  611. else
  612. return PVIEW_PRIORITY_HIGH;
  613. } else {
  614. return PVIEW_PRIORITY_NORMAL;
  615. }
  616. } else
  617. return PVIEW_PRIORITY_NORMAL;
  618. }
  619. //*********************************************************************
  620. //
  621. // RefreshPerfData
  622. //
  623. // Get a new set of performance data. pData should be NULL initially.
  624. //
  625. PPERF_DATA RefreshPerfData (HKEY hPerfKey,
  626. LPTSTR szObjectIndex,
  627. PPERF_DATA pData,
  628. DWORD *pDataSize)
  629. {
  630. if (GetPerfData (hPerfKey, szObjectIndex, &pData, pDataSize) == ERROR_SUCCESS)
  631. return pData;
  632. else
  633. return NULL;
  634. }
  635. //*********************************************************************
  636. //
  637. // SetProcessListText
  638. //
  639. // Format the process list text.
  640. //
  641. void SetProcessListText (PPERF_INSTANCE pInst,
  642. PPERF_COUNTER pCPU,
  643. PPERF_COUNTER pPRIV,
  644. PPERF_COUNTER pProcID,
  645. double fTime,
  646. LPTSTR str)
  647. {
  648. DWORD *pdwProcID;
  649. LARGE_INTEGER *liCPU;
  650. LARGE_INTEGER *liPRIV;
  651. double fCPU = 0;
  652. double fPRIV = 0;
  653. INT PcntPRIV = 0;
  654. INT PcntUSER = 0;
  655. TIME_FIELD TimeFld;
  656. TCHAR szTemp[100];
  657. if (pCPU) {
  658. liCPU = (LARGE_INTEGER *) CounterData (pInst, pCPU);
  659. if (liCPU) {
  660. fCPU = Li2Double (*liCPU);
  661. }
  662. }
  663. if (pPRIV) {
  664. liPRIV = (LARGE_INTEGER *) CounterData (pInst, pPRIV);
  665. if (liPRIV)
  666. fPRIV = Li2Double (*liPRIV);
  667. }
  668. if (fCPU > 0) {
  669. PcntPRIV = (INT)(fPRIV / fCPU * 100 + 0.5);
  670. PcntUSER = 100 - PcntPRIV;
  671. }
  672. if (pProcID) {
  673. pdwProcID = (DWORD *) CounterData (pInst, pProcID);
  674. if (pdwProcID)
  675. wsprintf (szTemp, TEXT("%ls (%#x)"), InstanceName(pInst), *pdwProcID);
  676. else
  677. wsprintf (szTemp, TEXT("%ls"), InstanceName(pInst));
  678. } else
  679. wsprintf (szTemp, TEXT("%ls"), InstanceName(pInst));
  680. FormatTimeFields (fCPU/1.0e7, &TimeFld);
  681. wsprintf (str,
  682. TEXT("%s\t%3ld:%02ld:%02ld.%03ld\t%3ld%%\t%3ld%%"),
  683. szTemp,
  684. TimeFld.Hours,
  685. TimeFld.Mins,
  686. TimeFld.Secs,
  687. TimeFld.mSecs,
  688. PcntPRIV,
  689. PcntUSER);
  690. }
  691. //*********************************************************************
  692. //
  693. // RefreshProcessList
  694. //
  695. // Find all process and update the process list.
  696. //
  697. void RefreshProcessList (HWND hProcessList,
  698. PPERF_OBJECT pObject)
  699. {
  700. PPERF_INSTANCE pInstance;
  701. TCHAR szListText[256];
  702. INT_PTR ListIndex;
  703. PPERF_COUNTER pCounterCPU;
  704. PPERF_COUNTER pCounterPRIV;
  705. PPERF_COUNTER pCounterProcID;
  706. double fObjectFreq;
  707. double fObjectTime;
  708. double fTime;
  709. INT InstanceIndex = 0;
  710. if (pObject) {
  711. if ((pCounterCPU = FindCounter (pObject, PX_PROCESS_CPU)) &&
  712. (pCounterPRIV = FindCounter (pObject, PX_PROCESS_PRIV)) &&
  713. (pCounterProcID = FindCounter (pObject, PX_PROCESS_ID))) {
  714. fObjectFreq = Li2Double (pObject->PerfFreq);
  715. fObjectTime = Li2Double (pObject->PerfTime);
  716. fTime = fObjectTime / fObjectFreq;
  717. pInstance = FirstInstance (pObject);
  718. while (pInstance && InstanceIndex < pObject->NumInstances) {
  719. SetProcessListText (pInstance,
  720. pCounterCPU,
  721. pCounterPRIV,
  722. pCounterProcID,
  723. fTime,
  724. szListText);
  725. ListIndex = SendMessage (hProcessList, LB_ADDSTRING, 0, (LPARAM)szListText);
  726. SendMessage (hProcessList, LB_SETITEMDATA, ListIndex, InstanceIndex);
  727. pInstance = NextInstance (pInstance);
  728. InstanceIndex++;
  729. }
  730. }
  731. }
  732. }
  733. //*********************************************************************
  734. //
  735. // RefreshProcessData
  736. //
  737. // Find data for a given process and update.
  738. //
  739. void RefreshProcessData (HWND hWnd,
  740. PPERF_OBJECT pObject,
  741. DWORD ProcessIndex)
  742. {
  743. PPERF_INSTANCE pInstance;
  744. if (pInstance = FindInstanceN (pObject, ProcessIndex)) {
  745. PutCounterDWKB (hWnd, PVIEW_WS, pInstance, pObject, PX_PROCESS_WORKING_SET);
  746. SetDlgItemText (hWnd, PVIEW_TOTALPRIVATE_COMMIT, NODATA);
  747. // set priority
  748. //
  749. CheckRadioButton (hWnd,
  750. PVIEW_PRIORITY_HIGH,
  751. PVIEW_PRIORITY_IDL,
  752. ProcessPriority (pObject, pInstance));
  753. }
  754. }
  755. //*********************************************************************
  756. //
  757. // SetThreadListText
  758. //
  759. // Format the thread list text.
  760. //
  761. void SetThreadListText (PPERF_INSTANCE pInst,
  762. PPERF_COUNTER pCPU,
  763. PPERF_COUNTER pPRIV,
  764. double fTime,
  765. LPTSTR str)
  766. {
  767. LARGE_INTEGER *liCPU;
  768. LARGE_INTEGER *liPRIV;
  769. double fCPU = 0;
  770. double fPRIV = 0;
  771. INT PcntPRIV = 0;
  772. INT PcntUSER = 0;
  773. TIME_FIELD TimeFld;
  774. TCHAR szTemp[100];
  775. if (pCPU) {
  776. liCPU = (LARGE_INTEGER *) CounterData (pInst, pCPU);
  777. if (liCPU)
  778. fCPU = Li2Double (*liCPU);
  779. }
  780. if (pPRIV) {
  781. liPRIV = (LARGE_INTEGER *) CounterData (pInst, pPRIV);
  782. if (liPRIV)
  783. fPRIV = Li2Double (*liPRIV);
  784. }
  785. if (fCPU > 0) {
  786. PcntPRIV = (INT)(fPRIV / fCPU * 100 + 0.5);
  787. PcntUSER = 100 - PcntPRIV;
  788. }
  789. if (pInst->UniqueID != PERF_NO_UNIQUE_ID)
  790. wsprintf (szTemp, TEXT("%ls (%#x)"), InstanceName(pInst), pInst->UniqueID);
  791. else
  792. wsprintf (szTemp, TEXT("%ls"), InstanceName(pInst));
  793. FormatTimeFields (fCPU/1.0e7, &TimeFld);
  794. wsprintf (str,
  795. TEXT("%s\t%3ld:%02ld:%02ld.%03ld\t%3ld%%\t%3ld %%"),
  796. szTemp,
  797. TimeFld.Hours,
  798. TimeFld.Mins,
  799. TimeFld.Secs,
  800. TimeFld.mSecs,
  801. PcntPRIV,
  802. PcntUSER);
  803. }
  804. //*********************************************************************
  805. //
  806. // RefreshThreadList
  807. //
  808. // Find all threads for a given process and update the thread list.
  809. //
  810. void RefreshThreadList (HWND hThreadList,
  811. PPERF_OBJECT pObject,
  812. DWORD ParentIndex)
  813. {
  814. PPERF_INSTANCE pInstance;
  815. TCHAR szListText[256];
  816. INT_PTR ListIndex;
  817. PPERF_COUNTER pCounterCPU;
  818. PPERF_COUNTER pCounterPRIV;
  819. double fObjectFreq;
  820. double fObjectTime;
  821. double fTime;
  822. INT InstanceIndex = 0;
  823. if (pObject) {
  824. if ((pCounterCPU = FindCounter (pObject, PX_THREAD_CPU)) &&
  825. (pCounterPRIV = FindCounter (pObject, PX_THREAD_PRIV))) {
  826. fObjectFreq = Li2Double (pObject->PerfFreq);
  827. fObjectTime = Li2Double (pObject->PerfTime);
  828. fTime = fObjectTime / fObjectFreq;
  829. pInstance = FirstInstance (pObject);
  830. while (pInstance && InstanceIndex < pObject->NumInstances) {
  831. if (ParentIndex == pInstance->ParentObjectInstance) {
  832. SetThreadListText (pInstance,
  833. pCounterCPU,
  834. pCounterPRIV,
  835. fTime,
  836. szListText);
  837. ListIndex = SendMessage (hThreadList,
  838. LB_INSERTSTRING,
  839. (WPARAM)-1,
  840. (LPARAM)szListText);
  841. SendMessage (hThreadList, LB_SETITEMDATA, ListIndex, InstanceIndex);
  842. }
  843. pInstance = NextInstance (pInstance);
  844. InstanceIndex++;
  845. }
  846. }
  847. }
  848. }
  849. //*********************************************************************
  850. //
  851. // RefreshThreadData
  852. //
  853. // Find data for a given thread and update.
  854. //
  855. void RefreshThreadData (HWND hWnd,
  856. PPERF_OBJECT pThreadObj,
  857. DWORD ThreadIndex,
  858. PPERF_OBJECT pProcessObj,
  859. PPERF_INSTANCE pProcessInst)
  860. {
  861. PPERF_INSTANCE pInstance;
  862. PPERF_COUNTER pCounter;
  863. DWORD *pdwData;
  864. DWORD *pdwProcPrio;
  865. BOOL bPrioCounter = TRUE;
  866. if (pInstance = FindInstanceN (pThreadObj, ThreadIndex)) {
  867. SetDlgItemText (hWnd, PVIEW_THREAD_PC, NODATA);
  868. PutCounterHEX (hWnd, PVIEW_THREAD_START, pInstance, pThreadObj, PX_THREAD_START);
  869. PutCounterDW (hWnd, PVIEW_THREAD_SWITCHES, pInstance, pThreadObj, PX_THREAD_SWITCHES);
  870. PutCounterDW (hWnd, PVIEW_THREAD_DYNAMIC, pInstance, pThreadObj, PX_THREAD_PRIO);
  871. }
  872. if (pInstance) {
  873. // get thread base priority
  874. //
  875. if (pCounter = FindCounter (pThreadObj, PX_THREAD_BASE_PRIO)) {
  876. pdwData = CounterData (pInstance, pCounter);
  877. if (!pdwData) {
  878. bPrioCounter = FALSE;
  879. }
  880. } else
  881. bPrioCounter = FALSE;
  882. // get process priority
  883. //
  884. if (pCounter = FindCounter (pProcessObj, PX_PROCESS_PRIO)) {
  885. pdwProcPrio = CounterData (pProcessInst, pCounter);
  886. if (!pdwProcPrio) {
  887. bPrioCounter = FALSE;
  888. }
  889. } else
  890. bPrioCounter = FALSE;
  891. } else
  892. bPrioCounter = FALSE;
  893. // set thread base priority
  894. //
  895. if (!bPrioCounter)
  896. CheckRadioButton (hWnd,
  897. PVIEW_THREAD_HIGHEST,
  898. PVIEW_THREAD_LOWEST,
  899. PVIEW_THREAD_NORMAL);
  900. else {
  901. switch (*pdwData - *pdwProcPrio) {
  902. case 2:
  903. CheckRadioButton (hWnd,
  904. PVIEW_THREAD_HIGHEST,
  905. PVIEW_THREAD_LOWEST,
  906. PVIEW_THREAD_HIGHEST);
  907. break;
  908. case 1:
  909. CheckRadioButton (hWnd,
  910. PVIEW_THREAD_HIGHEST,
  911. PVIEW_THREAD_LOWEST,
  912. PVIEW_THREAD_ABOVE);
  913. break;
  914. case -1:
  915. CheckRadioButton (hWnd,
  916. PVIEW_THREAD_HIGHEST,
  917. PVIEW_THREAD_LOWEST,
  918. PVIEW_THREAD_BELOW);
  919. break;
  920. case -2:
  921. CheckRadioButton (hWnd,
  922. PVIEW_THREAD_HIGHEST,
  923. PVIEW_THREAD_LOWEST,
  924. PVIEW_THREAD_LOWEST);
  925. break;
  926. case 0:
  927. default:
  928. CheckRadioButton (hWnd,
  929. PVIEW_THREAD_HIGHEST,
  930. PVIEW_THREAD_LOWEST,
  931. PVIEW_THREAD_NORMAL);
  932. break;
  933. }
  934. }
  935. }