Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
C
cpython
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Kirill Smelkov
cpython
Commits
084ed11e
Commit
084ed11e
authored
Jun 24, 2012
by
Gregory P. Smith
Browse files
Options
Browse Files
Download
Plain Diff
merge heads
parents
fb7e0fc8
7d8f090a
Changes
8
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
8 changed files
with
295 additions
and
15 deletions
+295
-15
Lib/test/test_file_eintr.py
Lib/test/test_file_eintr.py
+236
-0
Lib/test/test_io.py
Lib/test/test_io.py
+5
-5
Misc/NEWS
Misc/NEWS
+5
-0
Modules/_io/_iomodule.h
Modules/_io/_iomodule.h
+5
-0
Modules/_io/bufferedio.c
Modules/_io/bufferedio.c
+4
-4
Modules/_io/fileio.c
Modules/_io/fileio.c
+7
-0
Modules/_io/iobase.c
Modules/_io/iobase.c
+19
-4
Modules/_io/textio.c
Modules/_io/textio.c
+14
-2
No files found.
Lib/test/test_file_eintr.py
0 → 100644
View file @
084ed11e
This diff is collapsed.
Click to expand it.
Lib/test/test_io.py
View file @
084ed11e
...
...
@@ -2912,7 +2912,7 @@ class SignalsTest(unittest.TestCase):
try
:
wio
=
self
.
io
.
open
(
w
,
**
fdopen_kwargs
)
t
.
start
()
signal
.
alarm
(
1
)
signal
.
setitimer
(
signal
.
ITIMER_REAL
,
0.
1
)
# Fill the pipe enough that the write will be blocking.
# It will be interrupted by the timer armed above. Since the
# other thread has read one byte, the low-level write will
...
...
@@ -2957,7 +2957,7 @@ class SignalsTest(unittest.TestCase):
r
,
w
=
os
.
pipe
()
wio
=
self
.
io
.
open
(
w
,
**
fdopen_kwargs
)
try
:
signal
.
alarm
(
1
)
signal
.
setitimer
(
signal
.
ITIMER_REAL
,
0.
1
)
# Either the reentrant call to wio.write() fails with RuntimeError,
# or the signal handler raises ZeroDivisionError.
with
self
.
assertRaises
((
ZeroDivisionError
,
RuntimeError
))
as
cm
:
...
...
@@ -2992,7 +2992,7 @@ class SignalsTest(unittest.TestCase):
try
:
rio
=
self
.
io
.
open
(
r
,
**
fdopen_kwargs
)
os
.
write
(
w
,
b"foo"
)
signal
.
alarm
(
1
)
signal
.
setitimer
(
signal
.
ITIMER_REAL
,
0.
1
)
# Expected behaviour:
# - first raw read() returns partial b"foo"
# - second raw read() returns EINTR
...
...
@@ -3036,13 +3036,13 @@ class SignalsTest(unittest.TestCase):
t
.
daemon
=
True
def
alarm1
(
sig
,
frame
):
signal
.
signal
(
signal
.
SIGALRM
,
alarm2
)
signal
.
alarm
(
1
)
signal
.
setitimer
(
signal
.
ITIMER_REAL
,
0.
1
)
def
alarm2
(
sig
,
frame
):
t
.
start
()
signal
.
signal
(
signal
.
SIGALRM
,
alarm1
)
try
:
wio
=
self
.
io
.
open
(
w
,
**
fdopen_kwargs
)
signal
.
alarm
(
1
)
signal
.
setitimer
(
signal
.
ITIMER_REAL
,
0.
1
)
# Expected behaviour:
# - first raw write() is partial (because of the limited pipe buffer
# and the first alarm)
...
...
Misc/NEWS
View file @
084ed11e
...
...
@@ -10,6 +10,11 @@ What's New in Python 3.3.0 Beta 1?
Core and Builtins
-----------------
- Issue #12268: File readline, readlines and read() or readall() methods
no longer lose data when an underlying read system call is interrupted.
IOError is no longer raised due to a read system call returning EINTR
from within these methods.
- Issue #11626: Add _SizeT functions to stable ABI.
- Issue #15146: Add PyType_FromSpecWithBases. Patch by Robin Schreiber.
...
...
Modules/_io/_iomodule.h
View file @
084ed11e
...
...
@@ -57,6 +57,11 @@ extern Py_ssize_t _PyIO_find_line_ending(
int
translated
,
int
universal
,
PyObject
*
readnl
,
int
kind
,
char
*
start
,
char
*
end
,
Py_ssize_t
*
consumed
);
/* Return 1 if an EnvironmentError with errno == EINTR is set (and then
clears the error indicator), 0 otherwise.
Should only be called when PyErr_Occurred() is true.
*/
extern
int
_PyIO_trap_eintr
(
void
);
#define DEFAULT_BUFFER_SIZE (8 * 1024)
/* bytes */
...
...
Modules/_io/bufferedio.c
View file @
084ed11e
...
...
@@ -746,8 +746,8 @@ _buffered_init(buffered *self)
clears the error indicator), 0 otherwise.
Should only be called when PyErr_Occurred() is true.
*/
static
int
_trap_eintr
(
void
)
int
_
PyIO_
trap_eintr
(
void
)
{
static
PyObject
*
eintr_int
=
NULL
;
PyObject
*
typ
,
*
val
,
*
tb
;
...
...
@@ -1396,7 +1396,7 @@ _bufferedreader_raw_read(buffered *self, char *start, Py_ssize_t len)
*/
do
{
res
=
PyObject_CallMethodObjArgs
(
self
->
raw
,
_PyIO_str_readinto
,
memobj
,
NULL
);
}
while
(
res
==
NULL
&&
_trap_eintr
());
}
while
(
res
==
NULL
&&
_
PyIO_
trap_eintr
());
Py_DECREF
(
memobj
);
if
(
res
==
NULL
)
return
-
1
;
...
...
@@ -1850,7 +1850,7 @@ _bufferedwriter_raw_write(buffered *self, char *start, Py_ssize_t len)
errno
=
0
;
res
=
PyObject_CallMethodObjArgs
(
self
->
raw
,
_PyIO_str_write
,
memobj
,
NULL
);
errnum
=
errno
;
}
while
(
res
==
NULL
&&
_trap_eintr
());
}
while
(
res
==
NULL
&&
_
PyIO_
trap_eintr
());
Py_DECREF
(
memobj
);
if
(
res
==
NULL
)
return
-
1
;
...
...
Modules/_io/fileio.c
View file @
084ed11e
...
...
@@ -670,6 +670,13 @@ fileio_readall(fileio *self)
if
(
n
==
0
)
break
;
if
(
n
<
0
)
{
if
(
errno
==
EINTR
)
{
if
(
PyErr_CheckSignals
())
{
Py_DECREF
(
result
);
return
NULL
;
}
continue
;
}
if
(
total
>
0
)
break
;
if
(
errno
==
EAGAIN
)
{
...
...
Modules/_io/iobase.c
View file @
084ed11e
...
...
@@ -474,11 +474,15 @@ iobase_readline(PyObject *self, PyObject *args)
PyObject
*
b
;
if
(
has_peek
)
{
_Py_IDENTIFIER
(
peek
);
PyObject
*
readahead
=
_PyObject_CallMethodId
(
self
,
&
PyId_peek
,
"i"
,
1
);
if
(
readahead
==
NULL
)
if
(
readahead
==
NULL
)
{
/* NOTE: PyErr_SetFromErrno() calls PyErr_CheckSignals()
when EINTR occurs so we needn't do it ourselves. */
if
(
_PyIO_trap_eintr
())
{
continue
;
}
goto
fail
;
}
if
(
!
PyBytes_Check
(
readahead
))
{
PyErr_Format
(
PyExc_IOError
,
"peek() should have returned a bytes object, "
...
...
@@ -511,8 +515,14 @@ iobase_readline(PyObject *self, PyObject *args)
}
b
=
_PyObject_CallMethodId
(
self
,
&
PyId_read
,
"n"
,
nreadahead
);
if
(
b
==
NULL
)
if
(
b
==
NULL
)
{
/* NOTE: PyErr_SetFromErrno() calls PyErr_CheckSignals()
when EINTR occurs so we needn't do it ourselves. */
if
(
_PyIO_trap_eintr
())
{
continue
;
}
goto
fail
;
}
if
(
!
PyBytes_Check
(
b
))
{
PyErr_Format
(
PyExc_IOError
,
"read() should have returned a bytes object, "
...
...
@@ -827,6 +837,11 @@ rawiobase_readall(PyObject *self, PyObject *args)
PyObject
*
data
=
_PyObject_CallMethodId
(
self
,
&
PyId_read
,
"i"
,
DEFAULT_BUFFER_SIZE
);
if
(
!
data
)
{
/* NOTE: PyErr_SetFromErrno() calls PyErr_CheckSignals()
when EINTR occurs so we needn't do it ourselves. */
if
(
_PyIO_trap_eintr
())
{
continue
;
}
Py_DECREF
(
chunks
);
return
NULL
;
}
...
...
Modules/_io/textio.c
View file @
084ed11e
...
...
@@ -1560,8 +1560,14 @@ textiowrapper_read(textio *self, PyObject *args)
/* Keep reading chunks until we have n characters to return */
while
(
remaining
>
0
)
{
res
=
textiowrapper_read_chunk
(
self
,
remaining
);
if
(
res
<
0
)
if
(
res
<
0
)
{
/* NOTE: PyErr_SetFromErrno() calls PyErr_CheckSignals()
when EINTR occurs so we needn't do it ourselves. */
if
(
_PyIO_trap_eintr
())
{
continue
;
}
goto
fail
;
}
if
(
res
==
0
)
/* EOF */
break
;
if
(
chunks
==
NULL
)
{
...
...
@@ -1728,8 +1734,14 @@ _textiowrapper_readline(textio *self, Py_ssize_t limit)
while
(
!
self
->
decoded_chars
||
!
PyUnicode_GET_LENGTH
(
self
->
decoded_chars
))
{
res
=
textiowrapper_read_chunk
(
self
,
0
);
if
(
res
<
0
)
if
(
res
<
0
)
{
/* NOTE: PyErr_SetFromErrno() calls PyErr_CheckSignals()
when EINTR occurs so we needn't do it ourselves. */
if
(
_PyIO_trap_eintr
())
{
continue
;
}
goto
error
;
}
if
(
res
==
0
)
break
;
}
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment