summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMiss Islington (bot) <31488909+miss-islington@users.noreply.github.com>2020-08-16 15:34:27 (GMT)
committerGitHub <noreply@github.com>2020-08-16 15:34:27 (GMT)
commit2c050e52f1ccf5db03819e4ed70690521d67e9fa (patch)
tree20b2948def6a80d25027051c54bea98dcc99bc00
parent28bf82661ac9dfaf1b2d0fd0ac98fc0b31cd95bb (diff)
downloadcpython-2c050e52f1ccf5db03819e4ed70690521d67e9fa.zip
cpython-2c050e52f1ccf5db03819e4ed70690521d67e9fa.tar.gz
cpython-2c050e52f1ccf5db03819e4ed70690521d67e9fa.tar.bz2
[3.9] bpo-41503: Fix race between setTarget and flush in logging.handlers.MemoryHandler (GH-21765) (GH-21897)
(cherry picked from commit 2353d77fad7ed9d11d8a4d66b5dd1306cdb94125) Co-authored-by: Irit Katriel <iritkatriel@yahoo.com> Automerge-Triggered-By: @vsajip
-rw-r--r--Lib/logging/handlers.py6
-rw-r--r--Lib/test/test_logging.py21
-rw-r--r--Misc/NEWS.d/next/Library/2020-08-07-15-18-16.bpo-41503.IYftcu.rst1
3 files changed, 27 insertions, 1 deletions
diff --git a/Lib/logging/handlers.py b/Lib/logging/handlers.py
index 4a120e9..867ef4e 100644
--- a/Lib/logging/handlers.py
+++ b/Lib/logging/handlers.py
@@ -1324,7 +1324,11 @@ class MemoryHandler(BufferingHandler):
"""
Set the target handler for this handler.
"""
- self.target = target
+ self.acquire()
+ try:
+ self.target = target
+ finally:
+ self.release()
def flush(self):
"""
diff --git a/Lib/test/test_logging.py b/Lib/test/test_logging.py
index 8fea47a..62759c0 100644
--- a/Lib/test/test_logging.py
+++ b/Lib/test/test_logging.py
@@ -1157,6 +1157,27 @@ class MemoryHandlerTest(BaseTest):
# assert that no new lines have been added
self.assert_log_lines(lines) # no change
+ def test_race_between_set_target_and_flush(self):
+ class MockRaceConditionHandler:
+ def __init__(self, mem_hdlr):
+ self.mem_hdlr = mem_hdlr
+
+ def removeTarget(self):
+ self.mem_hdlr.setTarget(None)
+
+ def handle(self, msg):
+ t = threading.Thread(target=self.removeTarget)
+ t.daemon = True
+ t.start()
+
+ target = MockRaceConditionHandler(self.mem_hdlr)
+ self.mem_hdlr.setTarget(target)
+
+ for _ in range(10):
+ time.sleep(0.005)
+ self.mem_logger.info("not flushed")
+ self.mem_logger.warning("flushed")
+
class ExceptionFormatter(logging.Formatter):
"""A special exception formatter."""
diff --git a/Misc/NEWS.d/next/Library/2020-08-07-15-18-16.bpo-41503.IYftcu.rst b/Misc/NEWS.d/next/Library/2020-08-07-15-18-16.bpo-41503.IYftcu.rst
new file mode 100644
index 0000000..c34996d
--- /dev/null
+++ b/Misc/NEWS.d/next/Library/2020-08-07-15-18-16.bpo-41503.IYftcu.rst
@@ -0,0 +1 @@
+Fixed a race between setTarget and flush in logging.handlers.MemoryHandler. \ No newline at end of file