[Python-checkins] cpython: Issue #21377: PyBytes_Concat() now tries to concatenate in-place when the first
antoine.pitrou
python-checkins at python.org
Thu May 1 14:36:29 CEST 2014
http://hg.python.org/cpython/rev/4ed1b6c7e2f3
changeset: 90530:4ed1b6c7e2f3
user: Antoine Pitrou <solipsis at pitrou.net>
date: Thu May 01 14:36:20 2014 +0200
summary:
Issue #21377: PyBytes_Concat() now tries to concatenate in-place when the first argument has a reference count of 1.
Patch by Nikolaus Rath.
files:
Misc/NEWS | 3 ++
Objects/bytesobject.c | 43 ++++++++++++++++++++++++++++--
2 files changed, 42 insertions(+), 4 deletions(-)
diff --git a/Misc/NEWS b/Misc/NEWS
--- a/Misc/NEWS
+++ b/Misc/NEWS
@@ -10,6 +10,9 @@
Core and Builtins
-----------------
+- Issue #21377: PyBytes_Concat() now tries to concatenate in-place when the
+ first argument has a reference count of 1. Patch by Nikolaus Rath.
+
- Issue #20355: -W command line options now have higher priority than the
PYTHONWARNINGS environment variable. Patch by Arfrever.
diff --git a/Objects/bytesobject.c b/Objects/bytesobject.c
--- a/Objects/bytesobject.c
+++ b/Objects/bytesobject.c
@@ -2781,7 +2781,6 @@
void
PyBytes_Concat(PyObject **pv, PyObject *w)
{
- PyObject *v;
assert(pv != NULL);
if (*pv == NULL)
return;
@@ -2789,9 +2788,45 @@
Py_CLEAR(*pv);
return;
}
- v = bytes_concat(*pv, w);
- Py_DECREF(*pv);
- *pv = v;
+
+ if (Py_REFCNT(*pv) == 1 && PyBytes_CheckExact(*pv)) {
+ /* Only one reference, so we can resize in place */
+ size_t oldsize;
+ Py_buffer wb;
+
+ wb.len = -1;
+ if (_getbuffer(w, &wb) < 0) {
+ PyErr_Format(PyExc_TypeError, "can't concat %.100s to %.100s",
+ Py_TYPE(w)->tp_name, Py_TYPE(*pv)->tp_name);
+ Py_CLEAR(*pv);
+ return;
+ }
+
+ oldsize = PyBytes_GET_SIZE(*pv);
+ if (oldsize > PY_SSIZE_T_MAX - wb.len) {
+ PyErr_NoMemory();
+ goto error;
+ }
+ if (_PyBytes_Resize(pv, oldsize + wb.len) < 0)
+ goto error;
+
+ memcpy(PyBytes_AS_STRING(*pv) + oldsize, wb.buf, wb.len);
+ PyBuffer_Release(&wb);
+ return;
+
+ error:
+ PyBuffer_Release(&wb);
+ Py_CLEAR(*pv);
+ return;
+ }
+
+ else {
+ /* Multiple references, need to create new object */
+ PyObject *v;
+ v = bytes_concat(*pv, w);
+ Py_DECREF(*pv);
+ *pv = v;
+ }
}
void
--
Repository URL: http://hg.python.org/cpython
More information about the Python-checkins
mailing list