win_etw_metadata/
lib.rs

1//! Definitions for metadata used by
2//! [Event Tracing for Windows](https://docs.microsoft.com/en-us/windows/win32/etw/event-tracing-portal).
3//!
4//! These definitions are used by the `win_etw_macros` crate to describe the schema of events.
5//! Most applications will not need to use these definitions directly.
6
7#![no_std]
8#![deny(missing_docs)]
9
10use bitflags::bitflags;
11
12/// This structure describes the start of the ETW metadata section. A single static instance of
13/// this structure is placed in PE/COFF modules, and it identifies the start of the ETW metadata
14/// section. In this implementation, that single instance is `ETW_TRACE_LOGGING_METADATA`.
15#[repr(C)]
16pub struct TraceLoggingMetadata {
17    signature: u32, // = _tlg_MetadataSignature = "ETW0"
18    size: u16,      // = sizeof(_TraceLoggingMetadata_t)
19    version: u8,    // = _tlg_MetadataVersion
20    flags: u8,      // = _tlg_MetadataFlags
21    magic: u64,     // = _tlg_MetadataMagic
22}
23
24/// The value stored in `TraceLoggingMetadata::signature`.
25/// In little-endian ASCII, this is "ETW0".
26pub const METADATA_SIGNATURE: u32 = 0x30_57_54_45;
27
28/// The value stored in `TraceLoggingMetadata::magic`.
29pub const METADATA_MAGIC: u64 = 0xBB8A_052B_8804_0E86;
30
31/// The version of the metadata emitted. Currently, there is only one version.
32pub const METADATA_VERSION: u8 = 0;
33
34/// The bit flag which indicates the size of pointers on the target architecture.
35/// The value of this constant depends on the target architecture.
36#[cfg(target_pointer_width = "64")]
37pub const METADATA_FLAGS_POINTER_WIDTH: u8 = 1;
38
39/// The bit flag which indicates the size of pointers on the target architecture.
40/// The value of this constant depends on the target architecture.
41#[cfg(not(target_pointer_width = "64"))]
42pub const METADATA_FLAGS_POINTER_WIDTH: u8 = 0;
43
44#[cfg(feature = "metadata_headers")]
45#[link_section = ".rdata$etw0"]
46#[used]
47#[no_mangle]
48static ETW_TRACE_LOGGING_METADATA: TraceLoggingMetadata = TraceLoggingMetadata {
49    signature: METADATA_SIGNATURE,
50    size: core::mem::size_of::<TraceLoggingMetadata>() as u16,
51    version: METADATA_VERSION,
52    flags: METADATA_FLAGS_POINTER_WIDTH,
53    magic: METADATA_MAGIC,
54};
55
56/// Predefined event tracing levels
57#[repr(transparent)]
58#[derive(Copy, Clone, Eq, PartialEq, Hash, Ord, PartialOrd)]
59pub struct Level(pub u8);
60
61impl Level {
62    /// Tracing is not on
63    pub const NONE: Level = Level(0);
64    /// Abnormal exit or termination
65    pub const CRITICAL: Level = Level(1);
66    /// Deprecated name for Abnormal exit or termination
67    pub const FATAL: Level = Level(1);
68    /// Severe errors that need logging
69    pub const ERROR: Level = Level(2);
70    /// Warnings such as allocation failure
71    pub const WARN: Level = Level(3);
72    /// Includes non-error cases(e.g.,Entry-Exit)
73    pub const INFO: Level = Level(4);
74    /// Detailed traces from intermediate steps
75    pub const VERBOSE: Level = Level(5);
76}
77
78bitflags! {
79    /// Defines the input type of a field.
80    /// In traceloggingprovider.h, this is the 'TlgIn_t` enumerated type.
81    #[repr(transparent)]
82    pub struct InFlag: u8 {
83        /// No value at all
84        const NULL = 0;
85        /// A wide string (UTF-16), corresponding to `PCWSTR` in Win32.
86        const UNICODE_STRING = 1;
87        /// An ANSI string, corresponding to `PCSTR` in Win32.
88        /// The character set can be specified as UTF-8 by using `OutFlag::UTF8`.
89        const ANSI_STRING = 2;
90        /// `i8`
91        const INT8 = 3;
92        /// `u8`
93        const UINT8 = 4;
94        /// `i16`, stored in little-endian form.
95        const INT16 = 5;
96        /// `u16`, stored in little-endian form.
97        const UINT16 = 6;
98        /// `i16`, stored in little-endian form.
99        const INT32 = 7;
100        /// `u32`, stored in little-endian form.
101        const UINT32 = 8;
102        /// `i64`, stored in little-endian form.
103        const INT64 = 9;
104        /// `u64`, stored in little-endian form.
105        const UINT64 = 10;
106        /// `f32`, stored in little-endian form.
107        const FLOAT = 11;
108        /// `f64`, stored in little-endian form.
109        const DOUBLE = 12;
110        /// A Win32 'BOOL' value, which is `i32`, stored in little-endian form.
111        const BOOL32 = 13;
112        /// An array of bytes, stored in little-endian form.
113        const BINARY = 14;
114        /// A `GUID`, stored in canonical byte-oriented representation. The fields within the `GUID`
115        /// are stored in big-endian form.
116        const GUID = 15;
117        // POINTER (16) is not supported
118        /// A Win32 [`FILETIME`](https://docs.microsoft.com/en-us/windows/win32/api/minwinbase/ns-minwinbase-filetime)
119        /// value. `FILETIME` values are `u64` values, stored in little-endian form, counting 100ns
120        /// intervals from the `FILETIME` epoch.
121        const FILETIME = 17;
122        /// A Win32 [`SYSTEMTIME`](https://docs.microsoft.com/en-us/windows/win32/api/minwinbase/ns-minwinbase-systemtime)
123        /// value, with fields encoded in little-endian form.
124        const SYSTEMTIME = 18;
125        /// A Win32 [`SID`](https://docs.microsoft.com/en-us/windows/win32/api/winnt/ns-winnt-sid).
126        const SID = 19;
127        /// An `i32` value, encoded in little-endian form, displayed in hexadecimal.
128        const HEXINT32 = 20;
129        /// An `i64` value, encoded in little-endian form, displayed in hexadecimal.
130        const HEXINT64 = 21;
131        /// A counted wide string (UTF-16), corresponding to `UNICODE_STRING` in Win32.
132        /// This type uses two data descriptor slots. The first is a `u16` value, giving the
133        /// length of the string data in WCHAR units (not bytes). The second points to the
134        /// character data.
135        const COUNTED_UNICODE_STRING = 22;
136        /// A counted ANSI string, corresponding to `STRING` in Win32.
137        /// The character set can be specified as UTF-8 by using `OutFlag::UTF8`.
138        /// This type uses two data descriptor slots. The first is a `u16` value, giving the
139        /// length of the string data in WCHAR units (not bytes). The second points to the
140        /// character data.
141        const COUNTED_ANSI_STRING = 23;
142        /// A flag which indicates that this field is an array of constant length.
143        /// If this field is present, then the metadata contains an additional `u16` field, which
144        /// is the constant length.
145        const CCOUNT_FLAG = 0x20;
146        /// A flag which indicates that this field has a dynamic length. The field uses two
147        /// data descriptors. The first is a `u16` field specifying the length of the array.
148        /// The second points to the array data.
149        const VCOUNT_FLAG = 0x40;
150        /// A flag which indicates that this field metadata also includes an `OutFlag`. The
151        /// `OutFlag` byte immediately follows the `InFlag` byte.
152        const CHAIN_FLAG = 0b1000_0000;
153        /// A flag which indicates that the field uses a custom serializer.
154        const CUSTOM_FLAG = 0b0110_0000;
155        /// A mask of the field type flags.
156        const TYPE_MASK = 0b0001_1111;
157        /// A mask of the field length flags (`VCOUNT_FLAG`, `CCOUNT_FLAG`, `CUSTOM_FLAG`).
158        const COUNT_MASK = 0b0110_0000;
159        /// A mask over all of the flags (all bits excluding the type bits).
160        const FLAG_MASK = 0b1110_0000;
161    }
162}
163
164impl InFlag {
165    /// An alias for the architecture-dependent `USIZE` (pointer-sized word) `InFlag`.
166    #[cfg(target_pointer_width = "32")]
167    pub const USIZE: InFlag = InFlag::UINT32;
168
169    /// An alias for the architecture-dependent `ISIZE` (pointer-sized word) `InFlag`.
170    #[cfg(target_pointer_width = "32")]
171    pub const ISIZE: InFlag = InFlag::INT32;
172
173    /// An alias for the architecture-dependent `USIZE` (pointer-sized word) `InFlag`.
174    #[cfg(target_pointer_width = "64")]
175    pub const USIZE: InFlag = InFlag::UINT64;
176
177    /// An alias for the architecture-dependent `ISIZE` (pointer-sized word) `InFlag`.
178    #[cfg(target_pointer_width = "64")]
179    pub const ISIZE: InFlag = InFlag::INT64;
180}
181
182bitflags! {
183    /// Specifies how a field should be interpreted or displayed.
184    #[repr(transparent)]
185    pub struct OutFlag: u8 {
186        /// No display at all.
187        const NULL = 0;
188        /// No display at all.
189        const NOPRINT = 1;
190        /// Contains text.
191        const STRING = 2;
192        /// Is a boolean. This can only be used with `InFlag::INT8`.
193        const BOOLEAN = 3;
194        /// Display in hexadecimal. Can be used with any integer type.
195        const HEX = 4;
196        /// The field is a Win32 process ID.
197        const PID = 5;
198        /// The field is a Win32 thread ID.
199        const TID = 6;
200        /// The field is a TCP/IP or UDP/IP port, in big-endian encoding.
201        const PORT =  7;
202        /// The field is an IP v4 address, in big-endian encoding.
203        const IPV4 = 8;
204        /// The field is an IP v6 address, in big-endian encoding.
205        const IPV6 = 9;
206        /// The field is a `SOCKADDR`. See `[SOCKADDR](https://docs.microsoft.com/en-us/windows/win32/api/winsock/ns-winsock-sockaddr)`.
207        const SOCKETADDRESS = 10;
208        /// The field is text, and should be interpreted as XML.
209        const XML = 11;
210        /// The field is text, and should be interpreted as JSON.
211        const JSON = 12;
212        /// The field is a `Win32` error code. The field type should be `InFlag::UINT32`.
213        const WIN32ERROR = 13;
214        /// The field is an `NTSTATUS` error code. The field type should be `InFlag::UINT32`.
215        const NTSTATUS = 14;
216        /// The field is an `HRESULT` error code. The field type should be `InFlag::INT32`.
217        const HRESULT = 15;
218        /// The field is a Win32 `FILETIME` value.
219        const FILETIME = 16;
220        /// Display field as signed.
221        const SIGNED = 17;
222        /// Display field as unsigned.
223        const UNSIGNED = 18;
224        /// For strings, indicates that the string encoding is UTF-8.
225        const UTF8 = 35;
226        /// Used with `InFlag::BINARY`.
227        const PKCS7_WITH_TYPE_INFO = 36;
228        // const CODE_POINTER = 37;
229
230        /// Indicates that the timezone for a time value is UTC.
231        /// This can be used with `InFlag::FILETIME` or `InFlag::SYSTEMTIME`.
232        const DATETIME_UTC = 38;
233    }
234}
235
236// Event categories specified via keywords
237/// Event category for critical data (specified via keyword)
238pub const MICROSOFT_KEYWORD_CRITICAL_DATA: u64 = 0x0000_8000_0000_0000;
239/// Event category for measures (specified via keyword)
240pub const MICROSOFT_KEYWORD_MEASURES: u64 = 0x0000_4000_0000_0000;
241/// Event category for telemetry (specified via keyword)
242pub const MICROSOFT_KEYWORD_TELEMETRY: u64 = 0x0000_2000_0000_0000;
243
244// Event categories specified via event tags
245/// Event category defined by WIL
246pub const MICROSOFT_EVENTTAG_DROP_USER_IDS: u32 = 0x0000_8000;
247/// Event category defined by WIL
248pub const MICROSOFT_EVENTTAG_AGGREGATE: u32 = 0x0001_0000;
249/// Event category defined by WIL
250pub const MICROSOFT_EVENTTAG_DROP_PII_EXCEPT_IP: u32 = 0x0002_0000;
251/// Event category defined by WIL
252pub const MICROSOFT_EVENTTAG_COSTDEFERRED_LATENCY: u32 = 0x0004_0000;
253/// Event category defined by WIL
254pub const MICROSOFT_EVENTTAG_CORE_DATA: u32 = 0x0008_0000;
255/// Event category defined by WIL
256pub const MICROSOFT_EVENTTAG_INJECT_XTOKEN: u32 = 0x0010_0000;
257/// Event category defined by WIL
258pub const MICROSOFT_EVENTTAG_REALTIME_LATENCY: u32 = 0x0020_0000;
259/// Event category defined by WIL
260pub const MICROSOFT_EVENTTAG_NORMAL_LATENCY: u32 = 0x0040_0000;
261/// Event category defined by WIL
262pub const MICROSOFT_EVENTTAG_CRITICAL_PERSISTENCE: u32 = 0x0080_0000;
263/// Event category defined by WIL
264pub const MICROSOFT_EVENTTAG_NORMAL_PERSISTENCE: u32 = 0x0100_0000;
265/// Event category defined by WIL
266pub const MICROSOFT_EVENTTAG_DROP_PII: u32 = 0x0200_0000;
267/// Event category defined by WIL
268pub const MICROSOFT_EVENTTAG_HASH_PII: u32 = 0x0400_0000;
269/// Event category defined by WIL
270pub const MICROSOFT_EVENTTAG_MARK_PII: u32 = 0x0800_0000;