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.

509 lines
17 KiB

  1. `**********************************************************************`
  2. `* This is an include template file for tracewpp preprocessor. *`
  3. `* *`
  4. `* Copyright 1999-2001 Microsoft Corporation. All Rights Reserved. *`
  5. `**********************************************************************`
  6. // template `TemplateFile`
  7. //
  8. // Defines a set of functions that simplifies
  9. // kernel mode registration for tracing
  10. //
  11. #if !defined(WppDebug)
  12. # define WppDebug(a,b)
  13. #endif
  14. #define WMIREG_FLAG_CALLBACK 0x80000000 // not exposed in DDK
  15. #ifndef WPPINIT_EXPORT
  16. # define WPPINIT_EXPORT
  17. #endif
  18. #ifdef WPP_GLOBALLOGGER
  19. WPPINIT_EXPORT
  20. void WppIntToHex(
  21. LPWSTR Buf,
  22. unsigned int value,
  23. int digits
  24. )
  25. {
  26. static LPCWSTR hexDigit = L"0123456789abcdef";
  27. while (--digits >= 0) {
  28. Buf[digits] = hexDigit[ value & 15 ];
  29. value /= 16; // compiler is smart enough to change it to bitshift
  30. }
  31. }
  32. #define WPP_TEXTGUID_LEN 37
  33. // b1e5deaf-1524-4a04-82c4-c9dfbce6cf97<NULL>
  34. // 0 1 2 3
  35. // 0123456789012345678901234567890123456
  36. WPPINIT_EXPORT
  37. void WppGuidToStr(LPWSTR buf, LPCGUID guid) {
  38. WppIntToHex(buf + 0, guid->Data1, 8);
  39. buf[8] = '-';
  40. WppIntToHex(buf + 9, guid->Data2, 4);
  41. buf[13] = '-';
  42. WppIntToHex(buf + 14, guid->Data3, 4);
  43. buf[18] = '-';
  44. WppIntToHex(buf + 19, guid->Data4[0], 2);
  45. WppIntToHex(buf + 21, guid->Data4[1], 2);
  46. buf[23] = '-';
  47. WppIntToHex(buf + 24, guid->Data4[2], 2);
  48. WppIntToHex(buf + 26, guid->Data4[3], 2);
  49. WppIntToHex(buf + 28, guid->Data4[4], 2);
  50. WppIntToHex(buf + 30, guid->Data4[5], 2);
  51. WppIntToHex(buf + 32, guid->Data4[6], 2);
  52. WppIntToHex(buf + 34, guid->Data4[7], 2);
  53. buf[36] = 0;
  54. }
  55. #define GREGVALUENAMELENGTH 18 + WPP_TEXTGUID_LEN + 1 // wslen(L"WMI\\GlobalLogger\\") + GUIDLENGTH
  56. WPPINIT_EXPORT
  57. void WppInitGlobalLogger(
  58. LPCGUID pControlGuid,
  59. PTRACEHANDLE pLogger,
  60. PULONG pFlags,
  61. PUCHAR pLevel )
  62. {
  63. WCHAR GRegValueName[GREGVALUENAMELENGTH] ; // L"WMI\\GlobalLogger\\d58c126f-b309-11d1-969e-0000f875a5bc" ;
  64. RTL_QUERY_REGISTRY_TABLE parms[3];
  65. ULONG Lflags = 0,
  66. Llevel = 0,
  67. Lstart = 0;
  68. NTSTATUS status ;
  69. ULONG aZero = 0 ;
  70. WppDebug(0,("WPP checking Global Logger"));
  71. swprintf(GRegValueName,L"WMI\\GlobalLogger\\");
  72. //
  73. // Fill in the query table to find out if the Global Logger is Started
  74. //
  75. // Trace Flags
  76. parms[0].QueryRoutine = NULL ;
  77. parms[0].Flags = RTL_QUERY_REGISTRY_DIRECT;
  78. parms[0].Name = L"Start";
  79. parms[0].EntryContext = &Lstart;
  80. parms[0].DefaultType = REG_DWORD;
  81. parms[0].DefaultData = &aZero;
  82. parms[0].DefaultLength = sizeof(ULONG);
  83. // Termination
  84. parms[1].QueryRoutine = NULL ;
  85. parms[1].Flags = 0 ;
  86. //
  87. // Perform the query
  88. //
  89. status = RtlQueryRegistryValues(RTL_REGISTRY_CONTROL | RTL_REGISTRY_OPTIONAL,
  90. GRegValueName,
  91. parms,
  92. NULL,
  93. NULL);
  94. if (!NT_SUCCESS(status) || Lstart == 0 ) {
  95. return ;
  96. }
  97. // Fill in the query table to find out if we should use the Global logger
  98. //
  99. // Trace Flags
  100. parms[0].QueryRoutine = NULL ;
  101. parms[0].Flags = RTL_QUERY_REGISTRY_DIRECT;
  102. parms[0].Name = L"Flags";
  103. parms[0].EntryContext = &Lflags;
  104. parms[0].DefaultType = REG_DWORD;
  105. parms[0].DefaultData = &aZero;
  106. parms[0].DefaultLength = sizeof(ULONG);
  107. // Trace level
  108. parms[1].QueryRoutine = NULL ;
  109. parms[1].Flags = RTL_QUERY_REGISTRY_DIRECT;
  110. parms[1].Name = L"Level";
  111. parms[1].EntryContext = &Llevel;
  112. parms[1].DefaultType = REG_DWORD;
  113. parms[1].DefaultData = &aZero;
  114. parms[1].DefaultLength = sizeof(UCHAR);
  115. // Termination
  116. parms[2].QueryRoutine = NULL ;
  117. parms[2].Flags = 0 ;
  118. WppGuidToStr(&GRegValueName[wcslen(GRegValueName)], pControlGuid) ;
  119. //
  120. // Perform the query
  121. //
  122. status = RtlQueryRegistryValues(RTL_REGISTRY_CONTROL | RTL_REGISTRY_OPTIONAL,
  123. GRegValueName,
  124. parms,
  125. NULL,
  126. NULL);
  127. if (NT_SUCCESS(status)) {
  128. if (Lstart==1) {
  129. *pLogger= WMI_GLOBAL_LOGGER_ID ;
  130. *pFlags = Lflags & 0x7FFFFFFF ;
  131. *pLevel = (UCHAR)(Llevel & 0xFF) ;
  132. WppDebug(0,("WPP Enabled via Global Logger Flags=0x%08X Level=0x%02X",Lflags,Llevel));
  133. }
  134. }
  135. }
  136. #endif //#ifdef WPP_GLOBALLOGGER
  137. WPPINIT_EXPORT
  138. NTSTATUS
  139. WppTraceCallback(
  140. IN UCHAR minorFunction,
  141. IN PVOID DataPath,
  142. IN ULONG BufferLength,
  143. IN PVOID Buffer,
  144. IN PVOID Context,
  145. OUT PULONG Size
  146. )
  147. /*++
  148. Routine Description:
  149. Callback routine for IoWMIRegistrationControl.
  150. Arguments:
  151. Return Value:
  152. status
  153. Comments:
  154. if return value is STATUS_BUFFER_TOO_SMALL and BufferLength >= 4,
  155. then first ulong of buffer contains required size
  156. --*/
  157. {
  158. WPP_PROJECT_CONTROL_BLOCK *cb = (WPP_PROJECT_CONTROL_BLOCK*)Context;
  159. NTSTATUS status = STATUS_SUCCESS;
  160. UNREFERENCED_PARAMETER(DataPath);
  161. WppDebug(0,("WppTraceCallBack 0x%08X %p\n", minorFunction, Context));
  162. *Size = 0;
  163. switch(minorFunction)
  164. {
  165. case IRP_MN_REGINFO:
  166. {
  167. PWMIREGINFOW wmiRegInfo;
  168. PCUNICODE_STRING regPath;
  169. PWCHAR stringPtr;
  170. ULONG registryPathOffset;
  171. ULONG bufferNeeded;
  172. UNICODE_STRING nullRegistryPath;
  173. #if defined(WPP_TRACE_W2K_COMPATABILITY)
  174. wmiRegInfo = (PWMIREGINFO)Buffer;
  175. if (wmiRegInfo->GuidCount >= 1) {
  176. // Replace the null trace GUID with the driver's trace control GUID
  177. wmiRegInfo->WmiRegGuid[wmiRegInfo->GuidCount-1].Guid = *cb->Registration.ControlGuid;
  178. wmiRegInfo->WmiRegGuid[wmiRegInfo->GuidCount-1].Flags =
  179. WMIREG_FLAG_TRACE_CONTROL_GUID | WMIREG_FLAG_TRACED_GUID;
  180. *Size= wmiRegInfo->BufferSize;
  181. status = STATUS_SUCCESS;
  182. #ifdef WPP_GLOBALLOGGER
  183. // Check if Global logger is active
  184. WppInitGlobalLogger(cb->Registration.ControlGuid,
  185. (PTRACEHANDLE)&cb->Control.Logger,
  186. &cb->Control.Flags[0],
  187. &cb->Control.Level);
  188. #endif //#ifdef WPP_GLOBALLOGGER
  189. break;
  190. }
  191. #endif
  192. regPath = cb->Registration.RegistryPath;
  193. if (regPath == NULL)
  194. {
  195. // No registry path specified. This is a bad thing for
  196. // the device to do, but is not fatal
  197. RtlInitUnicodeString(&nullRegistryPath, NULL);
  198. regPath = &nullRegistryPath;
  199. }
  200. registryPathOffset = FIELD_OFFSET(WMIREGINFOW, WmiRegGuid)
  201. + 1 * sizeof(WMIREGGUIDW);
  202. bufferNeeded = registryPathOffset +
  203. regPath->Length + sizeof(USHORT);
  204. if (bufferNeeded <= BufferLength)
  205. {
  206. RtlZeroMemory(Buffer, BufferLength);
  207. wmiRegInfo = (PWMIREGINFO)Buffer;
  208. wmiRegInfo->BufferSize = bufferNeeded;
  209. wmiRegInfo->RegistryPath = registryPathOffset;
  210. wmiRegInfo->GuidCount = 1;
  211. wmiRegInfo->WmiRegGuid[0].Guid = *cb->Registration.ControlGuid;
  212. wmiRegInfo->WmiRegGuid[0].Flags =
  213. WMIREG_FLAG_TRACE_CONTROL_GUID | WMIREG_FLAG_TRACED_GUID;
  214. stringPtr = (PWCHAR)((PUCHAR)Buffer + registryPathOffset);
  215. *stringPtr++ = regPath->Length;
  216. RtlCopyMemory(stringPtr,
  217. regPath->Buffer,
  218. regPath->Length);
  219. status = STATUS_SUCCESS;
  220. *Size = bufferNeeded;
  221. } else {
  222. status = STATUS_BUFFER_TOO_SMALL;
  223. if (BufferLength >= sizeof(ULONG)) {
  224. *((PULONG)Buffer) = bufferNeeded;
  225. *Size = sizeof(ULONG);
  226. }
  227. }
  228. #ifdef WPP_GLOBALLOGGER
  229. // Check if Global logger is active
  230. WppInitGlobalLogger(cb->Registration.ControlGuid,
  231. (PTRACEHANDLE)&cb->Control.Logger,
  232. &cb->Control.Flags[0],
  233. &cb->Control.Level);
  234. #endif //#ifdef WPP_GLOBALLOGGER
  235. break;
  236. }
  237. case IRP_MN_ENABLE_EVENTS:
  238. case IRP_MN_DISABLE_EVENTS:
  239. {
  240. PWNODE_HEADER Wnode = (PWNODE_HEADER)Buffer;
  241. ULONG Level;
  242. ULONG ReturnLength ;
  243. if (cb == NULL )
  244. {
  245. status = STATUS_WMI_GUID_NOT_FOUND;
  246. break;
  247. }
  248. if (BufferLength >= sizeof(WNODE_HEADER)) {
  249. status = STATUS_SUCCESS;
  250. if (minorFunction == IRP_MN_DISABLE_EVENTS) {
  251. cb->Control.Level = 0;
  252. cb->Control.Flags[0] = 0;
  253. cb->Control.Logger = 0;
  254. } else {
  255. TRACEHANDLE lh;
  256. lh = (TRACEHANDLE)( Wnode->HistoricalContext );
  257. cb->Control.Logger = lh;
  258. #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  259. if ((status = WmiQueryTraceInformation( TraceEnableLevelClass,
  260. &Level,
  261. sizeof(Level),
  262. &ReturnLength,
  263. (PVOID)Wnode)) == STATUS_SUCCESS)
  264. {
  265. cb->Control.Level = (UCHAR)Level;
  266. }
  267. status = WmiQueryTraceInformation( TraceEnableFlagsClass,
  268. &cb->Control.Flags[0],
  269. sizeof(cb->Control.Flags[0]),
  270. &ReturnLength,
  271. (PVOID)Wnode);
  272. #else // #ifndef WPP_TRACE_W2K_COMPATABILITY
  273. cb->Control.Flags[0] = WmiGetLoggerEnableFlags(lh) ;
  274. cb->Control.Level = (UCHAR)WmiGetLoggerEnableLevel(lh) ;
  275. WppDebug(0,("Enable/Disable Logger = %p, Flags = 0x%8x, Level = %x08X\n",
  276. cb->Control.Logger,cb->Control.Flags[0],cb->Control.Level));
  277. #endif // #ifndef WPP_TRACE_W2K_COMPATABILITY
  278. }
  279. } else {
  280. status = STATUS_INVALID_PARAMETER;
  281. }
  282. break;
  283. }
  284. case IRP_MN_ENABLE_COLLECTION:
  285. case IRP_MN_DISABLE_COLLECTION:
  286. {
  287. status = STATUS_SUCCESS;
  288. break;
  289. }
  290. case IRP_MN_QUERY_ALL_DATA:
  291. case IRP_MN_QUERY_SINGLE_INSTANCE:
  292. case IRP_MN_CHANGE_SINGLE_INSTANCE:
  293. case IRP_MN_CHANGE_SINGLE_ITEM:
  294. case IRP_MN_EXECUTE_METHOD:
  295. {
  296. status = STATUS_INVALID_DEVICE_REQUEST;
  297. break;
  298. }
  299. default:
  300. {
  301. status = STATUS_INVALID_DEVICE_REQUEST;
  302. break;
  303. }
  304. }
  305. // DbgPrintEx(XX_FLTR, DPFLTR_TRACE_LEVEL,
  306. // "%!FUNC!(%!SYSCTRL!) => %!status! (size = %d)", minorFunction, status, *Size);
  307. return(status);
  308. }
  309. WPPINIT_EXPORT
  310. void WppInitKm(
  311. #if defined(WPP_TRACE_W2K_COMPATABILITY)
  312. IN PDEVICE_OBJECT pDevObject,
  313. #endif // #if defined(WPP_TRACE_W2K_COMPATABILITY)
  314. IN PUNICODE_STRING RegistryPath,
  315. IN OUT WPP_REGISTRATION_BLOCK* WppReg
  316. )
  317. {
  318. RegistryPath; // unused
  319. while(WppReg) {
  320. WPP_TRACE_CONTROL_BLOCK *cb = (WPP_TRACE_CONTROL_BLOCK*)WppReg;
  321. NTSTATUS status ;
  322. #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  323. WppReg -> Callback = WppTraceCallback;
  324. #else // #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  325. WppReg -> Callback = NULL ;
  326. #endif // #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  327. WppReg -> RegistryPath = NULL;
  328. cb -> FlagsLen = WppReg -> FlagsLen;
  329. cb -> Level = 0;
  330. cb -> Flags[0] = 0;
  331. #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  332. status = IoWMIRegistrationControl((PDEVICE_OBJECT)WppReg,
  333. WMIREG_ACTION_REGISTER | WMIREG_FLAG_CALLBACK
  334. #else // #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  335. status = IoWMIRegistrationControl(pDevObject,
  336. WMIREG_ACTION_REGISTER
  337. #endif // #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  338. );
  339. WppDebug(0,("IoWMIRegistrationControl status = %08X\n"));
  340. WppReg = WppReg->Next;
  341. }
  342. }
  343. #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  344. WPPINIT_EXPORT
  345. void WppCleanupKm(
  346. WPP_REGISTRATION_BLOCK* WppReg
  347. )
  348. {
  349. while (WppReg) {
  350. IoWMIRegistrationControl((PDEVICE_OBJECT)WppReg, WMIREG_ACTION_DEREGISTER | WMIREG_FLAG_CALLBACK );
  351. WppReg = WppReg -> Next;
  352. }
  353. }
  354. #else // #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  355. WPPINIT_EXPORT
  356. void WppCleanupKm(
  357. PDEVICE_OBJECT pDO
  358. )
  359. {
  360. IoWMIRegistrationControl(pDO, WMIREG_ACTION_DEREGISTER );
  361. }
  362. #endif // #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  363. #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  364. #define WPP_SYSTEMCONTROL(PDO)
  365. #define WPP_SYSTEMCONTROL2(PDO, offset)
  366. #else // #if !defined(WPP_TRACE_W2K_COMPATABILITY)
  367. ULONG_PTR WPP_Global_NextDeviceOffsetInDeviceExtension = -1;
  368. #define WPP_SYSTEMCONTROL(PDO) \
  369. PDO->MajorFunction[ IRP_MJ_SYSTEM_CONTROL ] = WPPSystemControlDispatch;
  370. #define WPP_SYSTEMCONTROL2(PDO, offset) \
  371. WPP_SYSTEMCONTROL(PDO); WPP_Global_NextDeviceOffsetInDeviceExtension = (ULONG_PTR)offset;
  372. // Routine to handle the System Control in W2K
  373. NTSTATUS
  374. WPPSystemControlDispatch(
  375. IN PDEVICE_OBJECT pDO,
  376. IN PIRP Irp
  377. );
  378. #ifdef ALLOC_PRAGMA
  379. #pragma alloc_text( PAGE, WPPSystemControlDispatch)
  380. #endif // ALLOC_PRAGMA
  381. // Routine to handle the System Control in W2K
  382. NTSTATUS
  383. WPPSystemControlDispatch(
  384. IN PDEVICE_OBJECT pDO,
  385. IN PIRP Irp
  386. )
  387. {
  388. PIO_STACK_LOCATION irpSp = IoGetCurrentIrpStackLocation(Irp);
  389. ULONG BufferSize = irpSp->Parameters.WMI.BufferSize;
  390. PVOID Buffer = irpSp->Parameters.WMI.Buffer;
  391. ULONG ReturnSize = 0;
  392. NTSTATUS Status = STATUS_SUCCESS;
  393. PWNODE_HEADER Wnode=NULL;
  394. HANDLE ThreadHandle;
  395. WppDebug(0,("WPPSYSTEMCONTROL\n"));
  396. if (pDO == (PDEVICE_OBJECT)irpSp->Parameters.WMI.ProviderId) {
  397. #if defined(WPP_TRACE_W2K_COMPATABILITY)
  398. //To differentiate between the case where wmilib has already filled in parts of the buffer
  399. if (irpSp->MinorFunction == IRP_MN_REGINFO) RtlZeroMemory(Buffer, BufferSize);
  400. #endif
  401. Status = WppTraceCallback((UCHAR)(irpSp->MinorFunction),
  402. NULL,
  403. BufferSize,
  404. Buffer,
  405. &WPP_CB[0],
  406. &ReturnSize);
  407. WppDebug(0,("WPPSYSTEMCONTROL Status 0x%08X\n",Status));
  408. Irp->IoStatus.Status = Status;
  409. Irp->IoStatus.Information = ReturnSize;
  410. IoCompleteRequest( Irp, IO_NO_INCREMENT );
  411. return Status;
  412. } else if (WPP_Global_NextDeviceOffsetInDeviceExtension != -1) {
  413. ULONG_PTR t;
  414. WppDebug(0,("WPPSYSTEMCONTROL - not for us\n"));
  415. //
  416. // Set current stack back one.
  417. //
  418. IoSkipCurrentIrpStackLocation( Irp );
  419. //
  420. // Pass the call to the next driver.
  421. //
  422. t = (ULONG_PTR)pDO->DeviceExtension;
  423. t += WPP_Global_NextDeviceOffsetInDeviceExtension;
  424. return IoCallDriver((PDEVICE_OBJECT)t,Irp);
  425. } else {
  426. //unable to pass down -- what to do?
  427. //don't change irp status - IO defaults to failure
  428. return Irp->IoStatus.Status;
  429. }
  430. }
  431. #endif // #if !defined(WPP_TRACE_W2K_COMPATABILITY)