Add Mono EventPipe Sample Profiler support. #47858
Merged
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Implement support for EventPipe Sample Profiler on Mono inline with CoreClr Sample Profiler behaviour. By default CoreClr sample profiler tries to run at 1000 hertz (every ms) and on each sample it will stop runtime, snap callstacks for all managed threads, submit EventPipe sample profile events and resume runtime. Doing a full stop/restart of the runtime on every sample could be quite invasive, but is probably the most portable way of implementing it working on most platforms.
This PR implements the same logic, but on Mono runtime, stopping the runtime, record all callstacks for all managed threads that should be sampled, restart runtime and then write all sample profile events into EventPipe. Note that events are written after the runtime has resumed since all code executed when runtime is stopped needs to be async safe (needed when running in preemptive mode) so we can't call into EventPipe at that point.
Going forward we should investigate alternative ways to do sample profiling depending on underlying platform and OS support. Currently implementation will work on all supported platforms, but it will not be as accurate as it could be (especially when using safe points and coop enabled runtime) and impacts measured target. Mono's profiler uses Signals/SuspendThread and for platforms supporting these API's, that could be an alternative implementation. It could also be worth to look into CPU hardware counters using ETW kernel log session on Windows and perf_event_open on Linux.