Skip to content
This repository was archived by the owner on Jan 23, 2023. It is now read-only.

Commit 8d03738

Browse files
authored
Merge pull request #22218 from sywhang/release-2.2-port-21993
Backporting #21993 to 2.2 branch - EventParameterInfo.GetMetadataLength() throws NotSupportedException
2 parents 6320ede + 714edba commit 8d03738

File tree

1 file changed

+36
-14
lines changed

1 file changed

+36
-14
lines changed

src/mscorlib/src/System/Diagnostics/Eventing/EventPipeMetadataGenerator.cs

Lines changed: 36 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,7 @@ private unsafe byte[] GenerateMetadata(
7575
// level : 4 bytes
7676
// parameterCount : 4 bytes
7777
uint metadataLength = 24 + ((uint)eventName.Length + 1) * 2;
78+
uint defaultMetadataLength = metadataLength;
7879

7980
// Check for an empty payload.
8081
// Write<T> calls with no arguments by convention have a parameter of
@@ -87,7 +88,16 @@ private unsafe byte[] GenerateMetadata(
8788
// Increase the metadataLength for parameters.
8889
foreach (var parameter in parameters)
8990
{
90-
metadataLength = metadataLength + parameter.GetMetadataLength();
91+
int pMetadataLength = parameter.GetMetadataLength();
92+
// The call above may return -1 which means we failed to get the metadata length.
93+
// We then return a default metadata blob (with parameterCount of 0) to prevent it from generating malformed metadata.
94+
if(pMetadataLength < 0)
95+
{
96+
parameters = Array.Empty<EventParameterInfo>();
97+
metadataLength = defaultMetadataLength;
98+
break;
99+
}
100+
metadataLength += (uint)pMetadataLength;
91101
}
92102

93103
metadata = new byte[metadataLength];
@@ -107,7 +117,11 @@ private unsafe byte[] GenerateMetadata(
107117
WriteToBuffer(pMetadata, metadataLength, ref offset, (uint)parameters.Length);
108118
foreach (var parameter in parameters)
109119
{
110-
parameter.GenerateMetadata(pMetadata, ref offset, metadataLength);
120+
if(!parameter.GenerateMetadata(pMetadata, ref offset, metadataLength))
121+
{
122+
// If we fail to generate metadata for any parameter, we should return the "default" metadata without any parameters
123+
return GenerateMetadata(eventId, eventName, keywords, level, version, Array.Empty<EventParameterInfo>());
124+
}
111125
}
112126
Debug.Assert(metadataLength == offset);
113127
}
@@ -174,7 +188,7 @@ internal void SetInfo(string name, Type type, TraceLoggingTypeInfo typeInfo = nu
174188
TypeInfo = typeInfo;
175189
}
176190

177-
internal unsafe void GenerateMetadata(byte* pMetadataBlob, ref uint offset, uint blobSize)
191+
internal unsafe bool GenerateMetadata(byte* pMetadataBlob, ref uint offset, uint blobSize)
178192
{
179193
TypeCode typeCode = GetTypeCodeExtended(ParameterType);
180194
if(typeCode == TypeCode.Object)
@@ -189,7 +203,7 @@ internal unsafe void GenerateMetadata(byte* pMetadataBlob, ref uint offset, uint
189203
InvokeTypeInfo invokeTypeInfo = TypeInfo as InvokeTypeInfo;
190204
if(invokeTypeInfo == null)
191205
{
192-
throw new NotSupportedException();
206+
return false;
193207
}
194208

195209
// Get the set of properties to be serialized.
@@ -201,7 +215,10 @@ internal unsafe void GenerateMetadata(byte* pMetadataBlob, ref uint offset, uint
201215

202216
foreach(PropertyAnalysis prop in properties)
203217
{
204-
GenerateMetadataForProperty(prop, pMetadataBlob, ref offset, blobSize);
218+
if(!GenerateMetadataForProperty(prop, pMetadataBlob, ref offset, blobSize))
219+
{
220+
return false;
221+
}
205222
}
206223
}
207224
else
@@ -225,9 +242,10 @@ internal unsafe void GenerateMetadata(byte* pMetadataBlob, ref uint offset, uint
225242
EventPipeMetadataGenerator.WriteToBuffer(pMetadataBlob, blobSize, ref offset, (byte *)pParameterName, ((uint)ParameterName.Length + 1) * 2);
226243
}
227244
}
245+
return true;
228246
}
229247

230-
private static unsafe void GenerateMetadataForProperty(PropertyAnalysis property, byte* pMetadataBlob, ref uint offset, uint blobSize)
248+
private static unsafe bool GenerateMetadataForProperty(PropertyAnalysis property, byte* pMetadataBlob, ref uint offset, uint blobSize)
231249
{
232250
Debug.Assert(property != null);
233251
Debug.Assert(pMetadataBlob != null);
@@ -252,7 +270,10 @@ private static unsafe void GenerateMetadataForProperty(PropertyAnalysis property
252270

253271
foreach(PropertyAnalysis prop in properties)
254272
{
255-
GenerateMetadataForProperty(prop, pMetadataBlob, ref offset, blobSize);
273+
if(!GenerateMetadataForProperty(prop, pMetadataBlob, ref offset, blobSize))
274+
{
275+
return false;
276+
}
256277
}
257278
}
258279
else
@@ -274,10 +295,10 @@ private static unsafe void GenerateMetadataForProperty(PropertyAnalysis property
274295
// PropertyName : NULL-terminated string
275296
TypeCode typeCode = GetTypeCodeExtended(property.typeInfo.DataType);
276297

277-
// EventPipe does not support this type. Throw, which will cause no metadata to be registered for this event.
298+
// EventPipe does not support this type. Return false, which will cause no metadata to be registered for this event.
278299
if(typeCode == TypeCode.Object)
279300
{
280-
throw new NotSupportedException();
301+
return false;
281302
}
282303

283304
// Write the type code.
@@ -289,20 +310,21 @@ private static unsafe void GenerateMetadataForProperty(PropertyAnalysis property
289310
EventPipeMetadataGenerator.WriteToBuffer(pMetadataBlob, blobSize, ref offset, (byte *)pPropertyName, ((uint)property.name.Length + 1) * 2);
290311
}
291312
}
313+
return true;
292314
}
293315

294316

295-
internal unsafe uint GetMetadataLength()
317+
internal unsafe int GetMetadataLength()
296318
{
297-
uint ret = 0;
319+
int ret = 0;
298320

299321
TypeCode typeCode = GetTypeCodeExtended(ParameterType);
300322
if(typeCode == TypeCode.Object)
301323
{
302324
InvokeTypeInfo typeInfo = TypeInfo as InvokeTypeInfo;
303325
if(typeInfo == null)
304326
{
305-
throw new NotSupportedException();
327+
return -1;
306328
}
307329

308330
// Each nested struct is serialized as:
@@ -319,7 +341,7 @@ internal unsafe uint GetMetadataLength()
319341
{
320342
foreach(PropertyAnalysis prop in properties)
321343
{
322-
ret += GetMetadataLengthForProperty(prop);
344+
ret += (int)GetMetadataLengthForProperty(prop);
323345
}
324346
}
325347

@@ -330,7 +352,7 @@ internal unsafe uint GetMetadataLength()
330352
}
331353
else
332354
{
333-
ret += (uint)(sizeof(uint) + ((ParameterName.Length + 1) * 2));
355+
ret += (int)(sizeof(uint) + ((ParameterName.Length + 1) * 2));
334356
}
335357

336358
return ret;

0 commit comments

Comments
 (0)