/*
    An implementation of Buffered I/O as defined by PEP 3116 - "New I/O"

    Classes defined here: BufferedIOBase, BufferedReader, BufferedWriter,
    BufferedRandom.

    Written by Amaury Forgeot d'Arc and Antoine Pitrou
*/

#define PY_SSIZE_T_CLEAN
#include "Python.h"
#include "structmember.h"
#include "pythread.h"
#include "_iomodule.h"

_Py_IDENTIFIER(close);
_Py_IDENTIFIER(_dealloc_warn);
_Py_IDENTIFIER(flush);
_Py_IDENTIFIER(isatty);
_Py_IDENTIFIER(mode);
_Py_IDENTIFIER(name);
_Py_IDENTIFIER(peek);
_Py_IDENTIFIER(read);
_Py_IDENTIFIER(read1);
_Py_IDENTIFIER(readable);
_Py_IDENTIFIER(readinto);
_Py_IDENTIFIER(writable);
_Py_IDENTIFIER(write);

/*
 * BufferedIOBase class, inherits from IOBase.
 */
PyDoc_STRVAR(bufferediobase_doc,
    "Base class for buffered IO objects.\n"
    "\n"
    "The main difference with RawIOBase is that the read() method\n"
    "supports omitting the size argument, and does not have a default\n"
    "implementation that defers to readinto().\n"
    "\n"
    "In addition, read(), readinto() and write() may raise\n"
    "BlockingIOError if the underlying raw stream is in non-blocking\n"
    "mode and not ready; unlike their raw counterparts, they will never\n"
    "return None.\n"
    "\n"
    "A typical implementation should not inherit from a RawIOBase\n"
    "implementation, but wrap one.\n"
    );

static PyObject *
bufferediobase_readinto(PyObject *self, PyObject *args)
{
    Py_buffer buf;
    Py_ssize_t len;
    PyObject *data;
    _Py_IDENTIFIER(read);

    if (!PyArg_ParseTuple(args, "w*:readinto", &buf)) {
        return NULL;
    }

    data = _PyObject_CallMethodId(self, &PyId_read, "n", buf.len);
    if (data == NULL)
        goto error;

    if (!PyBytes_Check(data)) {
        Py_DECREF(data);
        PyErr_SetString(PyExc_TypeError, "read() should return bytes");
        goto error;
    }

    len = Py_SIZE(data);
    memcpy(buf.buf, PyBytes_AS_STRING(data), len);

    PyBuffer_Release(&buf);
    Py_DECREF(data);

    return PyLong_FromSsize_t(len);

  error:
    PyBuffer_Release(&buf);
    return NULL;
}

static PyObject *
bufferediobase_unsupported(const char *message)
{
    PyErr_SetString(IO_STATE->unsupported_operation, message);
    return NULL;
}

PyDoc_STRVAR(bufferediobase_detach_doc,
    "Disconnect this buffer from its underlying raw stream and return it.\n"
    "\n"
    "After the raw stream has been detached, the buffer is in an unusable\n"
    "state.\n");

static PyObject *
bufferediobase_detach(PyObject *self)
{
    return bufferediobase_unsupported("detach");
}

PyDoc_STRVAR(bufferediobase_read_doc,
    "Read and return up to n bytes.\n"
    "\n"
    "If the argument is omitted, None, or negative, reads and\n"
    "returns all data until EOF.\n"
    "\n"
    "If the argument is positive, and the underlying raw stream is\n"
    "not 'interactive', multiple raw reads may be issued to satisfy\n"
    "the byte count (unless EOF is reached first).  But for\n"
    "interactive raw streams (as well as sockets and pipes), at most\n"
    "one raw read will be issued, and a short result does not imply\n"
    "that EOF is imminent.\n"
    "\n"
    "Returns an empty bytes object on EOF.\n"
    "\n"
    "Returns None if the underlying raw stream was open in non-blocking\n"
    "mode and no data is available at the moment.\n");

static PyObject *
bufferediobase_read(PyObject *self, PyObject *args)
{
    return bufferediobase_unsupported("read");
}

PyDoc_STRVAR(bufferediobase_read1_doc,
    "Read and return up to n bytes, with at most one read() call\n"
    "to the underlying raw stream. A short result does not imply\n"
    "that EOF is imminent.\n"
    "\n"
    "Returns an empty bytes object on EOF.\n");

static PyObject *
bufferediobase_read1(PyObject *self, PyObject *args)
{
    return bufferediobase_unsupported("read1");
}

PyDoc_STRVAR(bufferediobase_write_doc,
    "Write the given buffer to the IO stream.\n"
    "\n"
    "Returns the number of bytes written, which is never less than\n"
    "len(b).\n"
    "\n"
    "Raises BlockingIOError if the buffer is full and the\n"
    "underlying raw stream cannot accept more data at the moment.\n");

static PyObject *
bufferediobase_write(PyObject *self, PyObject *args)
{
    return bufferediobase_unsupported("write");
}


static PyMethodDef bufferediobase_methods[] = {
    {"detach", (PyCFunction)bufferediobase_detach, METH_NOARGS, bufferediobase_detach_doc},
    {"read", bufferediobase_read, METH_VARARGS, bufferediobase_read_doc},
    {"read1", bufferediobase_read1, METH_VARARGS, bufferediobase_read1_doc},
    {"readinto", bufferediobase_readinto, METH_VARARGS, NULL},
    {"write", bufferediobase_write, METH_VARARGS, bufferediobase_write_doc},
    {NULL, NULL}
};

PyTypeObject PyBufferedIOBase_Type = {
    PyVarObject_HEAD_INIT(NULL, 0)
    "_io._BufferedIOBase",      /*tp_name*/
    0,                          /*tp_basicsize*/
    0,                          /*tp_itemsize*/
    0,                          /*tp_dealloc*/
    0,                          /*tp_print*/
    0,                          /*tp_getattr*/
    0,                          /*tp_setattr*/
    0,                          /*tp_compare */
    0,                          /*tp_repr*/
    0,                          /*tp_as_number*/
    0,                          /*tp_as_sequence*/
    0,                          /*tp_as_mapping*/
    0,                          /*tp_hash */
    0,                          /*tp_call*/
    0,                          /*tp_str*/
    0,                          /*tp_getattro*/
    0,                          /*tp_setattro*/
    0,                          /*tp_as_buffer*/
    Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,  /*tp_flags*/
    bufferediobase_doc,         /* tp_doc */
    0,                          /* tp_traverse */
    0,                          /* tp_clear */
    0,                          /* tp_richcompare */
    0,                          /* tp_weaklistoffset */
    0,                          /* tp_iter */
    0,                          /* tp_iternext */
    bufferediobase_methods,     /* tp_methods */
    0,                          /* tp_members */
    0,                          /* tp_getset */
    &PyIOBase_Type,             /* tp_base */
    0,                          /* tp_dict */
    0,                          /* tp_descr_get */
    0,                          /* tp_descr_set */
    0,                          /* tp_dictoffset */
    0,                          /* tp_init */
    0,                          /* tp_alloc */
    0,                          /* tp_new */
};


typedef struct {
    PyObject_HEAD

    PyObject *raw;
    int ok;    /* Initialized? */
    int detached;
    int readable;
    int writable;
    int deallocating;

    /* True if this is a vanilla Buffered object (rather than a user derived
       class) *and* the raw stream is a vanilla FileIO object. */
    int fast_closed_checks;

    /* Absolute position inside the raw stream (-1 if unknown). */
    Py_off_t abs_pos;

    /* A static buffer of size `buffer_size` */
    char *buffer;
    /* Current logical position in the buffer. */
    Py_off_t pos;
    /* Position of the raw stream in the buffer. */
    Py_off_t raw_pos;

    /* Just after the last buffered byte in the buffer, or -1 if the buffer
       isn't ready for reading. */
    Py_off_t read_end;

    /* Just after the last byte actually written */
    Py_off_t write_pos;
    /* Just after the last byte waiting to be written, or -1 if the buffer
       isn't ready for writing. */
    Py_off_t write_end;

#ifdef WITH_THREAD
    PyThread_type_lock lock;
    volatile long owner;
#endif

    Py_ssize_t buffer_size;
    Py_ssize_t buffer_mask;

    PyObject *dict;
    PyObject *weakreflist;
} buffered;

/*
    Implementation notes:

    * BufferedReader, BufferedWriter and BufferedRandom try to share most
      methods (this is helped by the members `readable` and `writable`, which
      are initialized in the respective constructors)
    * They also share a single buffer for reading and writing. This enables
      interleaved reads and writes without flushing. It also makes the logic
      a bit trickier to get right.
    * The absolute position of the raw stream is cached, if possible, in the
      `abs_pos` member. It must be updated every time an operation is done
      on the raw stream. If not sure, it can be reinitialized by calling
      _buffered_raw_tell(), which queries the raw stream (_buffered_raw_seek()
      also does it). To read it, use RAW_TELL().
    * Three helpers, _bufferedreader_raw_read, _bufferedwriter_raw_write and
      _bufferedwriter_flush_unlocked do a lot of useful housekeeping.

    NOTE: we should try to maintain block alignment of reads and writes to the
    raw stream (according to the buffer size), but for now it is only done
    in read() and friends.

*/

/* These macros protect the buffered object against concurrent operations. */

#ifdef WITH_THREAD

static int
_enter_buffered_busy(buffered *self)
{
    if (self->owner == PyThread_get_thread_ident()) {
        PyErr_Format(PyExc_RuntimeError,
                     "reentrant call inside %R", self);
        return 0;
    }
    Py_BEGIN_ALLOW_THREADS
    PyThread_acquire_lock(self->lock, 1);
    Py_END_ALLOW_THREADS
    return 1;
}

#define ENTER_BUFFERED(self) \
    ( (PyThread_acquire_lock(self->lock, 0) ? \
       1 : _enter_buffered_busy(self)) \
     && (self->owner = PyThread_get_thread_ident(), 1) )

#define LEAVE_BUFFERED(self) \
    do { \
        self->owner = 0; \
        PyThread_release_lock(self->lock); \
    } while(0);

#else
#define ENTER_BUFFERED(self) 1
#define LEAVE_BUFFERED(self)
#endif

