@@ -13,7 +13,6 @@
1313importio
1414importos
1515import_compression
16-fromthreadingimportRLock
17161817from_bz2importBZ2Compressor, BZ2Decompressor
1918@@ -53,9 +52,6 @@ def __init__(self, filename, mode="r", *, compresslevel=9):
5352 If mode is 'r', the input file may be the concatenation of
5453 multiple compressed streams.
5554 """
56-# This lock must be recursive, so that BufferedIOBase's
57-# writelines() does not deadlock.
58-self._lock=RLock()
5955self._fp=None
6056self._closefp=False
6157self._mode=_MODE_CLOSED
@@ -104,24 +100,23 @@ def close(self):
104100 May be called more than once without error. Once the file is
105101 closed, any other operation on it will raise a ValueError.
106102 """
107-withself._lock:
108-ifself._mode==_MODE_CLOSED:
109-return
103+ifself._mode==_MODE_CLOSED:
104+return
105+try:
106+ifself._mode==_MODE_READ:
107+self._buffer.close()
108+elifself._mode==_MODE_WRITE:
109+self._fp.write(self._compressor.flush())
110+self._compressor=None
111+finally:
110112try:
111-ifself._mode==_MODE_READ:
112-self._buffer.close()
113-elifself._mode==_MODE_WRITE:
114-self._fp.write(self._compressor.flush())
115-self._compressor=None
113+ifself._closefp:
114+self._fp.close()
116115finally:
117-try:
118-ifself._closefp:
119-self._fp.close()
120-finally:
121-self._fp=None
122-self._closefp=False
123-self._mode=_MODE_CLOSED
124-self._buffer=None
116+self._fp=None
117+self._closefp=False
118+self._mode=_MODE_CLOSED
119+self._buffer=None
125120126121@property
127122defclosed(self):
@@ -153,22 +148,20 @@ def peek(self, n=0):
153148 Always returns at least one byte of data, unless at EOF.
154149 The exact number of bytes returned is unspecified.
155150 """
156-withself._lock:
157-self._check_can_read()
158-# Relies on the undocumented fact that BufferedReader.peek()
159-# always returns at least one byte (except at EOF), independent
160-# of the value of n
161-returnself._buffer.peek(n)
151+self._check_can_read()
152+# Relies on the undocumented fact that BufferedReader.peek()
153+# always returns at least one byte (except at EOF), independent
154+# of the value of n
155+returnself._buffer.peek(n)
162156163157defread(self, size=-1):
164158"""Read up to size uncompressed bytes from the file.
165159166160 If size is negative or omitted, read until EOF is reached.
167161 Returns b'' if the file is already at EOF.
168162 """
169-withself._lock:
170-self._check_can_read()
171-returnself._buffer.read(size)
163+self._check_can_read()
164+returnself._buffer.read(size)
172165173166defread1(self, size=-1):
174167"""Read up to size uncompressed bytes, while trying to avoid
@@ -177,20 +170,18 @@ def read1(self, size=-1):
177170178171 Returns b'' if the file is at EOF.
179172 """
180-withself._lock:
181-self._check_can_read()
182-ifsize<0:
183-size=io.DEFAULT_BUFFER_SIZE
184-returnself._buffer.read1(size)
173+self._check_can_read()
174+ifsize<0:
175+size=io.DEFAULT_BUFFER_SIZE
176+returnself._buffer.read1(size)
185177186178defreadinto(self, b):
187179"""Read bytes into b.
188180189181 Returns the number of bytes read (0 for EOF).
190182 """
191-withself._lock:
192-self._check_can_read()
193-returnself._buffer.readinto(b)
183+self._check_can_read()
184+returnself._buffer.readinto(b)
194185195186defreadline(self, size=-1):
196187"""Read a line of uncompressed bytes from the file.
@@ -203,9 +194,8 @@ def readline(self, size=-1):
203194ifnothasattr(size, "__index__"):
204195raiseTypeError("Integer argument expected")
205196size=size.__index__()
206-withself._lock:
207-self._check_can_read()
208-returnself._buffer.readline(size)
197+self._check_can_read()
198+returnself._buffer.readline(size)
209199210200defreadlines(self, size=-1):
211201"""Read a list of lines of uncompressed bytes from the file.
@@ -218,9 +208,8 @@ def readlines(self, size=-1):
218208ifnothasattr(size, "__index__"):
219209raiseTypeError("Integer argument expected")
220210size=size.__index__()
221-withself._lock:
222-self._check_can_read()
223-returnself._buffer.readlines(size)
211+self._check_can_read()
212+returnself._buffer.readlines(size)
224213225214defwrite(self, data):
226215"""Write a byte string to the file.
@@ -229,12 +218,11 @@ def write(self, data):
229218 always len(data). Note that due to buffering, the file on disk
230219 may not reflect the data written until close() is called.
231220 """
232-withself._lock:
233-self._check_can_write()
234-compressed=self._compressor.compress(data)
235-self._fp.write(compressed)
236-self._pos+=len(data)
237-returnlen(data)
221+self._check_can_write()
222+compressed=self._compressor.compress(data)
223+self._fp.write(compressed)
224+self._pos+=len(data)
225+returnlen(data)
238226239227defwritelines(self, seq):
240228"""Write a sequence of byte strings to the file.
@@ -244,8 +232,7 @@ def writelines(self, seq):
244232245233 Line separators are not added between the written byte strings.
246234 """
247-withself._lock:
248-return_compression.BaseStream.writelines(self, seq)
235+return_compression.BaseStream.writelines(self, seq)
249236250237defseek(self, offset, whence=io.SEEK_SET):
251238"""Change the file position.
@@ -262,17 +249,15 @@ def seek(self, offset, whence=io.SEEK_SET):
262249 Note that seeking is emulated, so depending on the parameters,
263250 this operation may be extremely slow.
264251 """
265-withself._lock:
266-self._check_can_seek()
267-returnself._buffer.seek(offset, whence)
252+self._check_can_seek()
253+returnself._buffer.seek(offset, whence)
268254269255deftell(self):
270256"""Return the current file position."""
271-withself._lock:
272-self._check_not_closed()
273-ifself._mode==_MODE_READ:
274-returnself._buffer.tell()
275-returnself._pos
257+self._check_not_closed()
258+ifself._mode==_MODE_READ:
259+returnself._buffer.tell()
260+returnself._pos
276261277262278263defopen(filename, mode="rb", compresslevel=9,