Skip to content

Commit 40ef4e1

Browse files
committed
Add PyBytesWriter_GrowAndUpdatePointer()
1 parent 457e21a commit 40ef4e1

File tree

4 files changed

+54
-34
lines changed

4 files changed

+54
-34
lines changed

Include/cpython/bytesobject.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,3 +84,10 @@ PyAPI_FUNC(void*) PyBytesWriter_ResizeAndUpdatePointer(
8484
PyBytesWriter *writer,
8585
Py_ssize_t size,
8686
void *data);
87+
PyAPI_FUNC(int) PyBytesWriter_Grow(
88+
PyBytesWriter *writer,
89+
Py_ssize_t size);
90+
PyAPI_FUNC(void*) PyBytesWriter_GrowAndUpdatePointer(
91+
PyBytesWriter *writer,
92+
Py_ssize_t size,
93+
void *data);

Modules/_pickle.c

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2631,8 +2631,7 @@ raw_unicode_escape(PyObject *obj)
26312631
/* Map 32-bit characters to '\Uxxxxxxxx' */
26322632
if (ch >= 0x10000) {
26332633
/* -1: subtract 1 preallocated byte */
2634-
alloc += 10-1;
2635-
p = PyBytesWriter_ResizeAndUpdatePointer(writer, alloc, p);
2634+
p = PyBytesWriter_GrowAndUpdatePointer(writer, 10-1, p);
26362635
if (p == NULL) {
26372636
goto error;
26382637
}
@@ -2654,8 +2653,7 @@ raw_unicode_escape(PyObject *obj)
26542653
ch == 0x1a)
26552654
{
26562655
/* -1: subtract 1 preallocated byte */
2657-
alloc += 6-1;
2658-
p = PyBytesWriter_ResizeAndUpdatePointer(writer, alloc, p);
2656+
p = PyBytesWriter_GrowAndUpdatePointer(writer, 6-1, p);
26592657
if (p == NULL) {
26602658
goto error;
26612659
}

Objects/bytesobject.c

Lines changed: 39 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -221,8 +221,7 @@ bytes_fromformat(PyBytesWriter *writer, Py_ssize_t writer_pos,
221221
#define WRITE_BYTES_LEN(str, len_expr) \
222222
do { \
223223
size_t len = (len_expr); \
224-
alloc += len; \
225-
s = PyBytesWriter_ResizeAndUpdatePointer(writer, alloc, s); \
224+
s = PyBytesWriter_GrowAndUpdatePointer(writer, len, s); \
226225
if (s == NULL) { \
227226
goto error; \
228227
} \
@@ -459,8 +458,7 @@ formatfloat(PyObject *v, int flags, int prec, int type,
459458

460459
len = strlen(p);
461460
if (writer != NULL) {
462-
Py_ssize_t resize = PyBytesWriter_GetSize(writer) + len;
463-
str = PyBytesWriter_ResizeAndUpdatePointer(writer, resize, str);
461+
str = PyBytesWriter_GrowAndUpdatePointer(writer, len, str);
464462
if (str == NULL) {
465463
PyMem_Free(p);
466464
return NULL;
@@ -982,8 +980,7 @@ _PyBytes_FormatEx(const char *format, Py_ssize_t format_len,
982980
alloc++;
983981
/* 2: size preallocated for %s */
984982
if (alloc > 2) {
985-
Py_ssize_t resize = PyBytesWriter_GetSize(writer) + alloc - 2;
986-
res = PyBytesWriter_ResizeAndUpdatePointer(writer, resize, res);
983+
res = PyBytesWriter_GrowAndUpdatePointer(writer, alloc - 2, res);
987984
if (res == NULL) {
988985
goto error;
989986
}
@@ -3971,41 +3968,50 @@ PyBytesWriter_Resize(PyBytesWriter *writer, Py_ssize_t size)
39713968

39723969

39733970
int
3974-
PyBytesWriter_WriteBytes(PyBytesWriter *writer,
3975-
const void *bytes, Py_ssize_t size)
3971+
PyBytesWriter_Grow(PyBytesWriter *writer, Py_ssize_t size)
39763972
{
39773973
if (size < 0) {
3978-
size = strlen(bytes);
3974+
PyErr_SetString(PyExc_ValueError, "size must be >= 0");
3975+
return -1;
39793976
}
39803977

3981-
Py_ssize_t pos = writer->size;
3982-
if (size > PY_SSIZE_T_MAX - pos) {
3978+
if (size > PY_SSIZE_T_MAX - writer->size) {
39833979
PyErr_NoMemory();
39843980
return -1;
39853981
}
3986-
Py_ssize_t total = pos + size;
3982+
size = writer->size + size;
39873983

3988-
if (PyBytesWriter_Resize(writer, total) < 0) {
3984+
if (byteswriter_resize(writer, size, 1) < 0) {
39893985
return -1;
39903986
}
3991-
char *buf = byteswriter_data(writer);
3992-
memcpy(buf + pos, bytes, size);
3987+
writer->size = size;
39933988
return 0;
39943989
}
39953990

39963991

39973992
int
3998-
PyBytesWriter_Format(PyBytesWriter *writer, const char *format, ...)
3993+
PyBytesWriter_WriteBytes(PyBytesWriter *writer,
3994+
const void *bytes, Py_ssize_t size)
39993995
{
3996+
if (size < 0) {
3997+
size = strlen(bytes);
3998+
}
3999+
40004000
Py_ssize_t pos = writer->size;
4001-
Py_ssize_t format_len = strlen(format);
4002-
if (format_len > PY_SSIZE_T_MAX - pos) {
4003-
PyErr_NoMemory();
4001+
if (PyBytesWriter_Grow(writer, size) < 0) {
40044002
return -1;
40054003
}
4006-
Py_ssize_t alloc = pos + format_len;
4004+
char *buf = byteswriter_data(writer);
4005+
memcpy(buf + pos, bytes, size);
4006+
return 0;
4007+
}
4008+
40074009

4008-
if (PyBytesWriter_Resize(writer, alloc) < 0) {
4010+
int
4011+
PyBytesWriter_Format(PyBytesWriter *writer, const char *format, ...)
4012+
{
4013+
Py_ssize_t pos = writer->size;
4014+
if (PyBytesWriter_Grow(writer, strlen(format)) < 0) {
40094015
return -1;
40104016
}
40114017

@@ -4029,3 +4035,15 @@ PyBytesWriter_ResizeAndUpdatePointer(PyBytesWriter *writer, Py_ssize_t size,
40294035
}
40304036
return byteswriter_data(writer) + pos;
40314037
}
4038+
4039+
4040+
void*
4041+
PyBytesWriter_GrowAndUpdatePointer(PyBytesWriter *writer, Py_ssize_t size,
4042+
void *data)
4043+
{
4044+
Py_ssize_t pos = (char*)data - byteswriter_data(writer);
4045+
if (PyBytesWriter_Grow(writer, size) < 0) {
4046+
return NULL;
4047+
}
4048+
return byteswriter_data(writer) + pos;
4049+
}

Objects/longobject.c

Lines changed: 6 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2047,9 +2047,8 @@ pylong_int_to_decimal_string(PyObject *aa,
20472047
Py_ssize_t size = PyUnicode_GET_LENGTH(s);
20482048
const void *data = PyUnicode_DATA(s);
20492049
int kind = PyUnicode_KIND(s);
2050-
Py_ssize_t resize = PyBytesWriter_GetSize(bytes_writer) + size;
2051-
*bytes_str = PyBytesWriter_ResizeAndUpdatePointer(bytes_writer, resize,
2052-
*bytes_str);
2050+
*bytes_str = PyBytesWriter_GrowAndUpdatePointer(bytes_writer, size,
2051+
*bytes_str);
20532052
if (*bytes_str == NULL) {
20542053
goto error;
20552054
}
@@ -2212,9 +2211,8 @@ long_to_decimal_string_internal(PyObject *aa,
22122211
}
22132212
}
22142213
else if (bytes_writer) {
2215-
Py_ssize_t resize = PyBytesWriter_GetSize(bytes_writer) + strlen;
2216-
*bytes_str = PyBytesWriter_ResizeAndUpdatePointer(bytes_writer, resize,
2217-
*bytes_str);
2214+
*bytes_str = PyBytesWriter_GrowAndUpdatePointer(bytes_writer, strlen,
2215+
*bytes_str);
22182216
if (*bytes_str == NULL) {
22192217
Py_DECREF(scratch);
22202218
return -1;
@@ -2385,9 +2383,8 @@ long_format_binary(PyObject *aa, int base, int alternate,
23852383
return -1;
23862384
}
23872385
else if (bytes_writer) {
2388-
Py_ssize_t resize = PyBytesWriter_GetSize(bytes_writer) + sz;
2389-
*bytes_str = PyBytesWriter_ResizeAndUpdatePointer(bytes_writer, resize,
2390-
*bytes_str);
2386+
*bytes_str = PyBytesWriter_GrowAndUpdatePointer(bytes_writer, sz,
2387+
*bytes_str);
23912388
if (*bytes_str == NULL)
23922389
return -1;
23932390
}

0 commit comments

Comments
 (0)