#define CHECK_INITIALIZED(self) \
    if (self->ok <= 0) { \
        if (self->detached) { \
            PyErr_SetString(PyExc_ValueError, \
                 "raw stream has been detached"); \
        } else { \
            PyErr_SetString(PyExc_ValueError, \
                "I/O operation on uninitialized object"); \
        } \
        return NULL; \
    }

#define CHECK_INITIALIZED_INT(self) \
    if (self->ok <= 0) { \
        if (self->detached) { \
            PyErr_SetString(PyExc_ValueError, \
                 "raw stream has been detached"); \
        } else { \
            PyErr_SetString(PyExc_ValueError, \
                "I/O operation on uninitialized object"); \
        } \
        return -1; \
    }

#define IS_CLOSED(self) \
    (self->fast_closed_checks \
     ? _PyFileIO_closed(self->raw) \
     : buffered_closed(self))

#define CHECK_CLOSED(self, error_msg) \
    if (IS_CLOSED(self)) { \
        PyErr_SetString(PyExc_ValueError, error_msg); \
        return NULL; \
    }


#define VALID_READ_BUFFER(self) \
    (self->readable && self->read_end != -1)

#define VALID_WRITE_BUFFER(self) \
    (self->writable && self->write_end != -1)

#define ADJUST_POSITION(self, _new_pos) \
    do { \
        self->pos = _new_pos; \
        if (VALID_READ_BUFFER(self) && self->read_end < self->pos) \
            self->read_end = self->pos; \
    } while(0)

#define READAHEAD(self) \
    ((self->readable && VALID_READ_BUFFER(self)) \
        ? (self->read_end - self->pos) : 0)

#define RAW_OFFSET(self) \
    (((VALID_READ_BUFFER(self) || VALID_WRITE_BUFFER(self)) \
        && self->raw_pos >= 0) ? self->raw_pos - self->pos : 0)

#define RAW_TELL(self) \
    (self->abs_pos != -1 ? self->abs_pos : _buffered_raw_tell(self))

#define MINUS_LAST_BLOCK(self, size) \
    (self->buffer_mask ? \
        (size & ~self->buffer_mask) : \
        (self->buffer_size * (size / self->buffer_size)))


static void
buffered_dealloc(buffered *self)
{
    self->deallocating = 1;
    if (self->ok && _PyIOBase_finalize((PyObject *) self) < 0)
        return;
    _PyObject_GC_UNTRACK(self);
    self->ok = 0;
    if (self->weakreflist != NULL)
        PyObject_ClearWeakRefs((PyObject *)self);
    Py_CLEAR(self->raw);
    if (self->buffer) {
        PyMem_Free(self->buffer);
        self->buffer = NULL;
    }
#ifdef WITH_THREAD
    if (self->lock) {
        PyThread_free_lock(self->lock);
        self->lock = NULL;
    }
#endif
    Py_CLEAR(self->dict);
    Py_TYPE(self)->tp_free((PyObject *)self);
}

static PyObject *
buffered_sizeof(buffered *self, void *unused)
{
    Py_ssize_t res;

    res = sizeof(buffered);
    if (self->buffer)
        res += self->buffer_size;
    return PyLong_FromSsize_t(res);
}

static int
buffered_traverse(buffered *self, visitproc visit, void *arg)
{
    Py_VISIT(self->raw);
    Py_VISIT(self->dict);
    return 0;
}

static int
buffered_clear(buffered *self)
{
    if (self->ok && _PyIOBase_finalize((PyObject *) self) < 0)
        return -1;
    self->ok = 0;
    Py_CLEAR(self->raw);
    Py_CLEAR(self->dict);
    return 0;
}

/* Because this can call arbitrary code, it shouldn't be called when
   the refcount is 0 (that is, not directly from tp_dealloc unless
   the refcount has been temporarily re-incremented). */
static PyObject *
buffered_dealloc_warn(buffered *self, PyObject *source)
{
    if (self->ok && self->raw) {
        PyObject *r;
        r = _PyObject_CallMethodId(self->raw, &PyId__dealloc_warn, "O", source);
        if (r)
            Py_DECREF(r);
        else
            PyErr_Clear();
    }
    Py_RETURN_NONE;
}

/*
 * _BufferedIOMixin methods
 * This is not a class, just a collection of methods that will be reused
 * by BufferedReader and BufferedWriter
 */

/* Flush and close */

static PyObject *
buffered_simple_flush(buffered *self, PyObject *args)
{
    CHECK_INITIALIZED(self)
    return PyObject_CallMethodObjArgs(self->raw, _PyIO_str_flush, NULL);
}

static int
buffered_closed(buffered *self)
{
    int closed;
    PyObject *res;
    CHECK_INITIALIZED_INT(self)
    res = PyObject_GetAttr(self->raw, _PyIO_str_closed);
    if (res == NULL)
        return -1;
    closed = PyObject_IsTrue(res);
    Py_DECREF(res);
    return closed;
}

static PyObject *
buffered_closed_get(buffered *self, void *context)
{
    CHECK_INITIALIZED(self)
    return PyObject_GetAttr(self->raw, _PyIO_str_closed);
}

static PyObject *
buffered_close(buffered *self, PyObject *args)
{
    PyObject *res = NULL, *exc = NULL, *val, *tb;
    int r;

    CHECK_INITIALIZED(self)
    if (!ENTER_BUFFERED(self))
        return NULL;

    r = buffered_closed(self);
    if (r < 0)
        goto end;
    if (r > 0) {
        res = Py_None;
        Py_INCREF(res);
        goto end;
    }

    if (self->deallocating) {
        PyObject *r = buffered_dealloc_warn(self, (PyObject *) self);
        if (r)
            Py_DECREF(r);
        else
            PyErr_Clear();
    }
    /* flush() will most probably re-take the lock, so drop it first */
    LEAVE_BUFFERED(self)
    res = PyObject_CallMethodObjArgs((PyObject *)self, _PyIO_str_flush, NULL);
    if (!ENTER_BUFFERED(self))
        return NULL;
    if (res == NULL)
        PyErr_Fetch(&exc, &val, &tb);
    else
        Py_DECREF(res);

    res = PyObject_CallMethodObjArgs(self->raw, _PyIO_str_close, NULL);

    if (self->buffer) {
        PyMem_Free(self->buffer);
        self->buffer = NULL;
    }

    if (exc != NULL) {
        if (res != NULL) {
            Py_CLEAR(res);
            PyErr_Restore(exc, val, tb);
        }
        else {
            PyObject *val2;
            Py_DECREF(exc);
            Py_XDECREF(tb);
            PyErr_Fetch(&exc, &val2, &tb);
            PyErr_NormalizeException(&exc, &val2, &tb);
            PyException_SetContext(val2, val);
            PyErr_Restore(exc, val2, tb);
        }
    }

end:
    LEAVE_BUFFERED(self)
    return res;
}

/* detach */

static PyObject *
buffered_detach(buffered *self, PyObject *args)
{
    PyObject *raw, *res;
    CHECK_INITIALIZED(self)
    res = PyObject_CallMethodObjArgs((PyObject *)self, _PyIO_str_flush, NULL);
    if (res == NULL)
        return NULL;
    Py_DECREF(res);
    raw = self->raw;
    self->raw = NULL;
    self->detached = 1;
    self->ok = 0;
    return raw;
}

/* Inquiries */

static PyObject *
buffered_seekable(buffered *self, PyObject *args)
{
    CHECK_INITIALIZED(self)
    return PyObject_CallMethodObjArgs(self->raw, _PyIO_str_seekable, NULL);
}

static PyObject *
buffered_readable(buffered *self, PyObject *args)
{
    CHECK_INITIALIZED(self)
    return PyObject_CallMethodObjArgs(self->raw, _PyIO_str_readable, NULL);
}

static PyObject *
buffered_writable(buffered *self, PyObject *args)
{
    CHECK_INITIALIZED(self)
    return PyObject_CallMethodObjArgs(self->raw, _PyIO_str_writable, NULL);
}

static PyObject *
buffered_name_get(buffered *self, void *context)
{
    CHECK_INITIALIZED(self)
    return _PyObject_GetAttrId(self->raw, &PyId_name);
}

static PyObject *
buffered_mode_get(buffered *self, void *context)
{
    CHECK_INITIALIZED(self)
    return _PyObject_GetAttrId(self->raw, &PyId_mode);
}

/* Lower-level APIs */

static PyObject *
buffered_fileno(buffered *self, PyObject *args)
{
    CHECK_INITIALIZED(self)
    return PyObject_CallMethodObjArgs(self->raw, _PyIO_str_fileno, NULL);
}

static PyObject *
buffered_isatty(buffered *self, PyObject *args)
{
    CHECK_INITIALIZED(self)
    return PyObject_CallMethodObjArgs(self->raw, _PyIO_str_isatty, NULL);
}

/* Serialization */

static PyObject *
buffered_getstate(buffered *self, PyObject *args)
{
    PyErr_Format(PyExc_TypeError,
                 "cannot serialize '%s' object", Py_TYPE(self)->tp_name);
    return NULL;
}

/* Forward decls */
static PyObject *
_bufferedwriter_flush_unlocked(buffered *);
static Py_ssize_t
_bufferedreader_fill_buffer(buffered *self);
static void
_bufferedreader_reset_buf(buffered *self);
static void
_bufferedwriter_reset_buf(buffered *self);
static PyObject *
_bufferedreader_peek_unlocked(buffered *self);
static PyObject *
_bufferedreader_read_all(buffered *self);
static PyObject *
_bufferedreader_read_fast(buffered *self, Py_ssize_t);
static PyObject *
_bufferedreader_read_generic(buffered *self, Py_ssize_t);
static Py_ssize_t
_bufferedreader_raw_read(buffered *self, char *start, Py_ssize_t len);

/*
 * Helpers
 */

/* Sets the current error to BlockingIOError */
static void
_set_BlockingIOError(char *msg, Py_ssize_t written)
{
    PyObject *err;
    err = PyObject_CallFunction(PyExc_BlockingIOError, "isn",
                                errno, msg, written);
    if (err)
        PyErr_SetObject(PyExc_BlockingIOError, err);
    Py_XDECREF(err);
}

/* Returns the address of the `written` member if a BlockingIOError was
   raised, NULL otherwise. The error is always re-raised. */
