Skip to content

Commit

Permalink
[EventSource] Block EventCommandExecuted callback during initializati…
Browse files Browse the repository at this point in the history
…on (dotnet#105341)

* [EventSource] Relax assert on CounterGroup callback

* [EventSource] Avoid callback double invoke

Guard EventCommandExecuted deferred commands callbacks with
EventSource initialization to prevent CounterGroup's callback
registration from seeing unexpected commands

* Simplify comments for processing deferred commands
  • Loading branch information
mdh1418 committed Jul 26, 2024
1 parent ee8426c commit 24367aa
Showing 1 changed file with 16 additions and 10 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -500,13 +500,16 @@ public event EventHandler<EventCommandEventArgs>? EventCommandExecuted

m_eventCommandExecuted += value;

// If we have an EventHandler<EventCommandEventArgs> attached to the EventSource before the first command arrives
// It should get a chance to handle the deferred commands.
EventCommandEventArgs? deferredCommands = m_deferredCommands;
while (deferredCommands != null)
if (m_completelyInited)
{
value(this, deferredCommands);
deferredCommands = deferredCommands.nextCommand;
// If we have an EventHandler<EventCommandEventArgs> attached to the EventSource before the first command arrives
// It should get a chance to handle the deferred commands.
EventCommandEventArgs? deferredCommands = m_deferredCommands;
while (deferredCommands != null)
{
value(this, deferredCommands);
deferredCommands = deferredCommands.nextCommand;
}
}
}
remove
Expand Down Expand Up @@ -1638,8 +1641,6 @@ private unsafe void Initialize(Guid eventSourceGuid, string eventSourceName, str
m_eventPipeProvider = eventPipeProvider;
#endif
Debug.Assert(!m_eventSourceEnabled); // We can't be enabled until we are completely initted.
// We are logically completely initialized at this point.
m_completelyInited = true;
}
catch (Exception e)
{
Expand All @@ -1660,6 +1661,11 @@ private unsafe void Initialize(Guid eventSourceGuid, string eventSourceName, str
DoCommand(deferredCommands); // This can never throw, it catches them and reports the errors.
deferredCommands = deferredCommands.nextCommand;
}

if (m_constructionException == null)
{
m_completelyInited = true;
}
}
}

Expand Down Expand Up @@ -2573,9 +2579,9 @@ internal void DoCommand(EventCommandEventArgs commandArgs)
}

// PRECONDITION: We should be holding the EventListener.EventListenersLock
// We defer commands until we are completely inited. This allows error messages to be sent.
Debug.Assert(m_completelyInited);
Debug.Assert(Monitor.IsEntered(EventListener.EventListenersLock));

// We defer commands until we can send error messages.
if (m_etwProvider == null) // If we failed to construct
return;

Expand Down

0 comments on commit 24367aa

Please sign in to comment.