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.

729 lines
22 KiB

  1. /*===================================================================
  2. Microsoft Denali
  3. Microsoft Confidential.
  4. Copyright 1996 Microsoft Corporation. All Rights Reserved.
  5. Component: NT Event logging
  6. File: Eventlog.cpp
  7. Owner: Jhittle
  8. This file contains general event logging routines for Denali.
  9. ===================================================================*/
  10. #include "denpre.h"
  11. #pragma hdrstop
  12. #include <direct.h>
  13. #include "denevent.h"
  14. #include "memchk.h"
  15. extern HINSTANCE g_hinstDLL;
  16. extern CRITICAL_SECTION g_csEventlogLock;
  17. /*===================================================================
  18. STDAPI UnRegisterEventLog( void )
  19. UnRegister the event log.
  20. Returns:
  21. HRESULT S_OK or E_FAIL
  22. Side effects:
  23. Removes denali NT eventlog entries from the registry
  24. ===================================================================*/
  25. STDAPI UnRegisterEventLog( void )
  26. {
  27. HKEY hkey = NULL;
  28. DWORD iKey;
  29. CHAR szKeyName[255];
  30. DWORD cbKeyName;
  31. static const char szDenaliKey[] = "SYSTEM\\CurrentControlSet\\Services\\EventLog\\Application\\Active Server Pages";
  32. // Open the HKEY_CLASSES_ROOT\CLSID\{...} key so we can delete its subkeys
  33. if (RegOpenKeyExA(HKEY_LOCAL_MACHINE, szDenaliKey, 0, KEY_READ | KEY_WRITE, &hkey) != ERROR_SUCCESS)
  34. goto LErrExit;
  35. // Enumerate all its subkeys, and delete them
  36. for (iKey=0;;iKey++)
  37. {
  38. cbKeyName = sizeof(szKeyName);
  39. if (RegEnumKeyExA(hkey, iKey, szKeyName, &cbKeyName, 0, NULL, 0, NULL) != ERROR_SUCCESS)
  40. break;
  41. if (RegDeleteKeyA(hkey, szKeyName) != ERROR_SUCCESS)
  42. goto LErrExit;
  43. }
  44. // Close the key, and then delete it
  45. if (RegCloseKey(hkey) != ERROR_SUCCESS)
  46. return E_FAIL;
  47. if (RegDeleteKeyA(HKEY_LOCAL_MACHINE, szDenaliKey) != ERROR_SUCCESS)
  48. return E_FAIL;
  49. return S_OK;
  50. LErrExit:
  51. RegCloseKey(hkey);
  52. return E_FAIL;
  53. }
  54. /*===================================================================
  55. STDAPI RegisterEventLog(void)
  56. Register the NT event log.
  57. Returns:
  58. HRESULT S_OK or E_FAIL
  59. Side effects:
  60. Sets up denali dll in the Eventlog registry for resolution of
  61. NT eventlog message strings
  62. ===================================================================*/
  63. STDAPI RegisterEventLog( void )
  64. {
  65. HKEY hk; // registry key handle
  66. DWORD dwData;
  67. BOOL bSuccess;
  68. //char szMsgDLL[MAX_PATH];
  69. char szPath[MAX_PATH];
  70. char *pch;
  71. // Get the path and name of Denali
  72. if (!GetModuleFileNameA(g_hinstDLL, szPath, sizeof(szPath)/sizeof(char)))
  73. return E_FAIL;
  74. // BUG FIX: 102010 DBCS code changes
  75. //
  76. //for (pch = szPath + lstrlen(szPath); pch > szPath && *pch != TEXT('\\'); pch--)
  77. // ;
  78. //
  79. //if (pch == szPath)
  80. // return E_FAIL;
  81. pch = (char*) _mbsrchr((const unsigned char*)szPath, '\\');
  82. if (pch == NULL)
  83. return E_FAIL;
  84. strcpy(pch + 1, ASP_DLL_NAME);
  85. // When an application uses the RegisterEventSource or OpenEventLog
  86. // function to get a handle of an event log, the event loggging service
  87. // searches for the specified source name in the registry. You can add a
  88. // new source name to the registry by opening a new registry subkey
  89. // under the Application key and adding registry values to the new
  90. // subkey.
  91. // Create a new key for our application
  92. bSuccess = RegCreateKeyA(HKEY_LOCAL_MACHINE,
  93. "SYSTEM\\CurrentControlSet\\Services\\EventLog\\Application\\Active Server Pages", &hk);
  94. if(bSuccess != ERROR_SUCCESS)
  95. return E_FAIL;
  96. // Add the Event-ID message-file name to the subkey.
  97. bSuccess = RegSetValueExA(hk, // subkey handle
  98. "EventMessageFile", // value name
  99. 0, // must be zero
  100. REG_EXPAND_SZ, // value type
  101. (LPBYTE) szPath, // address of value data
  102. strlen(szPath) + 1); // length of value data
  103. if(bSuccess != ERROR_SUCCESS)
  104. goto LT_ERROR;
  105. // Set the supported types flags and addit to the subkey.
  106. dwData = EVENTLOG_ERROR_TYPE | EVENTLOG_WARNING_TYPE | EVENTLOG_INFORMATION_TYPE;
  107. bSuccess = RegSetValueExA(hk, // subkey handle
  108. "TypesSupported", // value name
  109. 0, // must be zero
  110. REG_DWORD, // value type
  111. (LPBYTE) &dwData, // address of value data
  112. sizeof(DWORD)); // length of value data
  113. if(bSuccess != ERROR_SUCCESS)
  114. goto LT_ERROR;
  115. RegCloseKey(hk);
  116. return S_OK;
  117. LT_ERROR:
  118. RegCloseKey(hk);
  119. return E_FAIL;
  120. }
  121. /*===================================================================
  122. STDAPI reportAnEvent(DWORD, WORD, LPSTR);
  123. Register report an event to the NT event log
  124. INPUT:
  125. the event ID to report in the log, the number of insert
  126. strings, and an array of null-terminated insert strings
  127. Returns:
  128. HRESULT S_OK or E_FAIL
  129. Side effects:
  130. Addes an entry in the NT event log
  131. ===================================================================*/
  132. STDAPI ReportAnEvent(DWORD dwIdEvent, WORD wEventlog_Type, WORD cStrings, LPCSTR *pszStrings)
  133. {
  134. HANDLE hAppLog;
  135. BOOL bSuccess;
  136. HRESULT hr = S_OK;
  137. // Get a handle to the Application event log
  138. hAppLog = RegisterEventSourceA(NULL, // use local machine
  139. "Active Server Pages"); // source name
  140. if(hAppLog == NULL)
  141. return E_FAIL;
  142. // Now report the event, which will add this event to the event log
  143. bSuccess = ReportEventA(hAppLog, // event-log handle
  144. wEventlog_Type, // event type
  145. 0, // category zero
  146. dwIdEvent, // event ID
  147. NULL, // no user SID
  148. cStrings, // number of substitution strings
  149. 0, // no binary data
  150. pszStrings, // string array
  151. NULL); // address of data
  152. if(!bSuccess)
  153. hr = E_FAIL;
  154. DeregisterEventSource(hAppLog);
  155. return hr;
  156. }
  157. /*===================================================================
  158. void MSG_DenaliStarted(void)
  159. report an event to the NT event log
  160. INPUT:
  161. None
  162. Returns:
  163. Nonw
  164. Side effects:
  165. Addes an entry in the NT event log
  166. ===================================================================*/
  167. void MSG_DenaliStarted(void)
  168. {
  169. ReportAnEvent( (DWORD) MSG_DENALI_SERVICE_STARTED, (WORD) EVENTLOG_INFORMATION_TYPE, (WORD) 0, (LPCSTR *) NULL );
  170. }
  171. /*===================================================================
  172. void MSG_DenaliStoped(void)
  173. report an event to the NT event log
  174. INPUT:
  175. None
  176. Returns:
  177. None
  178. Side effects:
  179. Addes an entry in the NT event log
  180. ===================================================================*/
  181. void MSG_DenaliStoped(void)
  182. {
  183. ReportAnEvent( (DWORD) MSG_DENALI_SERVICE_STOPPED, (WORD) EVENTLOG_INFORMATION_TYPE, (WORD) 0, (LPCSTR *) NULL );
  184. return;
  185. }
  186. /*===================================================================
  187. void MSG_Error( LPCSTR sz )
  188. report an event to the NT event log
  189. INPUT:
  190. ptr to null-terminated string
  191. Returns:
  192. None
  193. Side effects:
  194. Addes an entry in the NT event log
  195. ===================================================================*/
  196. void MSG_Error( LPCSTR strSource )
  197. {
  198. static char szLastError[MAX_MSG_LENGTH];
  199. EnterCriticalSection(&g_csEventlogLock);
  200. if (strcmp(strSource, szLastError) == 0)
  201. {
  202. LeaveCriticalSection(&g_csEventlogLock);
  203. return;
  204. }
  205. strncpy(szLastError,strSource, MAX_MSG_LENGTH);
  206. szLastError[MAX_MSG_LENGTH-1] = '\0';
  207. LeaveCriticalSection(&g_csEventlogLock);
  208. ReportAnEvent( (DWORD) MSG_DENALI_ERROR_1, (WORD) EVENTLOG_ERROR_TYPE, (WORD) 1, &strSource /*aInsertStrs*/ );
  209. }
  210. /*===================================================================
  211. void MSG_Error( UINT ustrID )
  212. report an event to the NT event log
  213. INPUT:
  214. string table string ID
  215. Returns:
  216. None
  217. Side effects:
  218. Addes an entry in the NT event log
  219. ===================================================================*/
  220. void MSG_Error( UINT SourceID1 )
  221. {
  222. static unsigned int nLastSourceID1;
  223. // if this is a repeat of the last reported message then return
  224. /// without posting an error.
  225. EnterCriticalSection(&g_csEventlogLock);
  226. if (SourceID1 == nLastSourceID1)
  227. {
  228. LeaveCriticalSection(&g_csEventlogLock);
  229. return;
  230. }
  231. nLastSourceID1 = SourceID1;
  232. LeaveCriticalSection(&g_csEventlogLock);
  233. DWORD cch;
  234. char strSource[MAX_MSG_LENGTH];
  235. char *aInsertStrs[MAX_INSERT_STRS]; // array of pointers to insert strings
  236. cch = CchLoadStringOfId(SourceID1, strSource, MAX_MSG_LENGTH);
  237. Assert(cch > 0);
  238. aInsertStrs[0] = (char*) strSource;
  239. ReportAnEvent( (DWORD) MSG_DENALI_ERROR_1, (WORD) EVENTLOG_ERROR_TYPE, (WORD) 1, (LPCSTR *) aInsertStrs );
  240. return;
  241. }
  242. /*===================================================================
  243. void MSG_Error( UINT SourcID1, UINT SourceID2 )
  244. report an event to the NT event log
  245. INPUT:
  246. two part message of string table string ID's
  247. Returns:
  248. None
  249. Side effects:
  250. Addes an entry in the NT event log
  251. ===================================================================*/
  252. void MSG_Error( UINT SourceID1, UINT SourceID2 )
  253. {
  254. static unsigned int nLastSourceID1;
  255. static unsigned int nLastSourceID2;
  256. // if this is a repeat of the last reported message then return
  257. // without posting an error.
  258. EnterCriticalSection(&g_csEventlogLock);
  259. if (SourceID1 == nLastSourceID1 && SourceID2 == nLastSourceID2)
  260. {
  261. LeaveCriticalSection(&g_csEventlogLock);
  262. return;
  263. }
  264. nLastSourceID1 = SourceID1;
  265. nLastSourceID2 = SourceID2;
  266. LeaveCriticalSection(&g_csEventlogLock);
  267. DWORD cch;
  268. char strSource[MAX_MSG_LENGTH];
  269. char *aInsertStrs[MAX_INSERT_STRS]; // array of pointers to insert strings
  270. cch = CchLoadStringOfId(SourceID1, strSource, MAX_MSG_LENGTH);
  271. Assert(cch > 0);
  272. aInsertStrs[0] = (char*) strSource;
  273. cch = CchLoadStringOfId(SourceID2, strSource, MAX_MSG_LENGTH);
  274. Assert(cch > 0);
  275. aInsertStrs[1] = (char*) strSource;
  276. ReportAnEvent( (DWORD) MSG_DENALI_ERROR_2, (WORD) EVENTLOG_ERROR_TYPE, (WORD) 2, (LPCSTR *) aInsertStrs );
  277. return;
  278. }
  279. /*===================================================================
  280. void MSG_Error( const char* pszError1, const char* pszError2, const char* pszError3)
  281. report an event to the NT event log
  282. INPUT:
  283. three part message string
  284. Returns:
  285. None
  286. Side effects:
  287. Addes an entry in the NT event log
  288. ===================================================================*/
  289. void MSG_Error( UINT SourceID1, UINT SourceID2, UINT SourceID3 )
  290. {
  291. static unsigned int nLastSourceID1;
  292. static unsigned int nLastSourceID2;
  293. static unsigned int nLastSourceID3;
  294. // if this is a repeat of the last reported message then return
  295. /// without posting an error.
  296. EnterCriticalSection(&g_csEventlogLock);
  297. if (SourceID1 == nLastSourceID1 && SourceID2 == nLastSourceID2 && SourceID3 == nLastSourceID3)
  298. {
  299. LeaveCriticalSection(&g_csEventlogLock);
  300. return;
  301. }
  302. nLastSourceID1 = SourceID1;
  303. nLastSourceID2 = SourceID2;
  304. nLastSourceID3 = SourceID3;
  305. LeaveCriticalSection(&g_csEventlogLock);
  306. DWORD cch;
  307. char strSource[MAX_MSG_LENGTH];
  308. char *aInsertStrs[MAX_INSERT_STRS]; // array of pointers to insert strings
  309. cch = CchLoadStringOfId(SourceID1, strSource, MAX_MSG_LENGTH);
  310. Assert(cch > 0);
  311. aInsertStrs[0] = (char*) strSource;
  312. cch = CchLoadStringOfId(SourceID2, strSource, MAX_MSG_LENGTH);
  313. Assert(cch > 0);
  314. aInsertStrs[1] = (char*) strSource;
  315. cch = CchLoadStringOfId(SourceID3, strSource, MAX_MSG_LENGTH);
  316. Assert(cch > 0);
  317. aInsertStrs[2] = (char*) strSource;
  318. ReportAnEvent( (DWORD) MSG_DENALI_ERROR_3, (WORD) EVENTLOG_ERROR_TYPE, (WORD) 3, (LPCSTR *) aInsertStrs );
  319. return;
  320. }
  321. /*===================================================================
  322. void MSG_Error( UINT SourcID1, UINT SourceID2, UINT SourceID3, UINT SourceID4 )
  323. report an event to the NT event log
  324. INPUT:
  325. four String table ID's
  326. Returns:
  327. None
  328. Side effects:
  329. Addes an entry in the NT event log
  330. ===================================================================*/
  331. void MSG_Error( UINT SourceID1, UINT SourceID2, UINT SourceID3, UINT SourceID4 )
  332. {
  333. static unsigned int nLastSourceID1;
  334. static unsigned int nLastSourceID2;
  335. static unsigned int nLastSourceID3;
  336. static unsigned int nLastSourceID4;
  337. // if this is a repeat of the last reported message then return
  338. /// without posting an error.
  339. EnterCriticalSection(&g_csEventlogLock);
  340. if (SourceID1 == nLastSourceID1 && SourceID2 == nLastSourceID2 && SourceID3 == nLastSourceID3 && SourceID4 == nLastSourceID4)
  341. {
  342. LeaveCriticalSection(&g_csEventlogLock);
  343. return;
  344. }
  345. nLastSourceID1 = SourceID1;
  346. nLastSourceID2 = SourceID2;
  347. nLastSourceID3 = SourceID3;
  348. nLastSourceID4 = SourceID4;
  349. LeaveCriticalSection(&g_csEventlogLock);
  350. DWORD cch;
  351. char strSource[MAX_MSG_LENGTH];
  352. char *aInsertStrs[MAX_INSERT_STRS]; // array of pointers to insert strings
  353. cch = CchLoadStringOfId(SourceID1, strSource, MAX_MSG_LENGTH);
  354. Assert(cch > 0);
  355. aInsertStrs[0] = (char*) strSource;
  356. cch = CchLoadStringOfId(SourceID2, strSource, MAX_MSG_LENGTH);
  357. Assert(cch > 0);
  358. aInsertStrs[1] = (char*) strSource;
  359. cch = CchLoadStringOfId(SourceID3, strSource, MAX_MSG_LENGTH);
  360. Assert(cch > 0);
  361. aInsertStrs[2] = (char*) strSource;
  362. cch = CchLoadStringOfId(SourceID4, strSource, MAX_MSG_LENGTH);
  363. Assert(cch > 0);
  364. aInsertStrs[3] = (char*) strSource;
  365. ReportAnEvent( (DWORD) MSG_DENALI_ERROR_4, (WORD) EVENTLOG_ERROR_TYPE, (WORD) 4, (LPCSTR *) aInsertStrs );
  366. return;
  367. }
  368. /*===================================================================
  369. void MSG_Warning( LPCSTR strSource )
  370. report an event to the NT event log
  371. INPUT:
  372. ptr to null-terminated string
  373. Returns:
  374. None
  375. Side effects:
  376. Addes an entry in the NT event log
  377. ===================================================================*/
  378. void MSG_Warning( LPCSTR strSource )
  379. {
  380. static char szLastError[MAX_MSG_LENGTH];
  381. EnterCriticalSection(&g_csEventlogLock);
  382. if (strcmp(strSource, szLastError) == 0)
  383. {
  384. LeaveCriticalSection(&g_csEventlogLock);
  385. return;
  386. }
  387. szLastError[0] = '\0';
  388. strncat(szLastError,strSource, MAX_MSG_LENGTH-1);
  389. LeaveCriticalSection(&g_csEventlogLock);
  390. ReportAnEvent( (DWORD) MSG_DENALI_WARNING_1, (WORD) EVENTLOG_WARNING_TYPE, (WORD) 1, &strSource /*aInsertStrs*/ );
  391. }
  392. /*===================================================================
  393. void MSG_Warning( UINT SourceID1)
  394. report an event to the NT event log
  395. INPUT:
  396. String table message ID
  397. Returns:
  398. None
  399. Side effects:
  400. Addes an entry in the NT event log
  401. ===================================================================*/
  402. void MSG_Warning( UINT SourceID1 )
  403. {
  404. static unsigned int nLastSourceID1;
  405. // if this is a repeat of the last reported message then return
  406. /// without posting an error.
  407. EnterCriticalSection(&g_csEventlogLock);
  408. if (SourceID1 == nLastSourceID1)
  409. {
  410. LeaveCriticalSection(&g_csEventlogLock);
  411. return;
  412. }
  413. nLastSourceID1 = SourceID1;
  414. LeaveCriticalSection(&g_csEventlogLock);
  415. DWORD cch;
  416. char strSource[MAX_MSG_LENGTH];
  417. char *aInsertStrs[MAX_INSERT_STRS]; // array of pointers to insert strings
  418. cch = CchLoadStringOfId(SourceID1, strSource, MAX_MSG_LENGTH);
  419. Assert(cch > 0);
  420. aInsertStrs[0] = (char*) strSource;
  421. ReportAnEvent( (DWORD) MSG_DENALI_WARNING_1, (WORD) EVENTLOG_WARNING_TYPE, (WORD) 1, (LPCSTR *) aInsertStrs );
  422. return;
  423. }
  424. /*===================================================================
  425. void MSG_Warning( UINT, SOurceID1, UINT SourceID2 )
  426. report an event to the NT event log
  427. INPUT:
  428. two string tabel message ID's
  429. Returns:
  430. None
  431. Side effects:
  432. Addes an entry in the NT event log
  433. ===================================================================*/
  434. void MSG_Warning( UINT SourceID1, UINT SourceID2 )
  435. {
  436. static unsigned int nLastSourceID1;
  437. static unsigned int nLastSourceID2;
  438. // if this is a repeat of the last reported message then return
  439. /// without posting an error.
  440. EnterCriticalSection(&g_csEventlogLock);
  441. if (SourceID1 == nLastSourceID1 && SourceID2 == nLastSourceID2)
  442. {
  443. LeaveCriticalSection(&g_csEventlogLock);
  444. return;
  445. }
  446. nLastSourceID1 = SourceID1;
  447. nLastSourceID2 = SourceID2;
  448. LeaveCriticalSection(&g_csEventlogLock);
  449. DWORD cch;
  450. char strSource[MAX_MSG_LENGTH];
  451. char *aInsertStrs[MAX_INSERT_STRS]; // array of pointers to insert strings
  452. cch = CchLoadStringOfId(SourceID1, strSource, MAX_MSG_LENGTH);
  453. Assert(cch > 0);
  454. aInsertStrs[0] = (char*) strSource;
  455. cch = CchLoadStringOfId(SourceID2, strSource, MAX_MSG_LENGTH);
  456. Assert(cch > 0);
  457. aInsertStrs[1] = (char*) strSource;
  458. ReportAnEvent( (DWORD) MSG_DENALI_WARNING_2, (WORD) EVENTLOG_WARNING_TYPE, (WORD) 2, (LPCSTR *) aInsertStrs );
  459. return;
  460. }
  461. /*===================================================================
  462. void MSG_Warning( UINT SourceID1, UINT SourceID2, UINT SourceID3 )
  463. report an event to the NT event log
  464. INPUT:
  465. three string table message ID's
  466. Returns:
  467. None
  468. Side effects:
  469. Addes an entry in the NT event log
  470. ===================================================================*/
  471. void MSG_Warning( UINT SourceID1, UINT SourceID2, UINT SourceID3)
  472. {
  473. static unsigned int nLastSourceID1;
  474. static unsigned int nLastSourceID2;
  475. static unsigned int nLastSourceID3;
  476. // if this is a repeat of the last reported message then return
  477. /// without posting an error.
  478. EnterCriticalSection(&g_csEventlogLock);
  479. if (SourceID1 == nLastSourceID1 && SourceID2 == nLastSourceID2 && SourceID3 == nLastSourceID3)
  480. {
  481. LeaveCriticalSection(&g_csEventlogLock);
  482. return;
  483. }
  484. nLastSourceID1 = SourceID1;
  485. nLastSourceID2 = SourceID2;
  486. nLastSourceID3 = SourceID3;
  487. LeaveCriticalSection(&g_csEventlogLock);
  488. DWORD cch;
  489. char strSource[MAX_MSG_LENGTH];
  490. char *aInsertStrs[MAX_INSERT_STRS]; // array of pointers to insert strings
  491. cch = CchLoadStringOfId(SourceID1, strSource, MAX_MSG_LENGTH);
  492. Assert(cch > 0);
  493. aInsertStrs[0] = (char*) strSource;
  494. cch = CchLoadStringOfId(SourceID2, strSource, MAX_MSG_LENGTH);
  495. Assert(cch > 0);
  496. aInsertStrs[1] = (char*) strSource;
  497. cch = CchLoadStringOfId(SourceID3, strSource, MAX_MSG_LENGTH);
  498. Assert(cch > 0);
  499. aInsertStrs[2] = (char*) strSource;
  500. ReportAnEvent( (DWORD) MSG_DENALI_WARNING_3, (WORD) EVENTLOG_WARNING_TYPE, (WORD) 3, (LPCSTR *) aInsertStrs );
  501. return;
  502. }
  503. /*===================================================================
  504. void MSG_Warning( UINT SourceID1, UINT SourceID2, UINT SourceID3, UINT SourceID4 )
  505. report an event to the NT event log
  506. INPUT:
  507. four String table message ID's
  508. Returns:
  509. None
  510. Side effects:
  511. Addes an entry in the NT event log
  512. ===================================================================*/
  513. void MSG_Warning( UINT SourceID1, UINT SourceID2, UINT SourceID3, UINT SourceID4 )
  514. {
  515. static unsigned int nLastSourceID1;
  516. static unsigned int nLastSourceID2;
  517. static unsigned int nLastSourceID3;
  518. static unsigned int nLastSourceID4;
  519. // if this is a repeat of the last reported message then return
  520. /// without posting an error.
  521. EnterCriticalSection(&g_csEventlogLock);
  522. if (SourceID1 == nLastSourceID1 && SourceID2 == nLastSourceID2 && SourceID3 == nLastSourceID3 && SourceID4 == nLastSourceID4)
  523. {
  524. LeaveCriticalSection(&g_csEventlogLock);
  525. return;
  526. }
  527. nLastSourceID1 = SourceID1;
  528. nLastSourceID2 = SourceID2;
  529. nLastSourceID3 = SourceID3;
  530. nLastSourceID4 = SourceID4;
  531. LeaveCriticalSection(&g_csEventlogLock);
  532. DWORD cch;
  533. char strSource[MAX_MSG_LENGTH];
  534. char *aInsertStrs[MAX_INSERT_STRS]; // array of pointers to insert strings
  535. cch = CchLoadStringOfId(SourceID1, strSource, MAX_MSG_LENGTH);
  536. Assert(cch > 0);
  537. aInsertStrs[0] = (char*) strSource;
  538. cch = CchLoadStringOfId(SourceID2, strSource, MAX_MSG_LENGTH);
  539. Assert(cch > 0);
  540. aInsertStrs[1] = (char*) strSource;
  541. cch = CchLoadStringOfId(SourceID3, strSource, MAX_MSG_LENGTH);
  542. Assert(cch > 0);
  543. aInsertStrs[2] = (char*) strSource;
  544. cch = CchLoadStringOfId(SourceID4, strSource, MAX_MSG_LENGTH);
  545. Assert(cch > 0);
  546. aInsertStrs[3] = (char*) strSource;
  547. ReportAnEvent( (DWORD) MSG_DENALI_WARNING_4, (WORD) EVENTLOG_WARNING_TYPE, (WORD) 4, (LPCSTR *) aInsertStrs );
  548. return;
  549. }
  550. /*===================================================================
  551. void MSG_Warning( UINT ErrId, UINT cItem, CHAR **szItems )
  552. report an event to the NT event log
  553. INPUT:
  554. four String table message ID's
  555. Returns:
  556. None
  557. Side effects:
  558. Addes an entry in the NT event log
  559. ===================================================================*/
  560. void MSG_Warning( UINT ErrId, UINT cItem, CHAR **szItems )
  561. {
  562. static unsigned int LastErrId;
  563. // if this is a repeat of the last reported message then return
  564. /// without posting an error.
  565. EnterCriticalSection(&g_csEventlogLock);
  566. if (ErrId == LastErrId)
  567. {
  568. LeaveCriticalSection(&g_csEventlogLock);
  569. return;
  570. }
  571. LastErrId = ErrId;
  572. LeaveCriticalSection(&g_csEventlogLock);
  573. MSG_Warning(ErrId);
  574. ReportAnEvent( (DWORD) MSG_DENALI_WARNING_4, (WORD) EVENTLOG_WARNING_TYPE, (WORD) cItem, (LPCSTR *) szItems );
  575. }