static Py_ssize_t *
_buffered_check_blocking_error(void)
{
    PyObject *t, *v, *tb;
    PyOSErrorObject *err;

    PyErr_Fetch(&t, &v, &tb);
    if (v == NULL || !PyErr_GivenExceptionMatches(v, PyExc_BlockingIOError)) {
        PyErr_Restore(t, v, tb);
        return NULL;
    }
    err = (PyOSErrorObject *) v;
    /* TODO: sanity check (err->written >= 0) */
    PyErr_Restore(t, v, tb);
    return &err->written;
}

static Py_off_t
_buffered_raw_tell(buffered *self)
{
    Py_off_t n;
    PyObject *res;
    res = PyObject_CallMethodObjArgs(self->raw, _PyIO_str_tell, NULL);
    if (res == NULL)
        return -1;
    n = PyNumber_AsOff_t(res, PyExc_ValueError);
    Py_DECREF(res);
    if (n < 0) {
        if (!PyErr_Occurred())
            PyErr_Format(PyExc_IOError,
                         "Raw stream returned invalid position %" PY_PRIdOFF,
                         (PY_OFF_T_COMPAT)n);
        return -1;
    }
    self->abs_pos = n;
    return n;
}

static Py_off_t
_buffered_raw_seek(buffered *self, Py_off_t target, int whence)
{
    PyObject *res, *posobj, *whenceobj;
    Py_off_t n;

    posobj = PyLong_FromOff_t(target);
    if (posobj == NULL)
        return -1;
    whenceobj = PyLong_FromLong(whence);
    if (whenceobj == NULL) {
        Py_DECREF(posobj);
        return -1;
    }
    res = PyObject_CallMethodObjArgs(self->raw, _PyIO_str_seek,
                                     posobj, whenceobj, NULL);
    Py_DECREF(posobj);
    Py_DECREF(whenceobj);
    if (res == NULL)
        return -1;
    n = PyNumber_AsOff_t(res, PyExc_ValueError);
    Py_DECREF(res);
    if (n < 0) {
        if (!PyErr_Occurred())
            PyErr_Format(PyExc_IOError,
                         "Raw stream returned invalid position %" PY_PRIdOFF,
                         (PY_OFF_T_COMPAT)n);
        return -1;
    }
    self->abs_pos = n;
    return n;
}

static int
_buffered_init(buffered *self)
{
    Py_ssize_t n;
    if (self->buffer_size <= 0) {
        PyErr_SetString(PyExc_ValueError,
            "buffer size must be strictly positive");
        return -1;
    }
    if (self->buffer)
        PyMem_Free(self->buffer);
    self->buffer = PyMem_Malloc(self->buffer_size);
    if (self->buffer == NULL) {
        PyErr_NoMemory();
        return -1;
    }
#ifdef WITH_THREAD
    if (self->lock)
        PyThread_free_lock(self->lock);
    self->lock = PyThread_allocate_lock();
    if (self->lock == NULL) {
        PyErr_SetString(PyExc_RuntimeError, "can't allocate read lock");
        return -1;
    }
    self->owner = 0;
#endif
    /* Find out whether buffer_size is a power of 2 */
    /* XXX is this optimization useful? */
    for (n = self->buffer_size - 1; n & 1; n >>= 1)
        ;
    if (n == 0)
        self->buffer_mask = self->buffer_size - 1;
    else
        self->buffer_mask = 0;
    if (_buffered_raw_tell(self) == -1)
        PyErr_Clear();
    return 0;
}

/* 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.
*/
int
_PyIO_trap_eintr(void)
{
    static PyObject *eintr_int = NULL;
    PyObject *typ, *val, *tb;
    PyEnvironmentErrorObject *env_err;

    if (eintr_int == NULL) {
        eintr_int = PyLong_FromLong(EINTR);
        assert(eintr_int != NULL);
    }
    if (!PyErr_ExceptionMatches(PyExc_EnvironmentError))
        return 0;
    PyErr_Fetch(&typ, &val, &tb);
    PyErr_NormalizeException(&typ, &val, &tb);
    env_err = (PyEnvironmentErrorObject *) val;
    assert(env_err != NULL);
    if (env_err->myerrno != NULL &&
        PyObject_RichCompareBool(env_err->myerrno, eintr_int, Py_EQ) > 0) {
        Py_DECREF(typ);
        Py_DECREF(val);
        Py_XDECREF(tb);
        return 1;
    }
    /* This silences any error set by PyObject_RichCompareBool() */
    PyErr_Restore(typ, val, tb);
    return 0;
}

/*
 * Shared methods and wrappers
 */

static PyObject *
buffered_flush_and_rewind_unlocked(buffered *self)
{
    PyObject *res;

    res = _bufferedwriter_flush_unlocked(self);
    if (res == NULL)
        return NULL;
    Py_DECREF(res);

    if (self->readable) {
        /* Rewind the raw stream so that its position corresponds to
           the current logical position. */
        Py_off_t n;
        n = _buffered_raw_seek(self, -RAW_OFFSET(self), 1);
        _bufferedreader_reset_buf(self);
        if (n == -1)
            return NULL;
    }
    Py_RETURN_NONE;
}

static PyObject *
buffered_flush(buffered *self, PyObject *args)
{
    PyObject *res;

    CHECK_INITIALIZED(self)
    CHECK_CLOSED(self, "flush of closed file")

    if (!ENTER_BUFFERED(self))
        return NULL;
    res = buffered_flush_and_rewind_unlocked(self);
    LEAVE_BUFFERED(self)

    return res;
}

static PyObject *
buffered_peek(buffered *self, PyObject *args)
{
    Py_ssize_t n = 0;
    PyObject *res = NULL;

    CHECK_INITIALIZED(self)
    if (!PyArg_ParseTuple(args, "|n:peek", &n)) {
        return NULL;
    }

    if (!ENTER_BUFFERED(self))
        return NULL;

    if (self->writable) {
        res = buffered_flush_and_rewind_unlocked(self);
        if (res == NULL)
            goto end;
        Py_CLEAR(res);
    }
    res = _bufferedreader_peek_unlocked(self);

end:
    LEAVE_BUFFERED(self)
    return res;
}

static PyObject *
buffered_read(buffered *self, PyObject *args)
{
    Py_ssize_t n = -1;
    PyObject *res;

    CHECK_INITIALIZED(self)
    if (!PyArg_ParseTuple(args, "|O&:read", &_PyIO_ConvertSsize_t, &n)) {
        return NULL;
    }
    if (n < -1) {
        PyErr_SetString(PyExc_ValueError,
                        "read length must be positive or -1");
        return NULL;
    }

    CHECK_CLOSED(self, "read of closed file")

    if (n == -1) {
        /* The number of bytes is unspecified, read until the end of stream */
        if (!ENTER_BUFFERED(self))
            return NULL;
        res = _bufferedreader_read_all(self);
    }
    else {
        res = _bufferedreader_read_fast(self, n);
        if (res != Py_None)
            return res;
        Py_DECREF(res);
        if (!ENTER_BUFFERED(self))
            return NULL;
        res = _bufferedreader_read_generic(self, n);
    }

    LEAVE_BUFFERED(self)
    return res;
}

static PyObject *
buffered_read1(buffered *self, PyObject *args)
{
    Py_ssize_t n, have, r;
    PyObject *res = NULL;

    CHECK_INITIALIZED(self)
    if (!PyArg_ParseTuple(args, "n:read1", &n)) {
        return NULL;
    }

    if (n < 0) {
        PyErr_SetString(PyExc_ValueError,
                        "read length must be positive");
        return NULL;
    }
    if (n == 0)
        return PyBytes_FromStringAndSize(NULL, 0);

    /* Return up to n bytes.  If at least one byte is buffered, we
       only return buffered bytes.  Otherwise, we do one raw read. */

    have = Py_SAFE_DOWNCAST(READAHEAD(self), Py_off_t, Py_ssize_t);
    if (have > 0) {
        n = Py_MIN(have, n);
        res = _bufferedreader_read_fast(self, n);
        assert(res != Py_None);
        return res;
    }
    res = PyBytes_FromStringAndSize(NULL, n);
    if (res == NULL)
        return NULL;
    if (!ENTER_BUFFERED(self)) {
        Py_DECREF(res);
        return NULL;
    }
    _bufferedreader_reset_buf(self);
    r = _bufferedreader_raw_read(self, PyBytes_AS_STRING(res), n);
    LEAVE_BUFFERED(self)
    if (r == -1) {
        Py_DECREF(res);
        return NULL;
    }
    if (r == -2)
        r = 0;
    if (n > r)
        _PyBytes_Resize(&res, r);
    return res;
}

static PyObject *
buffered_readinto(buffered *self, PyObject *args)
{
    Py_buffer buf;
    Py_ssize_t n, written = 0, remaining;
    PyObject *res = NULL;

    CHECK_INITIALIZED(self)

    if (!PyArg_ParseTuple(args, "w*:readinto", &buf))
        return NULL;

    n = Py_SAFE_DOWNCAST(READAHEAD(self), Py_off_t, Py_ssize_t);
    if (n > 0) {
        if (n >= buf.len) {
            memcpy(buf.buf, self->buffer + self->pos, buf.len);
            self->pos += buf.len;
            res = PyLong_FromSsize_t(buf.len);
            goto end_unlocked;
        }
        memcpy(buf.buf, self->buffer + self->pos, n);
        self->pos += n;
        written = n;
    }

    if (!ENTER_BUFFERED(self))
        goto end_unlocked;

    if (self->writable) {
        res = buffered_flush_and_rewind_unlocked(self);
        if (res == NULL)
            goto end;
        Py_CLEAR(res);
    }

    _bufferedreader_reset_buf(self);
    self->pos = 0;

    for (remaining = buf.len - written;
         remaining > 0;
         written += n, remaining -= n) {
        /* If remaining bytes is larger than internal buffer size, copy
         * directly into caller's buffer. */
        if (remaining > self->buffer_size) {
            n = _bufferedreader_raw_read(self, (char *) buf.buf + written,
                                         remaining);
        }
        else {
            n = _bufferedreader_fill_buffer(self);
            if (n > 0) {
                if (n > remaining)
                    n = remaining;
                memcpy((char *) buf.buf + written,
                       self->buffer + self->pos, n);
                self->pos += n;
                continue; /* short circuit */
            }
        }
        if (n == 0 || (n == -2 && written > 0))
            break;
        if (n < 0) {
            if (n == -2) {
                Py_INCREF(Py_None);
                res = Py_None;
            }
            goto end;
        }
    }
    res = PyLong_FromSsize_t(written);

end:
    LEAVE_BUFFERED(self);
end_unlocked:
    PyBuffer_Release(&buf);
    return res;
}

