Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support multithreaded profiling #352

Open
georgeharker opened this issue Dec 4, 2024 · 4 comments
Open

Support multithreaded profiling #352

georgeharker opened this issue Dec 4, 2024 · 4 comments

Comments

@georgeharker
Copy link

Thanks for pyintrument - it's incredibly useful

I had need to trace a multithreaded python app and examine the relationship between threads. Obviously in some cases multithreading can be a little interesting in python, but in this particular case works well.

I have extended a fork of pyinstrument to support showing all child threads from the one where profiling starts. I get nice results with all threads separated which has been hugely helpful.

I'll file a PR and reference this issue. It's still a bit of a WIP, but i'd be curious to see if it looks reasonable to you.

@lucamuscat
Copy link

lucamuscat commented Dec 28, 2024

This would definitely be a great feature to have in pyinstrument.

As a workaround until/if this feature gets picked up, I've come up with the following hack to automatically profile newly spawned threads by (ab)using threading.settrace, here's an implementation of this hack in one of my projects.

One can detect when a thread has started, and start the profiler when threading.settrace calls the tracing function with Threading.run() in its frame argument with the call event. The profiler can be stopped when the same Threading.run() is encountered in the trace function with a return event. You need to keep track of the number of times Threading.run() is called, as a thread can spawn other threads.

I had to use settrace instead of setprofile as pyinstrument uses setprofile, and overrides the custom profiling function with its own.

@georgeharker
Copy link
Author

Take a look at the referenced PR - it does much of that but also allows viewing the timelines of all threads together.

@lucamuscat
Copy link

@georgeharker I've already had a look, I need to dedicate some time on integrating it with my project.

My biggest issue with the PR in its current state is that the majority of tests are failing, there are some missing updates to the Session class in various methods, and the linters seem to be complaining.

Changing the return type for the Profiler from a list of frames to a dictionary seems like a tough breaking change. Maybe this multi threading aware code can be placed into its own class, leaving us with two kinds of profilers?

@georgeharker
Copy link
Author

Yeah there's still work to do there for sure! Just did enough for my needs and wanted some feedback about what it would look like to get it into a state for merge

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants