Skip to content

Commit cca4e09

Browse files
ZeroIntensityebonnal
authored andcommitted
pythongh-125864: Propagate pickle.loads() failures in InterpreterPoolExecutor (pythongh-125898)
Authored-by: Peter Bierma <[email protected]>
1 parent d1cbe18 commit cca4e09

File tree

2 files changed

+20
-1
lines changed

2 files changed

+20
-1
lines changed

Lib/concurrent/futures/interpreter.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -107,7 +107,8 @@ def _call(cls, func, args, kwargs, resultsid):
107107

108108
@classmethod
109109
def _call_pickled(cls, pickled, resultsid):
110-
fn, args, kwargs = pickle.loads(pickled)
110+
with cls._capture_exc(resultsid):
111+
fn, args, kwargs = pickle.loads(pickled)
111112
cls._call(fn, args, kwargs, resultsid)
112113

113114
def __init__(self, initdata, shared=None):

Lib/test/test_concurrent_futures/test_interpreter_pool.py

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,16 @@ def pipe(self):
5656
return r, w
5757

5858

59+
class PickleShenanigans:
60+
"""Succeeds with pickle.dumps(), but fails with pickle.loads()"""
61+
def __init__(self, value):
62+
if value == 1:
63+
raise RuntimeError("gotcha")
64+
65+
def __reduce__(self):
66+
return (self.__class__, (1,))
67+
68+
5969
class InterpreterPoolExecutorTest(
6070
InterpretersMixin, ExecutorTest, BaseTestCase):
6171

@@ -279,6 +289,14 @@ def test_idle_thread_reuse(self):
279289
self.assertEqual(len(executor._threads), 1)
280290
executor.shutdown(wait=True)
281291

292+
def test_pickle_errors_propagate(self):
293+
# GH-125864: Pickle errors happen before the script tries to execute, so the
294+
# queue used to wait infinitely.
295+
296+
fut = self.executor.submit(PickleShenanigans(0))
297+
with self.assertRaisesRegex(RuntimeError, "gotcha"):
298+
fut.result()
299+
282300

283301
class AsyncioTest(InterpretersMixin, testasyncio_utils.TestCase):
284302

0 commit comments

Comments
 (0)