static PyObject *
_buffered_readline(buffered *self, Py_ssize_t limit)
{
    PyObject *res = NULL;
    PyObject *chunks = NULL;
    Py_ssize_t n, written = 0;
    const char *start, *s, *end;

    CHECK_CLOSED(self, "readline of closed file")

    /* First, try to find a line in the buffer. This can run unlocked because
       the calls to the C API are simple enough that they can't trigger
       any thread switch. */
    n = Py_SAFE_DOWNCAST(READAHEAD(self), Py_off_t, Py_ssize_t);
    if (limit >= 0 && n > limit)
        n = limit;
    start = self->buffer + self->pos;
    s = memchr(start, '\n', n);
    if (s != NULL) {
        res = PyBytes_FromStringAndSize(start, s - start + 1);
        if (res != NULL)
            self->pos += s - start + 1;
        goto end_unlocked;
    }
    if (n == limit) {
        res = PyBytes_FromStringAndSize(start, n);
        if (res != NULL)
            self->pos += n;
        goto end_unlocked;
    }

    if (!ENTER_BUFFERED(self))
        goto end_unlocked;

    /* Now we try to get some more from the raw stream */
    chunks = PyList_New(0);
    if (chunks == NULL)
        goto end;
    if (n > 0) {
        res = PyBytes_FromStringAndSize(start, n);
        if (res == NULL)
            goto end;
        if (PyList_Append(chunks, res) < 0) {
            Py_CLEAR(res);
            goto end;
        }
        Py_CLEAR(res);
        written += n;
        self->pos += n;
        if (limit >= 0)
            limit -= n;
    }
    if (self->writable) {
        PyObject *r = buffered_flush_and_rewind_unlocked(self);
        if (r == NULL)
            goto end;
        Py_DECREF(r);
    }

    for (;;) {
        _bufferedreader_reset_buf(self);
        n = _bufferedreader_fill_buffer(self);
        if (n == -1)
            goto end;
        if (n <= 0)
            break;
        if (limit >= 0 && n > limit)
            n = limit;
        start = self->buffer;
        end = start + n;
        s = start;
        while (s < end) {
            if (*s++ == '\n') {
                res = PyBytes_FromStringAndSize(start, s - start);
                if (res == NULL)
                    goto end;
                self->pos = s - start;
                goto found;
            }
        }
        res = PyBytes_FromStringAndSize(start, n);
        if (res == NULL)
            goto end;
        if (n == limit) {
            self->pos = n;
            break;
        }
        if (PyList_Append(chunks, res) < 0) {
            Py_CLEAR(res);
            goto end;
        }
        Py_CLEAR(res);
        written += n;
        if (limit >= 0)
            limit -= n;
    }
found:
    if (res != NULL && PyList_Append(chunks, res) < 0) {
        Py_CLEAR(res);
        goto end;
    }
    Py_CLEAR(res);
    res = _PyBytes_Join(_PyIO_empty_bytes, chunks);

end:
    LEAVE_BUFFERED(self)
end_unlocked:
    Py_XDECREF(chunks);
    return res;
}

static PyObject *
buffered_readline(buffered *self, PyObject *args)
{
    Py_ssize_t limit = -1;

    CHECK_INITIALIZED(self)
    if (!PyArg_ParseTuple(args, "|O&:readline", &_PyIO_ConvertSsize_t, &limit))
        return NULL;
    return _buffered_readline(self, limit);
}


static PyObject *
buffered_tell(buffered *self, PyObject *args)
{
    Py_off_t pos;

    CHECK_INITIALIZED(self)
    pos = _buffered_raw_tell(self);
    if (pos == -1)
        return NULL;
    pos -= RAW_OFFSET(self);
    /* TODO: sanity check (pos >= 0) */
    return PyLong_FromOff_t(pos);
}

static PyObject *
buffered_seek(buffered *self, PyObject *args)
{
    Py_off_t target, n;
    int whence = 0;
    PyObject *targetobj, *res = NULL;

    CHECK_INITIALIZED(self)
    if (!PyArg_ParseTuple(args, "O|i:seek", &targetobj, &whence)) {
        return NULL;
    }

    /* Do some error checking instead of trusting OS 'seek()'
    ** error detection, just in case.
    */
    if ((whence < 0 || whence >2)
#ifdef SEEK_HOLE
        && (whence != SEEK_HOLE)
#endif
#ifdef SEEK_DATA
        && (whence != SEEK_DATA)
#endif
        ) {
        PyErr_Format(PyExc_ValueError,
                     "whence value %d unsupported", whence);
        return NULL;
    }

    CHECK_CLOSED(self, "seek of closed file")

    if (_PyIOBase_check_seekable(self->raw, Py_True) == NULL)
        return NULL;

    target = PyNumber_AsOff_t(targetobj, PyExc_ValueError);
    if (target == -1 && PyErr_Occurred())
        return NULL;

    /* SEEK_SET and SEEK_CUR are special because we could seek inside the
       buffer. Other whence values must be managed without this optimization.
       Some Operating Systems can provide additional values, like
       SEEK_HOLE/SEEK_DATA. */
    if (((whence == 0) || (whence == 1)) && self->readable) {
        Py_off_t current, avail;
        /* Check if seeking leaves us inside the current buffer,
           so as to return quickly if possible. Also, we needn't take the
           lock in this fast path.
           Don't know how to do that when whence == 2, though. */
        /* NOTE: RAW_TELL() can release the GIL but the object is in a stable
           state at this point. */
        current = RAW_TELL(self);
        avail = READAHEAD(self);
        if (avail > 0) {
            Py_off_t offset;
            if (whence == 0)
                offset = target - (current - RAW_OFFSET(self));
            else
                offset = target;
            if (offset >= -self->pos && offset <= avail) {
                self->pos += offset;
                return PyLong_FromOff_t(current - avail + offset);
            }
        }
    }

    if (!ENTER_BUFFERED(self))
        return NULL;

    /* Fallback: invoke raw seek() method and clear buffer */
    if (self->writable) {
        res = _bufferedwriter_flush_unlocked(self);
        if (res == NULL)
            goto end;
        Py_CLEAR(res);
        _bufferedwriter_reset_buf(self);
    }

    /* TODO: align on block boundary and read buffer if needed? */
    if (whence == 1)
        target -= RAW_OFFSET(self);
    n = _buffered_raw_seek(self, target, whence);
    if (n == -1)
        goto end;
    self->raw_pos = -1;
    res = PyLong_FromOff_t(n);
    if (res != NULL && self->readable)
        _bufferedreader_reset_buf(self);

end:
    LEAVE_BUFFERED(self)
    return res;
}

static PyObject *
buffered_truncate(buffered *self, PyObject *args)
{
    PyObject *pos = Py_None;
    PyObject *res = NULL;

    CHECK_INITIALIZED(self)
    if (!PyArg_ParseTuple(args, "|O:truncate", &pos)) {
        return NULL;
    }

    if (!ENTER_BUFFERED(self))
        return NULL;

    if (self->writable) {
        res = buffered_flush_and_rewind_unlocked(self);
        if (res == NULL)
            goto end;
        Py_CLEAR(res);
    }
    res = PyObject_CallMethodObjArgs(self->raw, _PyIO_str_truncate, pos, NULL);
    if (res == NULL)
        goto end;
    /* Reset cached position */
    if (_buffered_raw_tell(self) == -1)
        PyErr_Clear();

end:
    LEAVE_BUFFERED(self)
    return res;
}

static PyObject *
buffered_iternext(buffered *self)
{
    PyObject *line;
    PyTypeObject *tp;

    CHECK_INITIALIZED(self);

    tp = Py_TYPE(self);
    if (tp == &PyBufferedReader_Type ||
        tp == &PyBufferedRandom_Type) {
        /* Skip method call overhead for speed */
        line = _buffered_readline(self, -1);
    }
    else {
        line = PyObject_CallMethodObjArgs((PyObject *)self,
                                           _PyIO_str_readline, NULL);
        if (line && !PyBytes_Check(line)) {
            PyErr_Format(PyExc_IOError,
                         "readline() should have returned a bytes object, "
                         "not '%.200s'", Py_TYPE(line)->tp_name);
            Py_DECREF(line);
            return NULL;
        }
    }

    if (line == NULL)
        return NULL;

    if (PyBytes_GET_SIZE(line) == 0) {
        /* Reached EOF or would have blocked */
        Py_DECREF(line);
        return NULL;
    }

    return line;
}

static PyObject *
buffered_repr(buffered *self)
{
    PyObject *nameobj, *res;

    nameobj = _PyObject_GetAttrId((PyObject *) self, &PyId_name);
    if (nameobj == NULL) {
        if (PyErr_ExceptionMatches(PyExc_AttributeError))
            PyErr_Clear();
        else
            return NULL;
        res = PyUnicode_FromFormat("<%s>", Py_TYPE(self)->tp_name);
    }
    else {
        res = PyUnicode_FromFormat("<%s name=%R>",
                                   Py_TYPE(self)->tp_name, nameobj);
        Py_DECREF(nameobj);
    }
    return res;
}

/*
 * class BufferedReader
 */

PyDoc_STRVAR(bufferedreader_doc,
             "Create a new buffered reader using the given readable raw IO object.");

static void _bufferedreader_reset_buf(buffered *self)
{
    self->read_end = -1;
}

static int
bufferedreader_init(buffered *self, PyObject *args, PyObject *kwds)
{
    char *kwlist[] = {"raw", "buffer_size", NULL};
    Py_ssize_t buffer_size = DEFAULT_BUFFER_SIZE;
    PyObject *raw;

    self->ok = 0;
    self->detached = 0;

    if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|n:BufferedReader", kwlist,
                                     &raw, &buffer_size)) {
        return -1;
    }

    if (_PyIOBase_check_readable(raw, Py_True) == NULL)
        return -1;

    Py_CLEAR(self->raw);
    Py_INCREF(raw);
    self->raw = raw;
    self->buffer_size = buffer_size;
    self->readable = 1;
    self->writable = 0;

    if (_buffered_init(self) < 0)
        return -1;
    _bufferedreader_reset_buf(self);

    self->fast_closed_checks = (Py_TYPE(self) == &PyBufferedReader_Type &&
                                Py_TYPE(raw) == &PyFileIO_Type);

    self->ok = 1;
    return 0;
}

static Py_ssize_t
_bufferedreader_raw_read(buffered *self, char *start, Py_ssize_t len)
{
    Py_buffer buf;
    PyObject *memobj, *res;
    Py_ssize_t n;
    /* NOTE: the buffer needn't be released as its object is NULL. */
    if (PyBuffer_FillInfo(&buf, NULL, start, len, 0, PyBUF_CONTIG) == -1)
        return -1;
    memobj = PyMemoryView_FromBuffer(&buf);
    if (memobj == NULL)
        return -1;
    /* NOTE: PyErr_SetFromErrno() calls PyErr_CheckSignals() when EINTR
       occurs so we needn't do it ourselves.
       We then retry reading, ignoring the signal if no handler has
       raised (see issue #10956).
    */
    do {
        res = PyObject_CallMethodObjArgs(self->raw, _PyIO_str_readinto, memobj, NULL);
    } while (res == NULL && _PyIO_trap_eintr());
    Py_DECREF(memobj);
    if (res == NULL)
        return -1;
    if (res == Py_None) {
        /* Non-blocking stream would have blocked. Special return code! */
        Py_DECREF(res);
        return -2;
    }
    n = PyNumber_AsSsize_t(res, PyExc_ValueError);
    Py_DECREF(res);
    if (n < 0 || n > len) {
        PyErr_Format(PyExc_IOError,
                     "raw readinto() returned invalid length %zd "
                     "(should have been between 0 and %zd)", n, len);
        return -1;
    }
    if (n > 0 && self->abs_pos != -1)
        self->abs_pos += n;
    return n;
}

static Py_ssize_t
_bufferedreader_fill_buffer(buffered *self)
{
    Py_ssize_t start, len, n;
    if (VALID_READ_BUFFER(self))
        start = Py_SAFE_DOWNCAST(self->read_end, Py_off_t, Py_ssize_t);
    else
        start = 0;
    len = self->buffer_size - start;
    n = _bufferedreader_raw_read(self, self->buffer + start, len);
    if (n <= 0)
        return n;
    self->read_end = start + n;
    self->raw_pos = start + n;
    return n;
}

static PyObject *
_bufferedreader_read_all(buffered *self)
{
    Py_ssize_t current_size;
    PyObject *res, *data = NULL, *chunk, *chunks;

    /* First copy what we have in the current buffer. */
    current_size = Py_SAFE_DOWNCAST(READAHEAD(self), Py_off_t, Py_ssize_t);
    if (current_size) {
        data = PyBytes_FromStringAndSize(
            self->buffer + self->pos, current_size);
        if (data == NULL)
            return NULL;
        self->pos += current_size;
    }
    /* We're going past the buffer's bounds, flush it */
    if (self->writable) {
        res = buffered_flush_and_rewind_unlocked(self);
        if (res == NULL)
            return NULL;
        Py_CLEAR(res);
    }
    _bufferedreader_reset_buf(self);

    if (PyObject_HasAttr(self->raw, _PyIO_str_readall)) {
        chunk = PyObject_CallMethodObjArgs(self->raw, _PyIO_str_readall, NULL);
        if (chunk == NULL)
            return NULL;
        if (chunk != Py_None && !PyBytes_Check(chunk)) {
            Py_XDECREF(data);
            Py_DECREF(chunk);
            PyErr_SetString(PyExc_TypeError, "readall() should return bytes");
            return NULL;
        }
        if (chunk == Py_None) {
            if (current_size == 0)
                return chunk;
            else {
                Py_DECREF(chunk);
                return data;
            }
        }
        else if (current_size) {
            PyBytes_Concat(&data, chunk);
            Py_DECREF(chunk);
            if (data == NULL)
                return NULL;
            return data;
        } else
            return chunk;
    }

    chunks = PyList_New(0);
    if (chunks == NULL) {
        Py_XDECREF(data);
        return NULL;
    }

    while (1) {
        if (data) {
            if (PyList_Append(chunks, data) < 0) {
                Py_DECREF(data);
                Py_DECREF(chunks);
                return NULL;
            }
            Py_DECREF(data);
        }

        /* Read until EOF or until read() would block. */
        data = PyObject_CallMethodObjArgs(self->raw, _PyIO_str_read, NULL);
        if (data == NULL) {
            Py_DECREF(chunks);
            return NULL;
        }
        if (data != Py_None && !PyBytes_Check(data)) {
            Py_DECREF(data);
            Py_DECREF(chunks);
            PyErr_SetString(PyExc_TypeError, "read() should return bytes");
            return NULL;
        }
        if (data == Py_None || PyBytes_GET_SIZE(data) == 0) {
            if (current_size == 0) {
                Py_DECREF(chunks);
                return data;
            }
            else {
                res = _PyBytes_Join(_PyIO_empty_bytes, chunks);
                Py_DECREF(data);
                Py_DECREF(chunks);
                return res;
            }
        }
        current_size += PyBytes_GET_SIZE(data);
        if (self->abs_pos != -1)
            self->abs_pos += PyBytes_GET_SIZE(data);
    }
}

/* Read n bytes from the buffer if it can, otherwise return None.
   This function is simple enough that it can run unlocked. */
static PyObject *
_bufferedreader_read_fast(buffered *self, Py_ssize_t n)
{
    Py_ssize_t current_size;

    current_size = Py_SAFE_DOWNCAST(READAHEAD(self), Py_off_t, Py_ssize_t);
    if (n <= current_size) {
        /* Fast path: the data to read is fully buffered. */
        PyObject *res = PyBytes_FromStringAndSize(self->buffer + self->pos, n);
        if (res != NULL)
            self->pos += n;
        return res;
    }
    Py_RETURN_NONE;
}

/* Generic read function: read from the stream until enough bytes are read,
 * or until an EOF occurs or until read() would block.
 */
static PyObject *
_bufferedreader_read_generic(buffered *self, Py_ssize_t n)
{
    PyObject *res = NULL;
    Py_ssize_t current_size, remaining, written;
    char *out;

    current_size = Py_SAFE_DOWNCAST(READAHEAD(self), Py_off_t, Py_ssize_t);
    if (n <= current_size)
        return _bufferedreader_read_fast(self, n);

    res = PyBytes_FromStringAndSize(NULL, n);
    if (res == NULL)
        goto error;
    out = PyBytes_AS_STRING(res);
    remaining = n;
    written = 0;
    if (current_size > 0) {
        memcpy(out, self->buffer + self->pos, current_size);
        remaining -= current_size;
        written += current_size;
        self->pos += current_size;
    }
    /* Flush the write buffer if necessary */
    if (self->writable) {
        PyObject *r = buffered_flush_and_rewind_unlocked(self);
        if (r == NULL)
            goto error;
        Py_DECREF(r);
    }
    _bufferedreader_reset_buf(self);
    while (remaining > 0) {
        /* We want to read a whole block at the end into buffer.
           If we had readv() we could do this in one pass. */
        Py_ssize_t r = MINUS_LAST_BLOCK(self, remaining);
        if (r == 0)
            break;
        r = _bufferedreader_raw_read(self, out + written, r);
        if (r == -1)
            goto error;
        if (r == 0 || r == -2) {
            /* EOF occurred or read() would block. */
            if (r == 0 || written > 0) {
                if (_PyBytes_Resize(&res, written))
                    goto error;
                return res;
            }
            Py_DECREF(res);
            Py_INCREF(Py_None);
            return Py_None;
        }
        remaining -= r;
        written += r;
    }
    assert(remaining <= self->buffer_size);
    self->pos = 0;
    self->raw_pos = 0;
    self->read_end = 0;
    /* NOTE: when the read is satisfied, we avoid issuing any additional
       reads, which could block indefinitely (e.g. on a socket).
       See issue #9550. */
    while (remaining > 0 && self->read_end < self->buffer_size) {
        Py_ssize_t r = _bufferedreader_fill_buffer(self);
        if (r == -1)
            goto error;
        if (r == 0 || r == -2) {
            /* EOF occurred or read() would block. */
            if (r == 0 || written > 0) {
                if (_PyBytes_Resize(&res, written))
                    goto error;
                return res;
            }
            Py_DECREF(res);
            Py_INCREF(Py_None);
            return Py_None;
        }
        if (remaining > r) {
            memcpy(out + written, self->buffer + self->pos, r);
            written += r;
            self->pos += r;
            remaining -= r;
        }
        else if (remaining > 0) {
            memcpy(out + written, self->buffer + self->pos, remaining);
            written += remaining;
            self->pos += remaining;
            remaining = 0;
        }
        if (remaining == 0)
            break;
    }

    return res;

error:
    Py_XDECREF(res);
    return NULL;
}

static PyObject *
_bufferedreader_peek_unlocked(buffered *self)
{
    Py_ssize_t have, r;

    have = Py_SAFE_DOWNCAST(READAHEAD(self), Py_off_t, Py_ssize_t);
    /* Constraints:
       1. we don't want to advance the file position.
       2. we don't want to lose block alignment, so we can't shift the buffer
          to make some place.
       Therefore, we either return `have` bytes (if > 0), or a full buffer.
    */
    if (have > 0) {
        return PyBytes_FromStringAndSize(self->buffer + self->pos, have);
    }

    /* Fill the buffer from the raw stream, and copy it to the result. */
    _bufferedreader_reset_buf(self);
    r = _bufferedreader_fill_buffer(self);
    if (r == -1)
        return NULL;
    if (r == -2)
        r = 0;
    self->pos = 0;
    return PyBytes_FromStringAndSize(self->buffer, r);
}

