Leaked source code of windows server 2003
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.

242 lines
6.4 KiB

  1. /*++
  2. Copyright (C) 1996-1999 Microsoft Corporation
  3. Module Name:
  4. browse.cpp
  5. Abstract:
  6. Implements the interaction with the PDH browser dialog.
  7. --*/
  8. #include <assert.h>
  9. #include "polyline.h"
  10. #include "pdhmsg.h"
  11. #include "browser.h"
  12. #include "smonmsg.h"
  13. #include "utils.h"
  14. typedef struct {
  15. PDH_BROWSE_DLG_CONFIG_H *pBrowseInfo;
  16. ENUMPATH_CALLBACK pCallback;
  17. LPVOID lpUserData;
  18. } ENUMCALLBACK_INFO;
  19. static PDH_FUNCTION
  20. BrowseCallback (
  21. DWORD_PTR lpParam
  22. );
  23. HRESULT
  24. BrowseCounters (
  25. HLOG hDataSource,
  26. DWORD dwDetailLevel,
  27. HWND hwndOwner,
  28. ENUMPATH_CALLBACK pCallback,
  29. LPVOID lpUserData,
  30. BOOL bUseInstanceIndex
  31. )
  32. {
  33. #define CTRBUFLEN 8192
  34. PDH_BROWSE_DLG_CONFIG_H BrowseInfo;
  35. ENUMCALLBACK_INFO CallbackInfo;
  36. // clear the structure before assigning values
  37. memset (&BrowseInfo, 0, sizeof (BrowseInfo));
  38. BrowseInfo.bIncludeInstanceIndex = (bUseInstanceIndex ? 1 : 0);
  39. BrowseInfo.bSingleCounterPerAdd = 0;
  40. BrowseInfo.bSingleCounterPerDialog = 0;
  41. BrowseInfo.bLocalCountersOnly = 0;
  42. BrowseInfo.bWildCardInstances = 1;
  43. BrowseInfo.bHideDetailBox = 1;
  44. BrowseInfo.bInitializePath = 0;
  45. BrowseInfo.bDisableMachineSelection = 0;
  46. BrowseInfo.bReserved = 0;
  47. BrowseInfo.bIncludeCostlyObjects = 0;
  48. BrowseInfo.szDialogBoxCaption = ResourceString(IDS_ADDCOUNTERS);
  49. BrowseInfo.hWndOwner = hwndOwner;
  50. BrowseInfo.hDataSource = hDataSource;
  51. BrowseInfo.dwDefaultDetailLevel = dwDetailLevel;
  52. BrowseInfo.szReturnPathBuffer = (LPWSTR)malloc(CTRBUFLEN * sizeof(WCHAR));
  53. if (BrowseInfo.szReturnPathBuffer == NULL) {
  54. return E_OUTOFMEMORY;
  55. }
  56. BrowseInfo.cchReturnPathLength = CTRBUFLEN;
  57. CallbackInfo.pBrowseInfo = &BrowseInfo;
  58. CallbackInfo.pCallback = pCallback;
  59. CallbackInfo.lpUserData = lpUserData;
  60. BrowseInfo.dwCallBackArg = (DWORD_PTR)&CallbackInfo;
  61. BrowseInfo.pCallBack = BrowseCallback;
  62. //
  63. // Call PDH function to browse the counters
  64. //
  65. PdhBrowseCountersH (&BrowseInfo);
  66. if (BrowseInfo.szReturnPathBuffer) {
  67. free(BrowseInfo.szReturnPathBuffer);
  68. }
  69. return NO_ERROR;
  70. }
  71. static PDH_FUNCTION
  72. BrowseCallback (
  73. DWORD_PTR dwParam
  74. )
  75. {
  76. #define CTRBUFLIMIT (0x10000000)
  77. HRESULT hr = S_OK;
  78. BOOLEAN fDuplicate = FALSE;
  79. ENUMCALLBACK_INFO *pCallbackInfo = (ENUMCALLBACK_INFO*)dwParam;
  80. PDH_BROWSE_DLG_CONFIG_H *pBrowseInfo = pCallbackInfo->pBrowseInfo;
  81. LPWSTR pszCtrPath;
  82. if (pBrowseInfo->CallBackStatus == ERROR_SUCCESS) {
  83. //
  84. // Call callback for each path
  85. // If wildcard path, EnumExpandedPath will call once for each generated path
  86. //
  87. for (pszCtrPath = pBrowseInfo->szReturnPathBuffer;
  88. *pszCtrPath != L'\0';
  89. pszCtrPath += (lstrlen(pszCtrPath) + 1)) {
  90. hr = EnumExpandedPath(pBrowseInfo->hDataSource,
  91. pszCtrPath,
  92. pCallbackInfo->pCallback,
  93. pCallbackInfo->lpUserData);
  94. if ((DWORD)hr == SMON_STATUS_DUPL_COUNTER_PATH)
  95. fDuplicate = TRUE;
  96. }
  97. // Notify user if duplicates encountered
  98. if (fDuplicate) {
  99. MessageBox(pBrowseInfo->hWndOwner,
  100. ResourceString(IDS_DUPL_PATH_ERR),
  101. ResourceString(IDS_APP_NAME),
  102. MB_OK | MB_ICONWARNING);
  103. }
  104. }
  105. else if (pBrowseInfo->CallBackStatus == PDH_MORE_DATA) {
  106. if (pBrowseInfo->szReturnPathBuffer) {
  107. free(pBrowseInfo->szReturnPathBuffer);
  108. pBrowseInfo->szReturnPathBuffer = NULL;
  109. }
  110. if (pBrowseInfo->cchReturnPathLength == CTRBUFLIMIT) {
  111. return PDH_MEMORY_ALLOCATION_FAILURE;
  112. }
  113. pBrowseInfo->cchReturnPathLength *= 2;
  114. if (pBrowseInfo->cchReturnPathLength > CTRBUFLIMIT) {
  115. pBrowseInfo->cchReturnPathLength = CTRBUFLIMIT;
  116. }
  117. pBrowseInfo->szReturnPathBuffer = (WCHAR*)malloc(pBrowseInfo->cchReturnPathLength * sizeof(WCHAR));
  118. if (pBrowseInfo->szReturnPathBuffer) {
  119. return PDH_RETRY;
  120. }
  121. else {
  122. pBrowseInfo->cchReturnPathLength = 0;
  123. return PDH_MEMORY_ALLOCATION_FAILURE;
  124. }
  125. }
  126. return ERROR_SUCCESS;
  127. }
  128. HRESULT
  129. EnumExpandedPath (
  130. HLOG hDataSource,
  131. LPWSTR pszCtrPath,
  132. ENUMPATH_CALLBACK pCallback,
  133. LPVOID lpUserData
  134. )
  135. {
  136. #define INSTBUFLEN 4096
  137. PDH_STATUS pdhStatus = ERROR_SUCCESS;
  138. ULONG ulBufLen;
  139. INT nInstBufRetry;
  140. LPWSTR pszInstBuf = NULL;
  141. LPWSTR pszInstance;
  142. //
  143. // If no wild card, invoke callback once on path
  144. //
  145. if (wcschr(pszCtrPath, L'*') == NULL) {
  146. return pCallback(pszCtrPath, (DWORD_PTR)lpUserData, 0);
  147. }
  148. //
  149. // Try 10 times before we fail out
  150. //
  151. nInstBufRetry = 10;
  152. ulBufLen = INSTBUFLEN;
  153. do {
  154. if ( NULL != pszInstBuf ) {
  155. free(pszInstBuf);
  156. pszInstBuf = NULL;
  157. ulBufLen *= 2;
  158. }
  159. pszInstBuf = (WCHAR*) malloc(ulBufLen * sizeof(WCHAR));
  160. if (pszInstBuf == NULL) {
  161. pdhStatus = E_OUTOFMEMORY;
  162. break;
  163. }
  164. pdhStatus = PdhExpandWildCardPathH (
  165. hDataSource,
  166. pszCtrPath,
  167. pszInstBuf,
  168. &ulBufLen,
  169. PDH_REFRESHCOUNTERS);
  170. nInstBufRetry--;
  171. } while ((pdhStatus == PDH_MORE_DATA) && (nInstBufRetry));
  172. if (pdhStatus == ERROR_SUCCESS) {
  173. // For each instance name, generate a path and invoke the callback
  174. for (pszInstance = pszInstBuf;
  175. *pszInstance != L'\0';
  176. pszInstance += lstrlen(pszInstance) + 1) {
  177. // Invoke callback
  178. HRESULT hr = pCallback(pszInstance, (DWORD_PTR)lpUserData, BROWSE_WILDCARD);
  179. // When expanding a wildcard, don't notify user about duplicate path errors
  180. if (hr != S_OK && (DWORD)hr != SMON_STATUS_DUPL_COUNTER_PATH) {
  181. pdhStatus = hr;
  182. }
  183. }
  184. }
  185. if (pszInstBuf) {
  186. free(pszInstBuf);
  187. }
  188. return pdhStatus;
  189. }