File tree Expand file tree Collapse file tree 2 files changed +42
-4
lines changed Expand file tree Collapse file tree 2 files changed +42
-4
lines changed Original file line number Diff line number Diff line change @@ -10,6 +10,9 @@ Release date: TBA
10
10
Core and Builtins
11
11
-----------------
12
12
13
+ - Issue #21377: PyBytes_Concat() now tries to concatenate in-place when the
14
+ first argument has a reference count of 1. Patch by Nikolaus Rath.
15
+
13
16
- Issue #20355: -W command line options now have higher priority than the
14
17
PYTHONWARNINGS environment variable. Patch by Arfrever.
15
18
Original file line number Diff line number Diff line change @@ -2781,17 +2781,52 @@ PyTypeObject PyBytes_Type = {
2781
2781
void
2782
2782
PyBytes_Concat (PyObject * * pv , PyObject * w )
2783
2783
{
2784
- PyObject * v ;
2785
2784
assert (pv != NULL );
2786
2785
if (* pv == NULL )
2787
2786
return ;
2788
2787
if (w == NULL ) {
2789
2788
Py_CLEAR (* pv );
2790
2789
return ;
2791
2790
}
2792
- v = bytes_concat (* pv , w );
2793
- Py_DECREF (* pv );
2794
- * pv = v ;
2791
+
2792
+ if (Py_REFCNT (* pv ) == 1 && PyBytes_CheckExact (* pv )) {
2793
+ /* Only one reference, so we can resize in place */
2794
+ size_t oldsize ;
2795
+ Py_buffer wb ;
2796
+
2797
+ wb .len = -1 ;
2798
+ if (_getbuffer (w , & wb ) < 0 ) {
2799
+ PyErr_Format (PyExc_TypeError , "can't concat %.100s to %.100s" ,
2800
+ Py_TYPE (w )-> tp_name , Py_TYPE (* pv )-> tp_name );
2801
+ Py_CLEAR (* pv );
2802
+ return ;
2803
+ }
2804
+
2805
+ oldsize = PyBytes_GET_SIZE (* pv );
2806
+ if (oldsize > PY_SSIZE_T_MAX - wb .len ) {
2807
+ PyErr_NoMemory ();
2808
+ goto error ;
2809
+ }
2810
+ if (_PyBytes_Resize (pv , oldsize + wb .len ) < 0 )
2811
+ goto error ;
2812
+
2813
+ memcpy (PyBytes_AS_STRING (* pv ) + oldsize , wb .buf , wb .len );
2814
+ PyBuffer_Release (& wb );
2815
+ return ;
2816
+
2817
+ error :
2818
+ PyBuffer_Release (& wb );
2819
+ Py_CLEAR (* pv );
2820
+ return ;
2821
+ }
2822
+
2823
+ else {
2824
+ /* Multiple references, need to create new object */
2825
+ PyObject * v ;
2826
+ v = bytes_concat (* pv , w );
2827
+ Py_DECREF (* pv );
2828
+ * pv = v ;
2829
+ }
2795
2830
}
2796
2831
2797
2832
void
You can’t perform that action at this time.
0 commit comments