static PyMethodDef bufferedreader_methods[] = {
    /* BufferedIOMixin methods */
    {"detach", (PyCFunction)buffered_detach, METH_NOARGS},
    {"flush", (PyCFunction)buffered_simple_flush, METH_NOARGS},
    {"close", (PyCFunction)buffered_close, METH_NOARGS},
    {"seekable", (PyCFunction)buffered_seekable, METH_NOARGS},
    {"readable", (PyCFunction)buffered_readable, METH_NOARGS},
    {"writable", (PyCFunction)buffered_writable, METH_NOARGS},
    {"fileno", (PyCFunction)buffered_fileno, METH_NOARGS},
    {"isatty", (PyCFunction)buffered_isatty, METH_NOARGS},
    {"_dealloc_warn", (PyCFunction)buffered_dealloc_warn, METH_O},
    {"__getstate__", (PyCFunction)buffered_getstate, METH_NOARGS},

    {"read", (PyCFunction)buffered_read, METH_VARARGS},
    {"peek", (PyCFunction)buffered_peek, METH_VARARGS},
    {"read1", (PyCFunction)buffered_read1, METH_VARARGS},
    {"readinto", (PyCFunction)buffered_readinto, METH_VARARGS},
    {"readline", (PyCFunction)buffered_readline, METH_VARARGS},
    {"seek", (PyCFunction)buffered_seek, METH_VARARGS},
    {"tell", (PyCFunction)buffered_tell, METH_NOARGS},
    {"truncate", (PyCFunction)buffered_truncate, METH_VARARGS},
    {"__sizeof__", (PyCFunction)buffered_sizeof, METH_NOARGS},
    {NULL, NULL}
};

static PyMemberDef bufferedreader_members[] = {
    {"raw", T_OBJECT, offsetof(buffered, raw), READONLY},
    {NULL}
};

static PyGetSetDef bufferedreader_getset[] = {
    {"closed", (getter)buffered_closed_get, NULL, NULL},
    {"name", (getter)buffered_name_get, NULL, NULL},
    {"mode", (getter)buffered_mode_get, NULL, NULL},
    {NULL}
};


PyTypeObject PyBufferedReader_Type = {
    PyVarObject_HEAD_INIT(NULL, 0)
    "_io.BufferedReader",       /*tp_name*/
    sizeof(buffered),           /*tp_basicsize*/
    0,                          /*tp_itemsize*/
    (destructor)buffered_dealloc,     /*tp_dealloc*/
    0,                          /*tp_print*/
    0,                          /*tp_getattr*/
    0,                          /*tp_setattr*/
    0,                          /*tp_compare */
    (reprfunc)buffered_repr,    /*tp_repr*/
    0,                          /*tp_as_number*/
    0,                          /*tp_as_sequence*/
    0,                          /*tp_as_mapping*/
    0,                          /*tp_hash */
    0,                          /*tp_call*/
    0,                          /*tp_str*/
    0,                          /*tp_getattro*/
    0,                          /*tp_setattro*/
    0,                          /*tp_as_buffer*/
    Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE
            | Py_TPFLAGS_HAVE_GC, /*tp_flags*/
    bufferedreader_doc,         /* tp_doc */
    (traverseproc)buffered_traverse, /* tp_traverse */
    (inquiry)buffered_clear,    /* tp_clear */
    0,                          /* tp_richcompare */
    offsetof(buffered, weakreflist), /*tp_weaklistoffset*/
    0,                          /* tp_iter */
    (iternextfunc)buffered_iternext, /* tp_iternext */
    bufferedreader_methods,     /* tp_methods */
    bufferedreader_members,     /* tp_members */
    bufferedreader_getset,      /* tp_getset */
    0,                          /* tp_base */
    0,                          /* tp_dict */
    0,                          /* tp_descr_get */
    0,                          /* tp_descr_set */
    offsetof(buffered, dict), /* tp_dictoffset */
    (initproc)bufferedreader_init, /* tp_init */
    0,                          /* tp_alloc */
    PyType_GenericNew,          /* tp_new */
};



/*
 * class BufferedWriter
 */
PyDoc_STRVAR(bufferedwriter_doc,
    "A buffer for a writeable sequential RawIO object.\n"
    "\n"
    "The constructor creates a BufferedWriter for the given writeable raw\n"
    "stream. If the buffer_size is not given, it defaults to\n"
    "DEFAULT_BUFFER_SIZE.\n"
    );

static void
_bufferedwriter_reset_buf(buffered *self)
{
    self->write_pos = 0;
    self->write_end = -1;
}

static int
bufferedwriter_init(buffered *self, PyObject *args, PyObject *kwds)
{
    char *kwlist[] = {"raw", "buffer_size", NULL};
    Py_ssize_t buffer_size = DEFAULT_BUFFER_SIZE;
    PyObject *raw;

    self->ok = 0;
    self->detached = 0;

    if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|n:BufferedWriter", kwlist,
                                     &raw, &buffer_size)) {
        return -1;
    }

    if (_PyIOBase_check_writable(raw, Py_True) == NULL)
        return -1;

    Py_CLEAR(self->raw);
    Py_INCREF(raw);
    self->raw = raw;
    self->readable = 0;
    self->writable = 1;

    self->buffer_size = buffer_size;
    if (_buffered_init(self) < 0)
        return -1;
    _bufferedwriter_reset_buf(self);
    self->pos = 0;

    self->fast_closed_checks = (Py_TYPE(self) == &PyBufferedWriter_Type &&
                                Py_TYPE(raw) == &PyFileIO_Type);

    self->ok = 1;
    return 0;
}

static Py_ssize_t
_bufferedwriter_raw_write(buffered *self, char *start, Py_ssize_t len)
{
    Py_buffer buf;
    PyObject *memobj, *res;
    Py_ssize_t n;
    int errnum;
    /* NOTE: the buffer needn't be released as its object is NULL. */
    if (PyBuffer_FillInfo(&buf, NULL, start, len, 1, PyBUF_CONTIG_RO) == -1)
        return -1;
    memobj = PyMemoryView_FromBuffer(&buf);
    if (memobj == NULL)
        return -1;
    /* NOTE: PyErr_SetFromErrno() calls PyErr_CheckSignals() when EINTR
       occurs so we needn't do it ourselves.
       We then retry writing, ignoring the signal if no handler has
       raised (see issue #10956).
    */
    do {
        errno = 0;
        res = PyObject_CallMethodObjArgs(self->raw, _PyIO_str_write, memobj, NULL);
        errnum = errno;
    } while (res == NULL && _PyIO_trap_eintr());
    Py_DECREF(memobj);
    if (res == NULL)
        return -1;
    if (res == Py_None) {
        /* Non-blocking stream would have blocked. Special return code!
           Being paranoid we reset errno in case it is changed by code
           triggered by a decref.  errno is used by _set_BlockingIOError(). */
        Py_DECREF(res);
        errno = errnum;
        return -2;
    }
    n = PyNumber_AsSsize_t(res, PyExc_ValueError);
    Py_DECREF(res);
    if (n < 0 || n > len) {
        PyErr_Format(PyExc_IOError,
                     "raw write() returned invalid length %zd "
                     "(should have been between 0 and %zd)", n, len);
        return -1;
    }
    if (n > 0 && self->abs_pos != -1)
        self->abs_pos += n;
    return n;
}

/* `restore_pos` is 1 if we need to restore the raw stream position at
   the end, 0 otherwise. */
static PyObject *
_bufferedwriter_flush_unlocked(buffered *self)
{
    Py_ssize_t written = 0;
    Py_off_t n, rewind;

    if (!VALID_WRITE_BUFFER(self) || self->write_pos == self->write_end)
        goto end;
    /* First, rewind */
    rewind = RAW_OFFSET(self) + (self->pos - self->write_pos);
    if (rewind != 0) {
        n = _buffered_raw_seek(self, -rewind, 1);
        if (n < 0) {
            goto error;
        }
        self->raw_pos -= rewind;
    }
    while (self->write_pos < self->write_end) {
        n = _bufferedwriter_raw_write(self,
            self->buffer + self->write_pos,
            Py_SAFE_DOWNCAST(self->write_end - self->write_pos,
                             Py_off_t, Py_ssize_t));
        if (n == -1) {
            goto error;
        }
        else if (n == -2) {
            _set_BlockingIOError("write could not complete without blocking",
                                 0);
            goto error;
        }
        self->write_pos += n;
        self->raw_pos = self->write_pos;
        written += Py_SAFE_DOWNCAST(n, Py_off_t, Py_ssize_t);
        /* Partial writes can return successfully when interrupted by a
           signal (see write(2)).  We must run signal handlers before
           blocking another time, possibly indefinitely. */
        if (PyErr_CheckSignals() < 0)
            goto error;
    }

    _bufferedwriter_reset_buf(self);

end:
    Py_RETURN_NONE;

error:
    return NULL;
}

static PyObject *
bufferedwriter_write(buffered *self, PyObject *args)
{
    PyObject *res = NULL;
    Py_buffer buf;
    Py_ssize_t written, avail, remaining;
    Py_off_t offset;

    CHECK_INITIALIZED(self)
    if (!PyArg_ParseTuple(args, "y*:write", &buf)) {
        return NULL;
    }

    if (IS_CLOSED(self)) {
        PyErr_SetString(PyExc_ValueError, "write to closed file");
        PyBuffer_Release(&buf);
        return NULL;
    }

    if (!ENTER_BUFFERED(self)) {
        PyBuffer_Release(&buf);
        return NULL;
    }

    /* Fast path: the data to write can be fully buffered. */
    if (!VALID_READ_BUFFER(self) && !VALID_WRITE_BUFFER(self)) {
        self->pos = 0;
        self->raw_pos = 0;
    }
    avail = Py_SAFE_DOWNCAST(self->buffer_size - self->pos, Py_off_t, Py_ssize_t);
    if (buf.len <= avail) {
        memcpy(self->buffer + self->pos, buf.buf, buf.len);
        if (!VALID_WRITE_BUFFER(self) || self->write_pos > self->pos) {
            self->write_pos = self->pos;
        }
        ADJUST_POSITION(self, self->pos + buf.len);
        if (self->pos > self->write_end)
            self->write_end = self->pos;
        written = buf.len;
        goto end;
    }

    /* First write the current buffer */
    res = _bufferedwriter_flush_unlocked(self);
    if (res == NULL) {
        Py_ssize_t *w = _buffered_check_blocking_error();
        if (w == NULL)
            goto error;
        if (self->readable)
            _bufferedreader_reset_buf(self);
        /* Make some place by shifting the buffer. */
        assert(VALID_WRITE_BUFFER(self));
        memmove(self->buffer, self->buffer + self->write_pos,
                Py_SAFE_DOWNCAST(self->write_end - self->write_pos,
                                 Py_off_t, Py_ssize_t));
        self->write_end -= self->write_pos;
        self->raw_pos -= self->write_pos;
        self->pos -= self->write_pos;
        self->write_pos = 0;
        avail = Py_SAFE_DOWNCAST(self->buffer_size - self->write_end,
                                 Py_off_t, Py_ssize_t);
        if (buf.len <= avail) {
            /* Everything can be buffered */
            PyErr_Clear();
            memcpy(self->buffer + self->write_end, buf.buf, buf.len);
            self->write_end += buf.len;
            self->pos += buf.len;
            written = buf.len;
            goto end;
        }
        /* Buffer as much as possible. */
        memcpy(self->buffer + self->write_end, buf.buf, avail);
        self->write_end += avail;
        self->pos += avail;
        /* XXX Modifying the existing exception e using the pointer w
           will change e.characters_written but not e.args[2].
           Therefore we just replace with a new error. */
        _set_BlockingIOError("write could not complete without blocking",
                             avail);
        goto error;
    }
    Py_CLEAR(res);

    /* Adjust the raw stream position if it is away from the logical stream
       position. This happens if the read buffer has been filled but not
       modified (and therefore _bufferedwriter_flush_unlocked() didn't rewind
       the raw stream by itself).
       Fixes issue #6629.
    */
    offset = RAW_OFFSET(self);
    if (offset != 0) {
        if (_buffered_raw_seek(self, -offset, 1) < 0)
            goto error;
        self->raw_pos -= offset;
    }

    /* Then write buf itself. At this point the buffer has been emptied. */
    remaining = buf.len;
    written = 0;
    while (remaining > self->buffer_size) {
        Py_ssize_t n = _bufferedwriter_raw_write(
            self, (char *) buf.buf + written, buf.len - written);
        if (n == -1) {
            goto error;
        } else if (n == -2) {
            /* Write failed because raw file is non-blocking */
            if (remaining > self->buffer_size) {
                /* Can't buffer everything, still buffer as much as possible */
                memcpy(self->buffer,
                       (char *) buf.buf + written, self->buffer_size);
                self->raw_pos = 0;
                ADJUST_POSITION(self, self->buffer_size);
                self->write_end = self->buffer_size;
                written += self->buffer_size;
                _set_BlockingIOError("write could not complete without "
                                     "blocking", written);
                goto error;
            }
            PyErr_Clear();
            break;
        }
        written += n;
        remaining -= n;
        /* Partial writes can return successfully when interrupted by a
           signal (see write(2)).  We must run signal handlers before
           blocking another time, possibly indefinitely. */
        if (PyErr_CheckSignals() < 0)
            goto error;
    }
    if (self->readable)
        _bufferedreader_reset_buf(self);
    if (remaining > 0) {
        memcpy(self->buffer, (char *) buf.buf + written, remaining);
        written += remaining;
    }
    self->write_pos = 0;
    /* TODO: sanity check (remaining >= 0) */
    self->write_end = remaining;
    ADJUST_POSITION(self, remaining);
    self->raw_pos = 0;

end:
    res = PyLong_FromSsize_t(written);

error:
    LEAVE_BUFFERED(self)
    PyBuffer_Release(&buf);
    return res;
}

static PyMethodDef bufferedwriter_methods[] = {
    /* BufferedIOMixin methods */
    {"close", (PyCFunction)buffered_close, METH_NOARGS},
    {"detach", (PyCFunction)buffered_detach, METH_NOARGS},
    {"seekable", (PyCFunction)buffered_seekable, METH_NOARGS},
    {"readable", (PyCFunction)buffered_readable, METH_NOARGS},
    {"writable", (PyCFunction)buffered_writable, METH_NOARGS},
    {"fileno", (PyCFunction)buffered_fileno, METH_NOARGS},
    {"isatty", (PyCFunction)buffered_isatty, METH_NOARGS},
    {"_dealloc_warn", (PyCFunction)buffered_dealloc_warn, METH_O},
    {"__getstate__", (PyCFunction)buffered_getstate, METH_NOARGS},

    {"write", (PyCFunction)bufferedwriter_write, METH_VARARGS},
    {"truncate", (PyCFunction)buffered_truncate, METH_VARARGS},
    {"flush", (PyCFunction)buffered_flush, METH_NOARGS},
    {"seek", (PyCFunction)buffered_seek, METH_VARARGS},
    {"tell", (PyCFunction)buffered_tell, METH_NOARGS},
    {"__sizeof__", (PyCFunction)buffered_sizeof, METH_NOARGS},
    {NULL, NULL}
};

static PyMemberDef bufferedwriter_members[] = {
    {"raw", T_OBJECT, offsetof(buffered, raw), READONLY},
    {NULL}
};

static PyGetSetDef bufferedwriter_getset[] = {
    {"closed", (getter)buffered_closed_get, NULL, NULL},
    {"name", (getter)buffered_name_get, NULL, NULL},
    {"mode", (getter)buffered_mode_get, NULL, NULL},
    {NULL}
};


PyTypeObject PyBufferedWriter_Type = {
    PyVarObject_HEAD_INIT(NULL, 0)
    "_io.BufferedWriter",       /*tp_name*/
    sizeof(buffered),           /*tp_basicsize*/
    0,                          /*tp_itemsize*/
    (destructor)buffered_dealloc,     /*tp_dealloc*/
    0,                          /*tp_print*/
    0,                          /*tp_getattr*/
    0,                          /*tp_setattr*/
    0,                          /*tp_compare */
    (reprfunc)buffered_repr,    /*tp_repr*/
    0,                          /*tp_as_number*/
    0,                          /*tp_as_sequence*/
    0,                          /*tp_as_mapping*/
    0,                          /*tp_hash */
    0,                          /*tp_call*/
    0,                          /*tp_str*/
    0,                          /*tp_getattro*/
    0,                          /*tp_setattro*/
    0,                          /*tp_as_buffer*/
    Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE
        | Py_TPFLAGS_HAVE_GC,   /*tp_flags*/
    bufferedwriter_doc,         /* tp_doc */
    (traverseproc)buffered_traverse, /* tp_traverse */
    (inquiry)buffered_clear,    /* tp_clear */
    0,                          /* tp_richcompare */
    offsetof(buffered, weakreflist), /*tp_weaklistoffset*/
    0,                          /* tp_iter */
    0,                          /* tp_iternext */
    bufferedwriter_methods,     /* tp_methods */
    bufferedwriter_members,     /* tp_members */
    bufferedwriter_getset,      /* tp_getset */
    0,                          /* tp_base */
    0,                          /* tp_dict */
    0,                          /* tp_descr_get */
    0,                          /* tp_descr_set */
    offsetof(buffered, dict),   /* tp_dictoffset */
    (initproc)bufferedwriter_init, /* tp_init */
    0,                          /* tp_alloc */
    PyType_GenericNew,          /* tp_new */
};



/*
 * BufferedRWPair
 */

PyDoc_STRVAR(bufferedrwpair_doc,
    "A buffered reader and writer object together.\n"
    "\n"
    "A buffered reader object and buffered writer object put together to\n"
    "form a sequential IO object that can read and write. This is typically\n"
    "used with a socket or two-way pipe.\n"
    "\n"
    "reader and writer are RawIOBase objects that are readable and\n"
    "writeable respectively. If the buffer_size is omitted it defaults to\n"
    "DEFAULT_BUFFER_SIZE.\n"
    );

/* XXX The usefulness of this (compared to having two separate IO objects) is
 * questionable.
 */

typedef struct {
    PyObject_HEAD
    buffered *reader;
    buffered *writer;
    PyObject *dict;
    PyObject *weakreflist;
} rwpair;

static int
bufferedrwpair_init(rwpair *self, PyObject *args, PyObject *kwds)
{
    PyObject *reader, *writer;
    Py_ssize_t buffer_size = DEFAULT_BUFFER_SIZE;

    if (!PyArg_ParseTuple(args, "OO|n:BufferedRWPair", &reader, &writer,
                          &buffer_size)) {
        return -1;
    }

    if (_PyIOBase_check_readable(reader, Py_True) == NULL)
        return -1;
    if (_PyIOBase_check_writable(writer, Py_True) == NULL)
        return -1;

    self->reader = (buffered *) PyObject_CallFunction(
            (PyObject *) &PyBufferedReader_Type, "On", reader, buffer_size);
    if (self->reader == NULL)
        return -1;

    self->writer = (buffered *) PyObject_CallFunction(
            (PyObject *) &PyBufferedWriter_Type, "On", writer, buffer_size);
    if (self->writer == NULL) {
        Py_CLEAR(self->reader);
        return -1;
    }

    return 0;
}

static int
bufferedrwpair_traverse(rwpair *self, visitproc visit, void *arg)
{
    Py_VISIT(self->dict);
    return 0;
}

static int
bufferedrwpair_clear(rwpair *self)
{
    Py_CLEAR(self->reader);
    Py_CLEAR(self->writer);
    Py_CLEAR(self->dict);
    return 0;
}

static void
bufferedrwpair_dealloc(rwpair *self)
{
    _PyObject_GC_UNTRACK(self);
    Py_CLEAR(self->reader);
    Py_CLEAR(self->writer);
    Py_CLEAR(self->dict);
    Py_TYPE(self)->tp_free((PyObject *) self);
}

static PyObject *
_forward_call(buffered *self, _Py_Identifier *name, PyObject *args)
{
    PyObject *func = _PyObject_GetAttrId((PyObject *)self, name);
    PyObject *ret;

    if (func == NULL) {
        PyErr_SetString(PyExc_AttributeError, name->string);
        return NULL;
    }

    ret = PyObject_CallObject(func, args);
    Py_DECREF(func);
    return ret;
}

static PyObject *
bufferedrwpair_read(rwpair *self, PyObject *args)
{
    return _forward_call(self->reader, &PyId_read, args);
}

static PyObject *
bufferedrwpair_peek(rwpair *self, PyObject *args)
{
    return _forward_call(self->reader, &PyId_peek, args);
}

static PyObject *
bufferedrwpair_read1(rwpair *self, PyObject *args)
{
    return _forward_call(self->reader, &PyId_read1, args);
}

static PyObject *
bufferedrwpair_readinto(rwpair *self, PyObject *args)
{
    return _forward_call(self->reader, &PyId_readinto, args);
}

static PyObject *
bufferedrwpair_write(rwpair *self, PyObject *args)
{
    return _forward_call(self->writer, &PyId_write, args);
}

static PyObject *
bufferedrwpair_flush(rwpair *self, PyObject *args)
{
    return _forward_call(self->writer, &PyId_flush, args);
}

static PyObject *
bufferedrwpair_readable(rwpair *self, PyObject *args)
{
    return _forward_call(self->reader, &PyId_readable, args);
}

static PyObject *
bufferedrwpair_writable(rwpair *self, PyObject *args)
{
    return _forward_call(self->writer, &PyId_writable, args);
}

static PyObject *
bufferedrwpair_close(rwpair *self, PyObject *args)
{
    PyObject *ret = _forward_call(self->writer, &PyId_close, args);
    if (ret == NULL)
        return NULL;
    Py_DECREF(ret);

    return _forward_call(self->reader, &PyId_close, args);
}

static PyObject *
bufferedrwpair_isatty(rwpair *self, PyObject *args)
{
    PyObject *ret = _forward_call(self->writer, &PyId_isatty, args);

    if (ret != Py_False) {
        /* either True or exception */
        return ret;
    }
    Py_DECREF(ret);

    return _forward_call(self->reader, &PyId_isatty, args);
}

static PyObject *
bufferedrwpair_closed_get(rwpair *self, void *context)
{
    if (self->writer == NULL) {
        PyErr_SetString(PyExc_RuntimeError,
                "the BufferedRWPair object is being garbage-collected");
        return NULL;
    }
    return PyObject_GetAttr((PyObject *) self->writer, _PyIO_str_closed);
}

static PyMethodDef bufferedrwpair_methods[] = {
    {"read", (PyCFunction)bufferedrwpair_read, METH_VARARGS},
    {"peek", (PyCFunction)bufferedrwpair_peek, METH_VARARGS},
    {"read1", (PyCFunction)bufferedrwpair_read1, METH_VARARGS},
    {"readinto", (PyCFunction)bufferedrwpair_readinto, METH_VARARGS},

    {"write", (PyCFunction)bufferedrwpair_write, METH_VARARGS},
    {"flush", (PyCFunction)bufferedrwpair_flush, METH_NOARGS},

    {"readable", (PyCFunction)bufferedrwpair_readable, METH_NOARGS},
    {"writable", (PyCFunction)bufferedrwpair_writable, METH_NOARGS},

    {"close", (PyCFunction)bufferedrwpair_close, METH_NOARGS},
    {"isatty", (PyCFunction)bufferedrwpair_isatty, METH_NOARGS},

    {"__getstate__", (PyCFunction)buffered_getstate, METH_NOARGS},

    {NULL, NULL}
};

static PyGetSetDef bufferedrwpair_getset[] = {
    {"closed", (getter)bufferedrwpair_closed_get, NULL, NULL},
    {NULL}
};

PyTypeObject PyBufferedRWPair_Type = {
    PyVarObject_HEAD_INIT(NULL, 0)
    "_io.BufferedRWPair",       /*tp_name*/
    sizeof(rwpair),            /*tp_basicsize*/
    0,                          /*tp_itemsize*/
    (destructor)bufferedrwpair_dealloc,     /*tp_dealloc*/
    0,                          /*tp_print*/
    0,                          /*tp_getattr*/
    0,                          /*tp_setattr*/
    0,                          /*tp_compare */
    0,                          /*tp_repr*/
    0,                          /*tp_as_number*/
    0,                          /*tp_as_sequence*/
    0,                          /*tp_as_mapping*/
    0,                          /*tp_hash */
    0,                          /*tp_call*/
    0,                          /*tp_str*/
    0,                          /*tp_getattro*/
    0,                          /*tp_setattro*/
    0,                          /*tp_as_buffer*/
    Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE
        | Py_TPFLAGS_HAVE_GC,   /* tp_flags */
    bufferedrwpair_doc,         /* tp_doc */
    (traverseproc)bufferedrwpair_traverse, /* tp_traverse */
    (inquiry)bufferedrwpair_clear, /* tp_clear */
    0,                          /* tp_richcompare */
    offsetof(rwpair, weakreflist), /*tp_weaklistoffset*/
    0,                          /* tp_iter */
    0,                          /* tp_iternext */
    bufferedrwpair_methods,     /* tp_methods */
    0,                          /* tp_members */
    bufferedrwpair_getset,      /* tp_getset */
    0,                          /* tp_base */
    0,                          /* tp_dict */
    0,                          /* tp_descr_get */
    0,                          /* tp_descr_set */
    offsetof(rwpair, dict),     /* tp_dictoffset */
    (initproc)bufferedrwpair_init, /* tp_init */
    0,                          /* tp_alloc */
    PyType_GenericNew,          /* tp_new */
};



/*
 * BufferedRandom
 */

PyDoc_STRVAR(bufferedrandom_doc,
    "A buffered interface to random access streams.\n"
    "\n"
    "The constructor creates a reader and writer for a seekable stream,\n"
    "raw, given in the first argument. If the buffer_size is omitted it\n"
    "defaults to DEFAULT_BUFFER_SIZE.\n"
    );

static int
bufferedrandom_init(buffered *self, PyObject *args, PyObject *kwds)
{
    char *kwlist[] = {"raw", "buffer_size", NULL};
    Py_ssize_t buffer_size = DEFAULT_BUFFER_SIZE;
    PyObject *raw;

    self->ok = 0;
    self->detached = 0;

    if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|n:BufferedRandom", kwlist,
                                     &raw, &buffer_size)) {
        return -1;
    }

    if (_PyIOBase_check_seekable(raw, Py_True) == NULL)
        return -1;
    if (_PyIOBase_check_readable(raw, Py_True) == NULL)
        return -1;
    if (_PyIOBase_check_writable(raw, Py_True) == NULL)
        return -1;

    Py_CLEAR(self->raw);
    Py_INCREF(raw);
    self->raw = raw;
    self->buffer_size = buffer_size;
    self->readable = 1;
    self->writable = 1;

    if (_buffered_init(self) < 0)
        return -1;
    _bufferedreader_reset_buf(self);
    _bufferedwriter_reset_buf(self);
    self->pos = 0;

    self->fast_closed_checks = (Py_TYPE(self) == &PyBufferedRandom_Type &&
                                Py_TYPE(raw) == &PyFileIO_Type);

    self->ok = 1;
    return 0;
}

static PyMethodDef bufferedrandom_methods[] = {
    /* BufferedIOMixin methods */
    {"close", (PyCFunction)buffered_close, METH_NOARGS},
    {"detach", (PyCFunction)buffered_detach, METH_NOARGS},
    {"seekable", (PyCFunction)buffered_seekable, METH_NOARGS},
    {"readable", (PyCFunction)buffered_readable, METH_NOARGS},
    {"writable", (PyCFunction)buffered_writable, METH_NOARGS},
    {"fileno", (PyCFunction)buffered_fileno, METH_NOARGS},
    {"isatty", (PyCFunction)buffered_isatty, METH_NOARGS},
    {"_dealloc_warn", (PyCFunction)buffered_dealloc_warn, METH_O},
    {"__getstate__", (PyCFunction)buffered_getstate, METH_NOARGS},

    {"flush", (PyCFunction)buffered_flush, METH_NOARGS},

    {"seek", (PyCFunction)buffered_seek, METH_VARARGS},
    {"tell", (PyCFunction)buffered_tell, METH_NOARGS},
    {"truncate", (PyCFunction)buffered_truncate, METH_VARARGS},
    {"read", (PyCFunction)buffered_read, METH_VARARGS},
    {"read1", (PyCFunction)buffered_read1, METH_VARARGS},
    {"readinto", (PyCFunction)buffered_readinto, METH_VARARGS},
    {"readline", (PyCFunction)buffered_readline, METH_VARARGS},
    {"peek", (PyCFunction)buffered_peek, METH_VARARGS},
    {"write", (PyCFunction)bufferedwriter_write, METH_VARARGS},
    {"__sizeof__", (PyCFunction)buffered_sizeof, METH_NOARGS},
    {NULL, NULL}
};

static PyMemberDef bufferedrandom_members[] = {
    {"raw", T_OBJECT, offsetof(buffered, raw), READONLY},
    {NULL}
};

static PyGetSetDef bufferedrandom_getset[] = {
    {"closed", (getter)buffered_closed_get, NULL, NULL},
    {"name", (getter)buffered_name_get, NULL, NULL},
    {"mode", (getter)buffered_mode_get, NULL, NULL},
    {NULL}
};


PyTypeObject PyBufferedRandom_Type = {
    PyVarObject_HEAD_INIT(NULL, 0)
    "_io.BufferedRandom",       /*tp_name*/
    sizeof(buffered),           /*tp_basicsize*/
    0,                          /*tp_itemsize*/
    (destructor)buffered_dealloc,     /*tp_dealloc*/
    0,                          /*tp_print*/
    0,                          /*tp_getattr*/
    0,                          /*tp_setattr*/
    0,                          /*tp_compare */
    (reprfunc)buffered_repr,    /*tp_repr*/
    0,                          /*tp_as_number*/
    0,                          /*tp_as_sequence*/
    0,                          /*tp_as_mapping*/
    0,                          /*tp_hash */
    0,                          /*tp_call*/
    0,                          /*tp_str*/
    0,                          /*tp_getattro*/
    0,                          /*tp_setattro*/
    0,                          /*tp_as_buffer*/
    Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE
        | Py_TPFLAGS_HAVE_GC,   /*tp_flags*/
    bufferedrandom_doc,         /* tp_doc */
    (traverseproc)buffered_traverse, /* tp_traverse */
    (inquiry)buffered_clear,    /* tp_clear */
    0,                          /* tp_richcompare */
    offsetof(buffered, weakreflist), /*tp_weaklistoffset*/
    0,                          /* tp_iter */
    (iternextfunc)buffered_iternext, /* tp_iternext */
    bufferedrandom_methods,     /* tp_methods */
    bufferedrandom_members,     /* tp_members */
    bufferedrandom_getset,      /* tp_getset */
    0,                          /* tp_base */
    0,                          /*tp_dict*/
    0,                          /* tp_descr_get */
    0,                          /* tp_descr_set */
    offsetof(buffered, dict), /*tp_dictoffset*/
    (initproc)bufferedrandom_init, /* tp_init */
    0,                          /* tp_alloc */
    PyType_GenericNew,          /* tp_new */
};
