8000 Fixes SIGSEGV and improve thread safety of journal.Reader class by sebres · Pull Request #144 · systemd/python-systemd · GitHub
[go: up one dir, main page]

Skip to content

Fixes SIGSEGV and improve thread safety of journal.Reader class #144

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 8000 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

Open
wants to merge 3 commits into
base: main
Choose a base branch
from

Conversation

sebres
Copy link
@sebres sebres commented Apr 1, 2025

This PR fixes threaded issues of journal.Reader class and improves its thread-safety, using simple protection with ref-counter;
It would avoid segfault by closing journal across threads.

The algorithm is simple, here short explanation illustrating the approach on an example of #143:

TH Action ref_count j_handle
... Reader created and has initial ref-count 1 1 valid
A Enter Reader_wait(), increment ref-count, release the lock (GIL), enter sd_journal_wait() 2 valid
A Leave sd_journal_wait(), acquiring the lock (GIL), decrement ref-count, not calling sd_journal_close() because of ref_count == 1, leave Reader_wait() 1 valid
- ... now thread A repeats the wait() however thread B invokes close() in-between ... - -
A Enter Reader_wait(), increment ref-count, release the lock (GIL), enter sd_journal_wait() 2 valid
B Enter Reader_close(), set closed flag, decrement ref-count, but don't close it because of ref_count > 0 1 valid
A Leave sd_journal_wait(), acquiring the lock (GIL), decrement ref-count, calling sd_journal_close() because of ref_count == 0, leave Reader_wait() 0 NULL

If thread B manages to close the handle before A enters wait mode, it is also safe, because then sd_journal_wait() would generate EINVARG and Reader.wait() raises an error ([Errno 22] Invalid argument).

Anyway, no segfault happens anymore and it is more or less thread-safe.

closes gh-143

sebres added 2 commits April 1, 2025 16:33
…th ref-counter; avoid segfault by closing journal across threads (closes systemdgh-143)
…ids unexpected states on repeated Reader.close)
@sebres sebres force-pushed the gh-143-sf-fix branch 2 times, most recently from 5a7719b to 03eec9d Compare April 2, 2025 16:31
@sebres
Copy link
Author
sebres commented Apr 2, 2025

7c99a39 seems to fix the GHA flows now (completely different issue), so can be cherry-picked to main branch as it is (or I could make a separate PR if necessary).

@sebres
Copy link
Author
sebres commented Jun 4, 2025

Ping.
Is this repository alive?

concurrency:
group: ${{ github.workflow }}-${{ matrix.python }}-${{ github.ref }}
cancel-in-progress: true
strategy:
fail-fast: false
matrix:
python: [
"3.7",
"3.8",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That should probably be dropped as well, since it is EOL or in other words: with 3.7 dropped I see no reason not to drop 3.8

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I dropped 3.7 only because of switch to ubuntu-latest, which doesn't have it.
I don't see any reason to drop 3.8. at least as long as it is compatible and running yet.
Anyway has nothing to do with the PR as is, I made the changes just in order to repair the GHA flow.

@@ -43,6 +44,9 @@ jobs:
run: |
sudo apt -y update
sudo apt -y install gcc libsystemd-dev
if dpkg --compare-versions "${{ matrix.python }}" ge 3.12; then
python -m pip install setuptools || echo "can't install setuptools"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Might make sense to always install setuptools, so that all versions are tested with the same?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Dunno... IMHO, only 3.12+ missing it as package, but I am unsure the attempt to install with pip for previous versions would be always successful (and not fail due to conflict with preinstalled package).
I can imagine it could.

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

Successfully merging this pull request may close these issues.

SIGSEGV using journal.Reader, thread safety issue?
2 participants
0