Skip to content

gh-146059: Call fast_save_leave() in pickle save_frozenset()#146173

Merged
vstinner merged 3 commits intopython:mainfrom
vstinner:pickle_fast
Mar 26, 2026
Merged

gh-146059: Call fast_save_leave() in pickle save_frozenset()#146173
vstinner merged 3 commits intopython:mainfrom
vstinner:pickle_fast

Conversation

@vstinner
Copy link
Member

@vstinner vstinner commented Mar 19, 2026

Copy link
Member Author

@vstinner vstinner left a comment

Choose a reason for hiding this comment

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

buf = io.BytesIO()
pickler = self.pickler(buf, protocol=proto)
# Enable fast mode (disables memo, enables cycle detection)
pickler.fast = 1
Copy link
Member Author

Choose a reason for hiding this comment

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

Would it be also worth it to test non-fast mode? The bug only triggers in fast mode.

Copy link
Member

@serhiy-storchaka serhiy-storchaka left a comment

Choose a reason for hiding this comment

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

Please add also tests for list, set, dict, tuple and frozendict.

Copy link
Member

@serhiy-storchaka serhiy-storchaka left a comment

Choose a reason for hiding this comment

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

Also, this mechanism is used to guard against deeply nested structures, so it would be worth to test deeply nested structures.

There are sets of tests for recursive structures. We can use similar tests for limited but deep recursion.

@vstinner
Copy link
Member Author

@serhiy-storchaka: Please review the updated PR. Is it what you expected?

Also, this mechanism is used to guard against deeply nested structures, so it would be worth to test deeply nested structures.

I added deep_nested_struct() tests for the 6 types.

More Pythonic way would be to make tested_type and data parameters and call the function with different arguments.

Good idea, I rewrote tests like that.

@vstinner
Copy link
Member Author

Ping @serhiy-storchaka.

@vstinner vstinner merged commit 5c0dcb3 into python:main Mar 26, 2026
48 checks passed
@vstinner vstinner deleted the pickle_fast branch March 26, 2026 16:35
@miss-islington-app
Copy link

Thanks @vstinner for the PR 🌮🎉.. I'm working now to backport this PR to: 3.13, 3.14.
🐍🍒⛏🤖 I'm not a witch! I'm not a witch!

miss-islington pushed a commit to miss-islington/cpython that referenced this pull request Mar 26, 2026
…ythonGH-146173)

Add more pickle tests: test also nested structures.
(cherry picked from commit 5c0dcb3e0d817bd8c28e8efcdb97103cd9210989)

Co-authored-by: Victor Stinner <[email protected]>
miss-islington pushed a commit to miss-islington/cpython that referenced this pull request Mar 26, 2026
…ythonGH-146173)

Add more pickle tests: test also nested structures.
(cherry picked from commit 5c0dcb3)

Co-authored-by: Victor Stinner <[email protected]>
@bedevere-app
Copy link

bedevere-app bot commented Mar 26, 2026

GH-146473 is a backport of this pull request to the 3.14 branch.

@bedevere-app bedevere-app bot removed the needs backport to 3.14 bugs and security fixes label Mar 26, 2026
@bedevere-app
Copy link

bedevere-app bot commented Mar 26, 2026

GH-146474 is a backport of this pull request to the 3.13 branch.

@bedevere-app bedevere-app bot removed the needs backport to 3.13 bugs and security fixes label Mar 26, 2026
vstinner added a commit that referenced this pull request Mar 26, 2026
…H-146173) (#146473)

gh-146059: Call fast_save_leave() in pickle save_frozenset() (GH-146173)

Add more pickle tests: test also nested structures.
(cherry picked from commit 5c0dcb3)

Co-authored-by: Victor Stinner <[email protected]>
Copy link
Member

@serhiy-storchaka serhiy-storchaka left a comment

Choose a reason for hiding this comment

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

LGTM. 👍

I only have some minor questions.

self.skipTest("need Pickler class")

data = [create_data(i) for i in range(FAST_NESTING_LIMIT * 2)]
data = {"key": data}
Copy link
Member

Choose a reason for hiding this comment

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

Why is this needed?

Copy link
Member Author

Choose a reason for hiding this comment

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

Ah, it comes from the initial reproducer. But I confirm that I can still reproduce the bug/crash without {"key": data}. I removed fast_save_leave() from save_list(), save_dict() and save_frozenset(), and the test fails or crash.

self.assertIn(expected, str(e))

def fast_save_enter(self, create_data, minprotocol=0):
# gh-146059: Check that fast_save() is called when
Copy link
Member

Choose a reason for hiding this comment

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

Did you mean fast_save_leave()?

Copy link
Member Author

Choose a reason for hiding this comment

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

Oops, you're right.

data = seed
for i in range(depth):
data = create_nested(data)
data = {"key": data}
Copy link
Member

Choose a reason for hiding this comment

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

Why is this needed?

def test_fast_save_enter_dict(self):
self.fast_save_enter(lambda i: {"key": i})

def deep_nested_struct(self, seed, create_nested,
Copy link
Member

Choose a reason for hiding this comment

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

Why is the seed parameter used? Can't we use the same seed (None) for all tests?

Copy link
Member Author

Choose a reason for hiding this comment

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

I looked nice to me to have a seed of the same type than the nested structure, but you're right, it makes the test too complex, it's not worth it. Also, I confirm that I can still trigger the bug (when removing fast_save_leave() manually in pickle) with None seed.

@vstinner
Copy link
Member Author

LGTM. 👍 I only have some minor questions.

Thanks for your review. I created #146481 to address your review.

vstinner added a commit that referenced this pull request Mar 27, 2026
…H-146173) (#146474)

gh-146059: Call fast_save_leave() in pickle save_frozenset() (GH-146173)

Add more pickle tests: test also nested structures.
(cherry picked from commit 5c0dcb3)

Co-authored-by: Victor Stinner <[email protected]>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants