@@ -1650,7 +1650,8 @@ state_reset(SRE_STATE* state)
16501650
16511651static void *
16521652getstring (PyObject * string , Py_ssize_t * p_length ,
1653- int * p_logical_charsize , int * p_charsize )
1653+ int * p_logical_charsize , int * p_charsize ,
1654+ Py_buffer * view )
16541655{
16551656 /* given a python object, return a data pointer, a length (in
16561657 characters), and a character size. return NULL if the object
@@ -1660,7 +1661,6 @@ getstring(PyObject* string, Py_ssize_t* p_length,
16601661 Py_ssize_t size , bytes ;
16611662 int charsize ;
16621663 void * ptr ;
1663- Py_buffer view ;
16641664
16651665 /* Unicode objects do not support the buffer API. So, get the data
16661666 directly instead. */
@@ -1675,26 +1675,21 @@ getstring(PyObject* string, Py_ssize_t* p_length,
16751675 }
16761676
16771677 /* get pointer to byte string buffer */
1678- view . len = -1 ;
1678+ view -> len = -1 ;
16791679 buffer = Py_TYPE (string )-> tp_as_buffer ;
16801680 if (!buffer || !buffer -> bf_getbuffer ||
1681- (* buffer -> bf_getbuffer )(string , & view , PyBUF_SIMPLE ) < 0 ) {
1681+ (* buffer -> bf_getbuffer )(string , view , PyBUF_SIMPLE ) < 0 ) {
16821682 PyErr_SetString (PyExc_TypeError , "expected string or buffer" );
16831683 return NULL ;
16841684 }
16851685
16861686 /* determine buffer size */
1687- bytes = view .len ;
1688- ptr = view .buf ;
1689-
1690- /* Release the buffer immediately --- possibly dangerous
1691- but doing something else would require some re-factoring
1692- */
1693- PyBuffer_Release (& view );
1687+ bytes = view -> len ;
1688+ ptr = view -> buf ;
16941689
16951690 if (bytes < 0 ) {
16961691 PyErr_SetString (PyExc_TypeError , "buffer has negative size" );
1697- return NULL ;
1692+ goto err ;
16981693 }
16991694
17001695 /* determine character size */
@@ -1704,7 +1699,7 @@ getstring(PyObject* string, Py_ssize_t* p_length,
17041699 charsize = 1 ;
17051700 else {
17061701 PyErr_SetString (PyExc_TypeError , "buffer size mismatch" );
1707- return NULL ;
1702+ goto err ;
17081703 }
17091704
17101705 * p_length = size ;
@@ -1714,8 +1709,13 @@ getstring(PyObject* string, Py_ssize_t* p_length,
17141709 if (ptr == NULL ) {
17151710 PyErr_SetString (PyExc_ValueError ,
17161711 "Buffer is NULL" );
1712+ goto err ;
17171713 }
17181714 return ptr ;
1715+ err :
1716+ PyBuffer_Release (view );
1717+ view -> buf = NULL ;
1718+ return NULL ;
17191719}
17201720
17211721LOCAL (PyObject * )
@@ -1733,20 +1733,21 @@ state_init(SRE_STATE* state, PatternObject* pattern, PyObject* string,
17331733 state -> lastmark = -1 ;
17341734 state -> lastindex = -1 ;
17351735
1736- ptr = getstring (string , & length , & logical_charsize , & charsize );
1736+ state -> buffer .buf = NULL ;
1737+ ptr = getstring (string , & length , & logical_charsize , & charsize , & state -> buffer );
17371738 if (!ptr )
1738- return NULL ;
1739+ goto err ;
17391740
1740- if (logical_charsize == 1 && pattern -> logical_charsize > 1 ) {
1741- PyErr_SetString (PyExc_TypeError ,
1741+ if (logical_charsize == 1 && pattern -> logical_charsize > 1 ) {
1742+ PyErr_SetString (PyExc_TypeError ,
17421743 "can't use a string pattern on a bytes-like object" );
1743- return NULL ;
1744- }
1745- if (logical_charsize > 1 && pattern -> logical_charsize == 1 ) {
1746- PyErr_SetString (PyExc_TypeError ,
1744+ goto err ;
1745+ }
1746+ if (logical_charsize > 1 && pattern -> logical_charsize == 1 ) {
1747+ PyErr_SetString (PyExc_TypeError ,
17471748 "can't use a bytes pattern on a string-like object" );
1748- return NULL ;
1749- }
1749+ goto err ;
1750+ }
17501751
17511752 /* adjust boundaries */
17521753 if (start < 0 )
@@ -1780,11 +1781,17 @@ state_init(SRE_STATE* state, PatternObject* pattern, PyObject* string,
17801781 state -> lower = sre_lower ;
17811782
17821783 return string ;
1784+ err :
1785+ if (state -> buffer .buf )
1786+ PyBuffer_Release (& state -> buffer );
1787+ return NULL ;
17831788}
17841789
17851790LOCAL (void )
17861791state_fini (SRE_STATE * state )
17871792{
1793+ if (state -> buffer .buf )
1794+ PyBuffer_Release (& state -> buffer );
17881795 Py_XDECREF (state -> string );
17891796 data_stack_dealloc (state );
17901797}
@@ -1846,6 +1853,8 @@ pattern_dealloc(PatternObject* self)
18461853{
18471854 if (self -> weakreflist != NULL )
18481855 PyObject_ClearWeakRefs ((PyObject * ) self );
1856+ if (self -> view .buf )
1857+ PyBuffer_Release (& self -> view );
18491858 Py_XDECREF (self -> pattern );
18501859 Py_XDECREF (self -> groupindex );
18511860 Py_XDECREF (self -> indexgroup );
@@ -2272,6 +2281,7 @@ pattern_subx(PatternObject* self, PyObject* ptemplate, PyObject* string,
22722281 Py_ssize_t i , b , e ;
22732282 int logical_charsize , charsize ;
22742283 int filter_is_callable ;
2284+ Py_buffer view ;
22752285
22762286 if (PyCallable_Check (ptemplate )) {
22772287 /* sub/subn takes either a function or a template */
@@ -2281,14 +2291,17 @@ pattern_subx(PatternObject* self, PyObject* ptemplate, PyObject* string,
22812291 } else {
22822292 /* if not callable, check if it's a literal string */
22832293 int literal ;
2284- ptr = getstring (ptemplate , & n , & logical_charsize , & charsize );
2294+ view .buf = NULL ;
2295+ ptr = getstring (ptemplate , & n , & logical_charsize , & charsize , & view );
22852296 b = charsize ;
22862297 if (ptr ) {
22872298 literal = sre_literal_template (b , ptr , n );
22882299 } else {
22892300 PyErr_Clear ();
22902301 literal = 0 ;
22912302 }
2303+ if (view .buf )
2304+ PyBuffer_Release (& view );
22922305 if (literal ) {
22932306 filter = ptemplate ;
22942307 Py_INCREF (filter );
@@ -2628,6 +2641,7 @@ _compile(PyObject* self_, PyObject* args)
26282641 Py_ssize_t groups = 0 ;
26292642 PyObject * groupindex = NULL ;
26302643 PyObject * indexgroup = NULL ;
2644+
26312645 if (!PyArg_ParseTuple (args , "OiO!|nOO" , & pattern , & flags ,
26322646 & PyList_Type , & code , & groups ,
26332647 & groupindex , & indexgroup ))
@@ -2642,6 +2656,7 @@ _compile(PyObject* self_, PyObject* args)
26422656 self -> pattern = NULL ;
26432657 self -> groupindex = NULL ;
26442658 self -> indexgroup = NULL ;
2659+ self -> view .buf = NULL ;
26452660
26462661 self -> codesize = n ;
26472662
@@ -2668,7 +2683,7 @@ _compile(PyObject* self_, PyObject* args)
26682683 else {
26692684 Py_ssize_t p_length ;
26702685 if (!getstring (pattern , & p_length , & self -> logical_charsize ,
2671- & self -> charsize )) {
2686+ & self -> charsize , & self -> view )) {
26722687 Py_DECREF (self );
26732688 return NULL ;
26742689 }
0 commit comments