blob: dae80d94245f6bd7cc3c5877f95dd5c418123e93 [file] [log] [blame]
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001/* PyByteArray (bytearray) implementation */
2
3#define PY_SSIZE_T_CLEAN
4#include "Python.h"
5#include "structmember.h"
6#include "bytes_methods.h"
Ethan Furmanb95b5612015-01-23 20:05:18 -08007#include "bytesobject.h"
Gregory P. Smith8cb65692015-04-25 23:22:26 +00008#include "pystrhex.h"
Christian Heimes2c9c7a52008-05-26 13:42:13 +00009
Martin v. Löwis7252a6e2014-07-27 16:25:09 +020010/*[clinic input]
11class bytearray "PyByteArrayObject *" "&PyByteArray_Type"
12[clinic start generated code]*/
13/*[clinic end generated code: output=da39a3ee5e6b4b0d input=5535b77c37a119e0]*/
14
Antoine Pitroufc8d6f42010-01-17 12:38:54 +000015char _PyByteArray_empty_string[] = "";
Christian Heimes2c9c7a52008-05-26 13:42:13 +000016
17void
18PyByteArray_Fini(void)
19{
Christian Heimes2c9c7a52008-05-26 13:42:13 +000020}
21
22int
23PyByteArray_Init(void)
24{
Christian Heimes2c9c7a52008-05-26 13:42:13 +000025 return 1;
26}
27
28/* end nullbytes support */
29
30/* Helpers */
31
32static int
33_getbytevalue(PyObject* arg, int *value)
34{
35 long face_value;
36
37 if (PyLong_Check(arg)) {
38 face_value = PyLong_AsLong(arg);
Georg Brandl9a54d7c2008-07-16 23:15:30 +000039 } else {
40 PyObject *index = PyNumber_Index(arg);
41 if (index == NULL) {
42 PyErr_Format(PyExc_TypeError, "an integer is required");
Mark Dickinson10de93a2010-07-09 19:25:48 +000043 *value = -1;
Christian Heimes2c9c7a52008-05-26 13:42:13 +000044 return 0;
45 }
Georg Brandl9a54d7c2008-07-16 23:15:30 +000046 face_value = PyLong_AsLong(index);
47 Py_DECREF(index);
48 }
49
50 if (face_value < 0 || face_value >= 256) {
51 /* this includes the OverflowError in case the long is too large */
52 PyErr_SetString(PyExc_ValueError, "byte must be in range(0, 256)");
Mark Dickinson10de93a2010-07-09 19:25:48 +000053 *value = -1;
Christian Heimes2c9c7a52008-05-26 13:42:13 +000054 return 0;
55 }
56
57 *value = face_value;
58 return 1;
59}
60
61static int
Benjamin Peterson153c70f2009-04-18 15:42:12 +000062bytearray_getbuffer(PyByteArrayObject *obj, Py_buffer *view, int flags)
Christian Heimes2c9c7a52008-05-26 13:42:13 +000063{
Christian Heimes2c9c7a52008-05-26 13:42:13 +000064 void *ptr;
65 if (view == NULL) {
Stefan Krah5178d912015-02-03 16:57:21 +010066 PyErr_SetString(PyExc_BufferError,
67 "bytearray_getbuffer: view==NULL argument is obsolete");
68 return -1;
Christian Heimes2c9c7a52008-05-26 13:42:13 +000069 }
Antoine Pitroufc8d6f42010-01-17 12:38:54 +000070 ptr = (void *) PyByteArray_AS_STRING(obj);
Stefan Krah5178d912015-02-03 16:57:21 +010071 /* cannot fail if view != NULL and readonly == 0 */
72 (void)PyBuffer_FillInfo(view, (PyObject*)obj, ptr, Py_SIZE(obj), 0, flags);
73 obj->ob_exports++;
74 return 0;
Christian Heimes2c9c7a52008-05-26 13:42:13 +000075}
76
77static void
Benjamin Peterson153c70f2009-04-18 15:42:12 +000078bytearray_releasebuffer(PyByteArrayObject *obj, Py_buffer *view)
Christian Heimes2c9c7a52008-05-26 13:42:13 +000079{
80 obj->ob_exports--;
81}
82
Antoine Pitrou5504e892008-12-06 21:27:53 +000083static int
84_canresize(PyByteArrayObject *self)
85{
86 if (self->ob_exports > 0) {
87 PyErr_SetString(PyExc_BufferError,
88 "Existing exports of data: object cannot be re-sized");
89 return 0;
90 }
91 return 1;
92}
93
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030094#include "clinic/bytearrayobject.c.h"
95
Christian Heimes2c9c7a52008-05-26 13:42:13 +000096/* Direct API functions */
97
98PyObject *
99PyByteArray_FromObject(PyObject *input)
100{
101 return PyObject_CallFunctionObjArgs((PyObject *)&PyByteArray_Type,
102 input, NULL);
103}
104
105PyObject *
106PyByteArray_FromStringAndSize(const char *bytes, Py_ssize_t size)
107{
108 PyByteArrayObject *new;
109 Py_ssize_t alloc;
110
111 if (size < 0) {
112 PyErr_SetString(PyExc_SystemError,
113 "Negative size passed to PyByteArray_FromStringAndSize");
114 return NULL;
115 }
116
Neal Norwitz3ce5d922008-08-24 07:08:55 +0000117 /* Prevent buffer overflow when setting alloc to size+1. */
118 if (size == PY_SSIZE_T_MAX) {
119 return PyErr_NoMemory();
120 }
121
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000122 new = PyObject_New(PyByteArrayObject, &PyByteArray_Type);
123 if (new == NULL)
124 return NULL;
125
126 if (size == 0) {
127 new->ob_bytes = NULL;
128 alloc = 0;
129 }
130 else {
131 alloc = size + 1;
Antoine Pitrou39aba4f2011-11-12 21:15:28 +0100132 new->ob_bytes = PyObject_Malloc(alloc);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000133 if (new->ob_bytes == NULL) {
134 Py_DECREF(new);
135 return PyErr_NoMemory();
136 }
Antoine Pitroufc8d6f42010-01-17 12:38:54 +0000137 if (bytes != NULL && size > 0)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000138 memcpy(new->ob_bytes, bytes, size);
139 new->ob_bytes[size] = '\0'; /* Trailing null byte */
140 }
141 Py_SIZE(new) = size;
142 new->ob_alloc = alloc;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200143 new->ob_start = new->ob_bytes;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000144 new->ob_exports = 0;
145
146 return (PyObject *)new;
147}
148
149Py_ssize_t
150PyByteArray_Size(PyObject *self)
151{
152 assert(self != NULL);
153 assert(PyByteArray_Check(self));
154
155 return PyByteArray_GET_SIZE(self);
156}
157
158char *
159PyByteArray_AsString(PyObject *self)
160{
161 assert(self != NULL);
162 assert(PyByteArray_Check(self));
163
164 return PyByteArray_AS_STRING(self);
165}
166
167int
Antoine Pitroucc231542014-11-02 18:40:09 +0100168PyByteArray_Resize(PyObject *self, Py_ssize_t requested_size)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000169{
170 void *sval;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200171 PyByteArrayObject *obj = ((PyByteArrayObject *)self);
Antoine Pitroucc231542014-11-02 18:40:09 +0100172 /* All computations are done unsigned to avoid integer overflows
173 (see issue #22335). */
174 size_t alloc = (size_t) obj->ob_alloc;
175 size_t logical_offset = (size_t) (obj->ob_start - obj->ob_bytes);
176 size_t size = (size_t) requested_size;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000177
178 assert(self != NULL);
179 assert(PyByteArray_Check(self));
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200180 assert(logical_offset <= alloc);
Antoine Pitroucc231542014-11-02 18:40:09 +0100181 assert(requested_size >= 0);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000182
Antoine Pitroucc231542014-11-02 18:40:09 +0100183 if (requested_size == Py_SIZE(self)) {
Antoine Pitrou5504e892008-12-06 21:27:53 +0000184 return 0;
185 }
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200186 if (!_canresize(obj)) {
Antoine Pitrou5504e892008-12-06 21:27:53 +0000187 return -1;
188 }
189
Antoine Pitrou25454112015-05-19 20:52:27 +0200190 if (size + logical_offset + 1 <= alloc) {
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200191 /* Current buffer is large enough to host the requested size,
192 decide on a strategy. */
193 if (size < alloc / 2) {
194 /* Major downsize; resize down to exact size */
195 alloc = size + 1;
196 }
197 else {
198 /* Minor downsize; quick exit */
199 Py_SIZE(self) = size;
200 PyByteArray_AS_STRING(self)[size] = '\0'; /* Trailing null */
201 return 0;
202 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000203 }
204 else {
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200205 /* Need growing, decide on a strategy */
206 if (size <= alloc * 1.125) {
207 /* Moderate upsize; overallocate similar to list_resize() */
208 alloc = size + (size >> 3) + (size < 9 ? 3 : 6);
209 }
210 else {
211 /* Major upsize; resize up to exact size */
212 alloc = size + 1;
213 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000214 }
Antoine Pitroucc231542014-11-02 18:40:09 +0100215 if (alloc > PY_SSIZE_T_MAX) {
216 PyErr_NoMemory();
217 return -1;
218 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000219
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200220 if (logical_offset > 0) {
221 sval = PyObject_Malloc(alloc);
222 if (sval == NULL) {
223 PyErr_NoMemory();
224 return -1;
225 }
Antoine Pitroucc231542014-11-02 18:40:09 +0100226 memcpy(sval, PyByteArray_AS_STRING(self),
227 Py_MIN(requested_size, Py_SIZE(self)));
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200228 PyObject_Free(obj->ob_bytes);
229 }
230 else {
231 sval = PyObject_Realloc(obj->ob_bytes, alloc);
232 if (sval == NULL) {
233 PyErr_NoMemory();
234 return -1;
235 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000236 }
237
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200238 obj->ob_bytes = obj->ob_start = sval;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000239 Py_SIZE(self) = size;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200240 obj->ob_alloc = alloc;
241 obj->ob_bytes[size] = '\0'; /* Trailing null byte */
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000242
243 return 0;
244}
245
246PyObject *
247PyByteArray_Concat(PyObject *a, PyObject *b)
248{
249 Py_ssize_t size;
250 Py_buffer va, vb;
251 PyByteArrayObject *result = NULL;
252
253 va.len = -1;
254 vb.len = -1;
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +0200255 if (PyObject_GetBuffer(a, &va, PyBUF_SIMPLE) != 0 ||
256 PyObject_GetBuffer(b, &vb, PyBUF_SIMPLE) != 0) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000257 PyErr_Format(PyExc_TypeError, "can't concat %.100s to %.100s",
258 Py_TYPE(a)->tp_name, Py_TYPE(b)->tp_name);
259 goto done;
260 }
261
262 size = va.len + vb.len;
263 if (size < 0) {
Benjamin Petersone0124bd2009-03-09 21:04:33 +0000264 PyErr_NoMemory();
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000265 goto done;
266 }
267
268 result = (PyByteArrayObject *) PyByteArray_FromStringAndSize(NULL, size);
269 if (result != NULL) {
270 memcpy(result->ob_bytes, va.buf, va.len);
271 memcpy(result->ob_bytes + va.len, vb.buf, vb.len);
272 }
273
274 done:
275 if (va.len != -1)
Martin v. Löwis423be952008-08-13 15:53:07 +0000276 PyBuffer_Release(&va);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000277 if (vb.len != -1)
Martin v. Löwis423be952008-08-13 15:53:07 +0000278 PyBuffer_Release(&vb);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000279 return (PyObject *)result;
280}
281
Ethan Furmanb95b5612015-01-23 20:05:18 -0800282static PyObject *
283bytearray_format(PyByteArrayObject *self, PyObject *args)
284{
285 PyObject *bytes_in, *bytes_out, *res;
286 char *bytestring;
287
288 if (self == NULL || !PyByteArray_Check(self) || args == NULL) {
289 PyErr_BadInternalCall();
290 return NULL;
291 }
292 bytestring = PyByteArray_AS_STRING(self);
293 bytes_in = PyBytes_FromString(bytestring);
294 if (bytes_in == NULL)
295 return NULL;
296 bytes_out = _PyBytes_Format(bytes_in, args);
297 Py_DECREF(bytes_in);
298 if (bytes_out == NULL)
299 return NULL;
300 res = PyByteArray_FromObject(bytes_out);
301 Py_DECREF(bytes_out);
302 if (res == NULL)
303 return NULL;
304 return res;
305}
306
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000307/* Functions stuffed into the type object */
308
309static Py_ssize_t
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000310bytearray_length(PyByteArrayObject *self)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000311{
312 return Py_SIZE(self);
313}
314
315static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000316bytearray_iconcat(PyByteArrayObject *self, PyObject *other)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000317{
318 Py_ssize_t mysize;
319 Py_ssize_t size;
320 Py_buffer vo;
321
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +0200322 if (PyObject_GetBuffer(other, &vo, PyBUF_SIMPLE) != 0) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000323 PyErr_Format(PyExc_TypeError, "can't concat %.100s to %.100s",
324 Py_TYPE(other)->tp_name, Py_TYPE(self)->tp_name);
325 return NULL;
326 }
327
328 mysize = Py_SIZE(self);
329 size = mysize + vo.len;
330 if (size < 0) {
Martin v. Löwis423be952008-08-13 15:53:07 +0000331 PyBuffer_Release(&vo);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000332 return PyErr_NoMemory();
333 }
Antoine Pitrou25454112015-05-19 20:52:27 +0200334 if (PyByteArray_Resize((PyObject *)self, size) < 0) {
Martin v. Löwis423be952008-08-13 15:53:07 +0000335 PyBuffer_Release(&vo);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000336 return NULL;
337 }
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200338 memcpy(PyByteArray_AS_STRING(self) + mysize, vo.buf, vo.len);
Martin v. Löwis423be952008-08-13 15:53:07 +0000339 PyBuffer_Release(&vo);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000340 Py_INCREF(self);
341 return (PyObject *)self;
342}
343
344static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000345bytearray_repeat(PyByteArrayObject *self, Py_ssize_t count)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000346{
347 PyByteArrayObject *result;
348 Py_ssize_t mysize;
349 Py_ssize_t size;
350
351 if (count < 0)
352 count = 0;
353 mysize = Py_SIZE(self);
Mark Dickinsoncf940c72010-08-10 18:35:01 +0000354 if (count > 0 && mysize > PY_SSIZE_T_MAX / count)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000355 return PyErr_NoMemory();
Mark Dickinsoncf940c72010-08-10 18:35:01 +0000356 size = mysize * count;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000357 result = (PyByteArrayObject *)PyByteArray_FromStringAndSize(NULL, size);
358 if (result != NULL && size != 0) {
359 if (mysize == 1)
360 memset(result->ob_bytes, self->ob_bytes[0], size);
361 else {
362 Py_ssize_t i;
363 for (i = 0; i < count; i++)
364 memcpy(result->ob_bytes + i*mysize, self->ob_bytes, mysize);
365 }
366 }
367 return (PyObject *)result;
368}
369
370static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000371bytearray_irepeat(PyByteArrayObject *self, Py_ssize_t count)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000372{
373 Py_ssize_t mysize;
374 Py_ssize_t size;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200375 char *buf;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000376
377 if (count < 0)
378 count = 0;
379 mysize = Py_SIZE(self);
Mark Dickinsoncf940c72010-08-10 18:35:01 +0000380 if (count > 0 && mysize > PY_SSIZE_T_MAX / count)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000381 return PyErr_NoMemory();
Mark Dickinsoncf940c72010-08-10 18:35:01 +0000382 size = mysize * count;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200383 if (PyByteArray_Resize((PyObject *)self, size) < 0)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000384 return NULL;
385
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200386 buf = PyByteArray_AS_STRING(self);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000387 if (mysize == 1)
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200388 memset(buf, buf[0], size);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000389 else {
390 Py_ssize_t i;
391 for (i = 1; i < count; i++)
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200392 memcpy(buf + i*mysize, buf, mysize);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000393 }
394
395 Py_INCREF(self);
396 return (PyObject *)self;
397}
398
399static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000400bytearray_getitem(PyByteArrayObject *self, Py_ssize_t i)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000401{
402 if (i < 0)
403 i += Py_SIZE(self);
404 if (i < 0 || i >= Py_SIZE(self)) {
405 PyErr_SetString(PyExc_IndexError, "bytearray index out of range");
406 return NULL;
407 }
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200408 return PyLong_FromLong((unsigned char)(PyByteArray_AS_STRING(self)[i]));
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000409}
410
411static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000412bytearray_subscript(PyByteArrayObject *self, PyObject *index)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000413{
Georg Brandl9a54d7c2008-07-16 23:15:30 +0000414 if (PyIndex_Check(index)) {
415 Py_ssize_t i = PyNumber_AsSsize_t(index, PyExc_IndexError);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000416
417 if (i == -1 && PyErr_Occurred())
418 return NULL;
419
420 if (i < 0)
421 i += PyByteArray_GET_SIZE(self);
422
423 if (i < 0 || i >= Py_SIZE(self)) {
424 PyErr_SetString(PyExc_IndexError, "bytearray index out of range");
425 return NULL;
426 }
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200427 return PyLong_FromLong((unsigned char)(PyByteArray_AS_STRING(self)[i]));
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000428 }
Georg Brandl9a54d7c2008-07-16 23:15:30 +0000429 else if (PySlice_Check(index)) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000430 Py_ssize_t start, stop, step, slicelength, cur, i;
Martin v. Löwis4d0d4712010-12-03 20:14:31 +0000431 if (PySlice_GetIndicesEx(index,
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000432 PyByteArray_GET_SIZE(self),
433 &start, &stop, &step, &slicelength) < 0) {
434 return NULL;
435 }
436
437 if (slicelength <= 0)
438 return PyByteArray_FromStringAndSize("", 0);
439 else if (step == 1) {
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200440 return PyByteArray_FromStringAndSize(
441 PyByteArray_AS_STRING(self) + start, slicelength);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000442 }
443 else {
444 char *source_buf = PyByteArray_AS_STRING(self);
Alexandre Vassalottie2641f42009-04-03 06:38:02 +0000445 char *result_buf;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000446 PyObject *result;
447
Alexandre Vassalottie2641f42009-04-03 06:38:02 +0000448 result = PyByteArray_FromStringAndSize(NULL, slicelength);
449 if (result == NULL)
450 return NULL;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000451
Alexandre Vassalottie2641f42009-04-03 06:38:02 +0000452 result_buf = PyByteArray_AS_STRING(result);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000453 for (cur = start, i = 0; i < slicelength;
454 cur += step, i++) {
455 result_buf[i] = source_buf[cur];
456 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000457 return result;
458 }
459 }
460 else {
Terry Jan Reedyffff1442014-08-02 01:30:37 -0400461 PyErr_Format(PyExc_TypeError,
462 "bytearray indices must be integers or slices, not %.200s",
463 Py_TYPE(index)->tp_name);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000464 return NULL;
465 }
466}
467
468static int
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200469bytearray_setslice_linear(PyByteArrayObject *self,
470 Py_ssize_t lo, Py_ssize_t hi,
471 char *bytes, Py_ssize_t bytes_len)
472{
473 Py_ssize_t avail = hi - lo;
474 char *buf = PyByteArray_AS_STRING(self);
475 Py_ssize_t growth = bytes_len - avail;
Victor Stinner84557232013-11-21 12:29:51 +0100476 int res = 0;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200477 assert(avail >= 0);
478
Victor Stinner84557232013-11-21 12:29:51 +0100479 if (growth < 0) {
480 if (!_canresize(self))
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200481 return -1;
Victor Stinner84557232013-11-21 12:29:51 +0100482
483 if (lo == 0) {
484 /* Shrink the buffer by advancing its logical start */
485 self->ob_start -= growth;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200486 /*
Victor Stinner84557232013-11-21 12:29:51 +0100487 0 lo hi old_size
488 | |<----avail----->|<-----tail------>|
489 | |<-bytes_len->|<-----tail------>|
490 0 new_lo new_hi new_size
491 */
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200492 }
Victor Stinner84557232013-11-21 12:29:51 +0100493 else {
494 /*
495 0 lo hi old_size
496 | |<----avail----->|<-----tomove------>|
497 | |<-bytes_len->|<-----tomove------>|
498 0 lo new_hi new_size
499 */
500 memmove(buf + lo + bytes_len, buf + hi,
501 Py_SIZE(self) - hi);
502 }
503 if (PyByteArray_Resize((PyObject *)self,
504 Py_SIZE(self) + growth) < 0) {
505 /* Issue #19578: Handling the memory allocation failure here is
506 tricky here because the bytearray object has already been
507 modified. Depending on growth and lo, the behaviour is
508 different.
509
510 If growth < 0 and lo != 0, the operation is completed, but a
511 MemoryError is still raised and the memory block is not
512 shrinked. Otherwise, the bytearray is restored in its previous
513 state and a MemoryError is raised. */
514 if (lo == 0) {
515 self->ob_start += growth;
516 return -1;
517 }
518 /* memmove() removed bytes, the bytearray object cannot be
519 restored in its previous state. */
520 Py_SIZE(self) += growth;
521 res = -1;
522 }
523 buf = PyByteArray_AS_STRING(self);
524 }
525 else if (growth > 0) {
526 if (Py_SIZE(self) > (Py_ssize_t)PY_SSIZE_T_MAX - growth) {
527 PyErr_NoMemory();
528 return -1;
529 }
530
531 if (PyByteArray_Resize((PyObject *)self,
532 Py_SIZE(self) + growth) < 0) {
533 return -1;
534 }
535 buf = PyByteArray_AS_STRING(self);
536 /* Make the place for the additional bytes */
537 /*
538 0 lo hi old_size
539 | |<-avail->|<-----tomove------>|
540 | |<---bytes_len-->|<-----tomove------>|
541 0 lo new_hi new_size
542 */
543 memmove(buf + lo + bytes_len, buf + hi,
544 Py_SIZE(self) - lo - bytes_len);
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200545 }
546
547 if (bytes_len > 0)
548 memcpy(buf + lo, bytes, bytes_len);
Victor Stinner84557232013-11-21 12:29:51 +0100549 return res;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200550}
551
552static int
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000553bytearray_setslice(PyByteArrayObject *self, Py_ssize_t lo, Py_ssize_t hi,
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000554 PyObject *values)
555{
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200556 Py_ssize_t needed;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000557 void *bytes;
558 Py_buffer vbytes;
559 int res = 0;
560
561 vbytes.len = -1;
562 if (values == (PyObject *)self) {
563 /* Make a copy and call this function recursively */
564 int err;
565 values = PyByteArray_FromObject(values);
566 if (values == NULL)
567 return -1;
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000568 err = bytearray_setslice(self, lo, hi, values);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000569 Py_DECREF(values);
570 return err;
571 }
572 if (values == NULL) {
573 /* del b[lo:hi] */
574 bytes = NULL;
575 needed = 0;
576 }
577 else {
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +0200578 if (PyObject_GetBuffer(values, &vbytes, PyBUF_SIMPLE) != 0) {
579 PyErr_Format(PyExc_TypeError,
580 "can't set bytearray slice from %.100s",
581 Py_TYPE(values)->tp_name);
582 return -1;
583 }
584 needed = vbytes.len;
585 bytes = vbytes.buf;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000586 }
587
588 if (lo < 0)
589 lo = 0;
590 if (hi < lo)
591 hi = lo;
592 if (hi > Py_SIZE(self))
593 hi = Py_SIZE(self);
594
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200595 res = bytearray_setslice_linear(self, lo, hi, bytes, needed);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000596 if (vbytes.len != -1)
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200597 PyBuffer_Release(&vbytes);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000598 return res;
599}
600
601static int
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000602bytearray_setitem(PyByteArrayObject *self, Py_ssize_t i, PyObject *value)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000603{
Georg Brandl9a54d7c2008-07-16 23:15:30 +0000604 int ival;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000605
606 if (i < 0)
607 i += Py_SIZE(self);
608
609 if (i < 0 || i >= Py_SIZE(self)) {
610 PyErr_SetString(PyExc_IndexError, "bytearray index out of range");
611 return -1;
612 }
613
614 if (value == NULL)
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000615 return bytearray_setslice(self, i, i+1, NULL);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000616
Georg Brandl9a54d7c2008-07-16 23:15:30 +0000617 if (!_getbytevalue(value, &ival))
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000618 return -1;
619
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200620 PyByteArray_AS_STRING(self)[i] = ival;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000621 return 0;
622}
623
624static int
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000625bytearray_ass_subscript(PyByteArrayObject *self, PyObject *index, PyObject *values)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000626{
627 Py_ssize_t start, stop, step, slicelen, needed;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200628 char *buf, *bytes;
629 buf = PyByteArray_AS_STRING(self);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000630
Georg Brandl9a54d7c2008-07-16 23:15:30 +0000631 if (PyIndex_Check(index)) {
632 Py_ssize_t i = PyNumber_AsSsize_t(index, PyExc_IndexError);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000633
634 if (i == -1 && PyErr_Occurred())
635 return -1;
636
637 if (i < 0)
638 i += PyByteArray_GET_SIZE(self);
639
640 if (i < 0 || i >= Py_SIZE(self)) {
641 PyErr_SetString(PyExc_IndexError, "bytearray index out of range");
642 return -1;
643 }
644
645 if (values == NULL) {
646 /* Fall through to slice assignment */
647 start = i;
648 stop = i + 1;
649 step = 1;
650 slicelen = 1;
651 }
652 else {
Georg Brandl9a54d7c2008-07-16 23:15:30 +0000653 int ival;
654 if (!_getbytevalue(values, &ival))
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000655 return -1;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200656 buf[i] = (char)ival;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000657 return 0;
658 }
659 }
Georg Brandl9a54d7c2008-07-16 23:15:30 +0000660 else if (PySlice_Check(index)) {
Martin v. Löwis4d0d4712010-12-03 20:14:31 +0000661 if (PySlice_GetIndicesEx(index,
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000662 PyByteArray_GET_SIZE(self),
663 &start, &stop, &step, &slicelen) < 0) {
664 return -1;
665 }
666 }
667 else {
Terry Jan Reedyffff1442014-08-02 01:30:37 -0400668 PyErr_Format(PyExc_TypeError,
669 "bytearray indices must be integers or slices, not %.200s",
670 Py_TYPE(index)->tp_name);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000671 return -1;
672 }
673
674 if (values == NULL) {
675 bytes = NULL;
676 needed = 0;
677 }
678 else if (values == (PyObject *)self || !PyByteArray_Check(values)) {
Christian Heimes6d26ade2012-11-03 23:07:59 +0100679 int err;
Ezio Melottic64bcbe2012-11-03 21:19:06 +0200680 if (PyNumber_Check(values) || PyUnicode_Check(values)) {
681 PyErr_SetString(PyExc_TypeError,
682 "can assign only bytes, buffers, or iterables "
683 "of ints in range(0, 256)");
684 return -1;
685 }
Georg Brandlf3fa5682010-12-04 17:09:30 +0000686 /* Make a copy and call this function recursively */
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000687 values = PyByteArray_FromObject(values);
688 if (values == NULL)
689 return -1;
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000690 err = bytearray_ass_subscript(self, index, values);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000691 Py_DECREF(values);
692 return err;
693 }
694 else {
695 assert(PyByteArray_Check(values));
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200696 bytes = PyByteArray_AS_STRING(values);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000697 needed = Py_SIZE(values);
698 }
699 /* Make sure b[5:2] = ... inserts before 5, not before 2. */
700 if ((step < 0 && start < stop) ||
701 (step > 0 && start > stop))
702 stop = start;
703 if (step == 1) {
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200704 return bytearray_setslice_linear(self, start, stop, bytes, needed);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000705 }
706 else {
707 if (needed == 0) {
708 /* Delete slice */
Mark Dickinsonbc099642010-01-29 17:27:24 +0000709 size_t cur;
710 Py_ssize_t i;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000711
Antoine Pitrou5504e892008-12-06 21:27:53 +0000712 if (!_canresize(self))
713 return -1;
Mark Dickinson7e3b9482010-08-06 21:33:18 +0000714
715 if (slicelen == 0)
716 /* Nothing to do here. */
717 return 0;
718
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000719 if (step < 0) {
720 stop = start + 1;
721 start = stop + step * (slicelen - 1) - 1;
722 step = -step;
723 }
724 for (cur = start, i = 0;
725 i < slicelen; cur += step, i++) {
726 Py_ssize_t lim = step - 1;
727
Mark Dickinson66f575b2010-02-14 12:53:32 +0000728 if (cur + step >= (size_t)PyByteArray_GET_SIZE(self))
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000729 lim = PyByteArray_GET_SIZE(self) - cur - 1;
730
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200731 memmove(buf + cur - i,
732 buf + cur + 1, lim);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000733 }
734 /* Move the tail of the bytes, in one chunk */
Mark Dickinson7e3b9482010-08-06 21:33:18 +0000735 cur = start + (size_t)slicelen*step;
Mark Dickinson66f575b2010-02-14 12:53:32 +0000736 if (cur < (size_t)PyByteArray_GET_SIZE(self)) {
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200737 memmove(buf + cur - slicelen,
738 buf + cur,
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000739 PyByteArray_GET_SIZE(self) - cur);
740 }
741 if (PyByteArray_Resize((PyObject *)self,
742 PyByteArray_GET_SIZE(self) - slicelen) < 0)
743 return -1;
744
745 return 0;
746 }
747 else {
748 /* Assign slice */
Mark Dickinson7e3b9482010-08-06 21:33:18 +0000749 Py_ssize_t i;
750 size_t cur;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000751
752 if (needed != slicelen) {
753 PyErr_Format(PyExc_ValueError,
754 "attempt to assign bytes of size %zd "
755 "to extended slice of size %zd",
756 needed, slicelen);
757 return -1;
758 }
759 for (cur = start, i = 0; i < slicelen; cur += step, i++)
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200760 buf[cur] = bytes[i];
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000761 return 0;
762 }
763 }
764}
765
766static int
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000767bytearray_init(PyByteArrayObject *self, PyObject *args, PyObject *kwds)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000768{
769 static char *kwlist[] = {"source", "encoding", "errors", 0};
770 PyObject *arg = NULL;
771 const char *encoding = NULL;
772 const char *errors = NULL;
773 Py_ssize_t count;
774 PyObject *it;
775 PyObject *(*iternext)(PyObject *);
776
777 if (Py_SIZE(self) != 0) {
778 /* Empty previous contents (yes, do this first of all!) */
779 if (PyByteArray_Resize((PyObject *)self, 0) < 0)
780 return -1;
781 }
782
783 /* Parse arguments */
Georg Brandl3dbca812008-07-23 16:10:53 +0000784 if (!PyArg_ParseTupleAndKeywords(args, kwds, "|Oss:bytearray", kwlist,
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000785 &arg, &encoding, &errors))
786 return -1;
787
788 /* Make a quick exit if no first argument */
789 if (arg == NULL) {
790 if (encoding != NULL || errors != NULL) {
791 PyErr_SetString(PyExc_TypeError,
792 "encoding or errors without sequence argument");
793 return -1;
794 }
795 return 0;
796 }
797
798 if (PyUnicode_Check(arg)) {
799 /* Encode via the codec registry */
800 PyObject *encoded, *new;
801 if (encoding == NULL) {
802 PyErr_SetString(PyExc_TypeError,
803 "string argument without an encoding");
804 return -1;
805 }
Marc-André Lemburgb2750b52008-06-06 12:18:17 +0000806 encoded = PyUnicode_AsEncodedString(arg, encoding, errors);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000807 if (encoded == NULL)
808 return -1;
809 assert(PyBytes_Check(encoded));
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000810 new = bytearray_iconcat(self, encoded);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000811 Py_DECREF(encoded);
812 if (new == NULL)
813 return -1;
814 Py_DECREF(new);
815 return 0;
816 }
817
818 /* If it's not unicode, there can't be encoding or errors */
819 if (encoding != NULL || errors != NULL) {
820 PyErr_SetString(PyExc_TypeError,
821 "encoding or errors without a string argument");
822 return -1;
823 }
824
825 /* Is it an int? */
Benjamin Peterson8380dd52010-04-16 22:51:37 +0000826 count = PyNumber_AsSsize_t(arg, PyExc_OverflowError);
827 if (count == -1 && PyErr_Occurred()) {
828 if (PyErr_ExceptionMatches(PyExc_OverflowError))
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000829 return -1;
Benjamin Peterson9c0e94f2010-04-16 23:00:53 +0000830 PyErr_Clear();
Benjamin Peterson8380dd52010-04-16 22:51:37 +0000831 }
832 else if (count < 0) {
833 PyErr_SetString(PyExc_ValueError, "negative count");
834 return -1;
835 }
836 else {
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000837 if (count > 0) {
Victor Stinner2bc4d952014-06-02 22:22:42 +0200838 if (PyByteArray_Resize((PyObject *)self, count))
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000839 return -1;
Victor Stinner2bc4d952014-06-02 22:22:42 +0200840 memset(PyByteArray_AS_STRING(self), 0, count);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000841 }
842 return 0;
843 }
844
845 /* Use the buffer API */
846 if (PyObject_CheckBuffer(arg)) {
847 Py_ssize_t size;
848 Py_buffer view;
849 if (PyObject_GetBuffer(arg, &view, PyBUF_FULL_RO) < 0)
850 return -1;
851 size = view.len;
852 if (PyByteArray_Resize((PyObject *)self, size) < 0) goto fail;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200853 if (PyBuffer_ToContiguous(PyByteArray_AS_STRING(self),
854 &view, size, 'C') < 0)
Stefan Krah7d12d9d2012-07-28 12:25:55 +0200855 goto fail;
Martin v. Löwis423be952008-08-13 15:53:07 +0000856 PyBuffer_Release(&view);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000857 return 0;
858 fail:
Martin v. Löwis423be952008-08-13 15:53:07 +0000859 PyBuffer_Release(&view);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000860 return -1;
861 }
862
863 /* XXX Optimize this if the arguments is a list, tuple */
864
865 /* Get the iterator */
866 it = PyObject_GetIter(arg);
867 if (it == NULL)
868 return -1;
869 iternext = *Py_TYPE(it)->tp_iternext;
870
871 /* Run the iterator to exhaustion */
872 for (;;) {
873 PyObject *item;
Georg Brandl9a54d7c2008-07-16 23:15:30 +0000874 int rc, value;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000875
876 /* Get the next item */
877 item = iternext(it);
878 if (item == NULL) {
879 if (PyErr_Occurred()) {
880 if (!PyErr_ExceptionMatches(PyExc_StopIteration))
881 goto error;
882 PyErr_Clear();
883 }
884 break;
885 }
886
887 /* Interpret it as an int (__index__) */
Georg Brandl9a54d7c2008-07-16 23:15:30 +0000888 rc = _getbytevalue(item, &value);
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000889 Py_DECREF(item);
Georg Brandl9a54d7c2008-07-16 23:15:30 +0000890 if (!rc)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000891 goto error;
892
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000893 /* Append the byte */
Serhiy Storchaka7b6e3b92015-06-29 21:14:06 +0300894 if (Py_SIZE(self) + 1 < self->ob_alloc) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000895 Py_SIZE(self)++;
Serhiy Storchaka7b6e3b92015-06-29 21:14:06 +0300896 PyByteArray_AS_STRING(self)[Py_SIZE(self)] = '\0';
897 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000898 else if (PyByteArray_Resize((PyObject *)self, Py_SIZE(self)+1) < 0)
899 goto error;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200900 PyByteArray_AS_STRING(self)[Py_SIZE(self)-1] = value;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000901 }
902
903 /* Clean up and return success */
904 Py_DECREF(it);
905 return 0;
906
907 error:
908 /* Error handling when it != NULL */
909 Py_DECREF(it);
910 return -1;
911}
912
913/* Mostly copied from string_repr, but without the
914 "smart quote" functionality. */
915static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000916bytearray_repr(PyByteArrayObject *self)
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000917{
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000918 const char *quote_prefix = "bytearray(b";
919 const char *quote_postfix = ")";
920 Py_ssize_t length = Py_SIZE(self);
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200921 /* 15 == strlen(quote_prefix) + 2 + strlen(quote_postfix) + 1 */
Mark Dickinson66f575b2010-02-14 12:53:32 +0000922 size_t newsize;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000923 PyObject *v;
Antoine Pitrou9ed5f272013-08-13 20:18:52 +0200924 Py_ssize_t i;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200925 char *bytes;
Antoine Pitrou9ed5f272013-08-13 20:18:52 +0200926 char c;
927 char *p;
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200928 int quote;
929 char *test, *start;
930 char *buffer;
931
932 if (length > (PY_SSIZE_T_MAX - 15) / 4) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000933 PyErr_SetString(PyExc_OverflowError,
934 "bytearray object is too large to make repr");
935 return NULL;
936 }
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200937
938 newsize = 15 + length * 4;
Antoine Pitrou39aba4f2011-11-12 21:15:28 +0100939 buffer = PyObject_Malloc(newsize);
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200940 if (buffer == NULL) {
941 PyErr_NoMemory();
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000942 return NULL;
943 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000944
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200945 /* Figure out which quote to use; single is preferred */
946 quote = '\'';
947 start = PyByteArray_AS_STRING(self);
948 for (test = start; test < start+length; ++test) {
949 if (*test == '"') {
950 quote = '\''; /* back to single */
951 break;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000952 }
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200953 else if (*test == '\'')
954 quote = '"';
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000955 }
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200956
957 p = buffer;
958 while (*quote_prefix)
959 *p++ = *quote_prefix++;
960 *p++ = quote;
961
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200962 bytes = PyByteArray_AS_STRING(self);
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200963 for (i = 0; i < length; i++) {
964 /* There's at least enough room for a hex escape
965 and a closing quote. */
966 assert(newsize - (p - buffer) >= 5);
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +0200967 c = bytes[i];
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200968 if (c == '\'' || c == '\\')
969 *p++ = '\\', *p++ = c;
970 else if (c == '\t')
971 *p++ = '\\', *p++ = 't';
972 else if (c == '\n')
973 *p++ = '\\', *p++ = 'n';
974 else if (c == '\r')
975 *p++ = '\\', *p++ = 'r';
976 else if (c == 0)
977 *p++ = '\\', *p++ = 'x', *p++ = '0', *p++ = '0';
978 else if (c < ' ' || c >= 0x7f) {
979 *p++ = '\\';
980 *p++ = 'x';
Victor Stinnerf5cff562011-10-14 02:13:11 +0200981 *p++ = Py_hexdigits[(c & 0xf0) >> 4];
982 *p++ = Py_hexdigits[c & 0xf];
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200983 }
984 else
985 *p++ = c;
986 }
987 assert(newsize - (p - buffer) >= 1);
988 *p++ = quote;
989 while (*quote_postfix) {
990 *p++ = *quote_postfix++;
991 }
992
993 v = PyUnicode_DecodeASCII(buffer, p - buffer, NULL);
Antoine Pitrou39aba4f2011-11-12 21:15:28 +0100994 PyObject_Free(buffer);
Martin v. Löwisd63a3b82011-09-28 07:41:54 +0200995 return v;
Christian Heimes2c9c7a52008-05-26 13:42:13 +0000996}
997
998static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +0000999bytearray_str(PyObject *op)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001000{
Alexander Belopolskyf0f45142010-08-11 17:31:17 +00001001 if (Py_BytesWarningFlag) {
1002 if (PyErr_WarnEx(PyExc_BytesWarning,
1003 "str() on a bytearray instance", 1))
1004 return NULL;
1005 }
1006 return bytearray_repr((PyByteArrayObject*)op);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001007}
1008
1009static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001010bytearray_richcompare(PyObject *self, PyObject *other, int op)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001011{
1012 Py_ssize_t self_size, other_size;
1013 Py_buffer self_bytes, other_bytes;
1014 PyObject *res;
1015 Py_ssize_t minsize;
Serhiy Storchakafa494fd2015-05-30 17:45:22 +03001016 int cmp, rc;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001017
1018 /* Bytes can be compared to anything that supports the (binary)
1019 buffer API. Except that a comparison with Unicode is always an
1020 error, even if the comparison is for equality. */
Serhiy Storchakafa494fd2015-05-30 17:45:22 +03001021 rc = PyObject_IsInstance(self, (PyObject*)&PyUnicode_Type);
1022 if (!rc)
1023 rc = PyObject_IsInstance(other, (PyObject*)&PyUnicode_Type);
1024 if (rc < 0)
1025 return NULL;
1026 if (rc) {
Barry Warsaw9e9dcd62008-10-17 01:50:37 +00001027 if (Py_BytesWarningFlag && (op == Py_EQ || op == Py_NE)) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001028 if (PyErr_WarnEx(PyExc_BytesWarning,
Georg Brandle5d68ac2008-06-04 11:30:26 +00001029 "Comparison between bytearray and string", 1))
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001030 return NULL;
1031 }
1032
Brian Curtindfc80e32011-08-10 20:28:54 -05001033 Py_RETURN_NOTIMPLEMENTED;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001034 }
1035
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02001036 if (PyObject_GetBuffer(self, &self_bytes, PyBUF_SIMPLE) != 0) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001037 PyErr_Clear();
Brian Curtindfc80e32011-08-10 20:28:54 -05001038 Py_RETURN_NOTIMPLEMENTED;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001039 }
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02001040 self_size = self_bytes.len;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001041
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02001042 if (PyObject_GetBuffer(other, &other_bytes, PyBUF_SIMPLE) != 0) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001043 PyErr_Clear();
Martin v. Löwis423be952008-08-13 15:53:07 +00001044 PyBuffer_Release(&self_bytes);
Brian Curtindfc80e32011-08-10 20:28:54 -05001045 Py_RETURN_NOTIMPLEMENTED;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001046 }
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02001047 other_size = other_bytes.len;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001048
1049 if (self_size != other_size && (op == Py_EQ || op == Py_NE)) {
1050 /* Shortcut: if the lengths differ, the objects differ */
1051 cmp = (op == Py_NE);
1052 }
1053 else {
1054 minsize = self_size;
1055 if (other_size < minsize)
1056 minsize = other_size;
1057
1058 cmp = memcmp(self_bytes.buf, other_bytes.buf, minsize);
1059 /* In ISO C, memcmp() guarantees to use unsigned bytes! */
1060
1061 if (cmp == 0) {
1062 if (self_size < other_size)
1063 cmp = -1;
1064 else if (self_size > other_size)
1065 cmp = 1;
1066 }
1067
1068 switch (op) {
1069 case Py_LT: cmp = cmp < 0; break;
1070 case Py_LE: cmp = cmp <= 0; break;
1071 case Py_EQ: cmp = cmp == 0; break;
1072 case Py_NE: cmp = cmp != 0; break;
1073 case Py_GT: cmp = cmp > 0; break;
1074 case Py_GE: cmp = cmp >= 0; break;
1075 }
1076 }
1077
1078 res = cmp ? Py_True : Py_False;
Martin v. Löwis423be952008-08-13 15:53:07 +00001079 PyBuffer_Release(&self_bytes);
1080 PyBuffer_Release(&other_bytes);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001081 Py_INCREF(res);
1082 return res;
1083}
1084
1085static void
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001086bytearray_dealloc(PyByteArrayObject *self)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001087{
Benjamin Petersone0124bd2009-03-09 21:04:33 +00001088 if (self->ob_exports > 0) {
1089 PyErr_SetString(PyExc_SystemError,
Benjamin Petersonef3e4c22009-04-11 19:48:14 +00001090 "deallocated bytearray object has exported buffers");
Benjamin Petersone0124bd2009-03-09 21:04:33 +00001091 PyErr_Print();
1092 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001093 if (self->ob_bytes != 0) {
Antoine Pitrou39aba4f2011-11-12 21:15:28 +01001094 PyObject_Free(self->ob_bytes);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001095 }
1096 Py_TYPE(self)->tp_free((PyObject *)self);
1097}
1098
1099
1100/* -------------------------------------------------------------------- */
1101/* Methods */
1102
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02001103#define FASTSEARCH fastsearch
1104#define STRINGLIB(F) stringlib_##F
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001105#define STRINGLIB_CHAR char
Antoine Pitroucfc22b42012-10-16 21:07:23 +02001106#define STRINGLIB_SIZEOF_CHAR 1
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001107#define STRINGLIB_LEN PyByteArray_GET_SIZE
1108#define STRINGLIB_STR PyByteArray_AS_STRING
1109#define STRINGLIB_NEW PyByteArray_FromStringAndSize
Antoine Pitrouf2c54842010-01-13 08:07:53 +00001110#define STRINGLIB_ISSPACE Py_ISSPACE
1111#define STRINGLIB_ISLINEBREAK(x) ((x == '\n') || (x == '\r'))
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001112#define STRINGLIB_CHECK_EXACT PyByteArray_CheckExact
1113#define STRINGLIB_MUTABLE 1
1114
1115#include "stringlib/fastsearch.h"
1116#include "stringlib/count.h"
1117#include "stringlib/find.h"
Antoine Pitroucfc22b42012-10-16 21:07:23 +02001118#include "stringlib/join.h"
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001119#include "stringlib/partition.h"
Antoine Pitrouf2c54842010-01-13 08:07:53 +00001120#include "stringlib/split.h"
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001121#include "stringlib/ctype.h"
1122#include "stringlib/transmogrify.h"
1123
1124
1125/* The following Py_LOCAL_INLINE and Py_LOCAL functions
1126were copied from the old char* style string object. */
1127
Antoine Pitrouf2c54842010-01-13 08:07:53 +00001128/* helper macro to fixup start/end slice values */
1129#define ADJUST_INDICES(start, end, len) \
1130 if (end > len) \
1131 end = len; \
1132 else if (end < 0) { \
1133 end += len; \
1134 if (end < 0) \
1135 end = 0; \
1136 } \
1137 if (start < 0) { \
1138 start += len; \
1139 if (start < 0) \
1140 start = 0; \
1141 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001142
1143Py_LOCAL_INLINE(Py_ssize_t)
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001144bytearray_find_internal(PyByteArrayObject *self, PyObject *args, int dir)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001145{
1146 PyObject *subobj;
Antoine Pitrouac65d962011-10-20 23:54:17 +02001147 char byte;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001148 Py_buffer subbuf;
Antoine Pitrouac65d962011-10-20 23:54:17 +02001149 const char *sub;
Serhiy Storchakad9d769f2015-03-24 21:55:47 +02001150 Py_ssize_t len, sub_len;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001151 Py_ssize_t start=0, end=PY_SSIZE_T_MAX;
1152 Py_ssize_t res;
1153
Antoine Pitrouac65d962011-10-20 23:54:17 +02001154 if (!stringlib_parse_args_finds_byte("find/rfind/index/rindex",
1155 args, &subobj, &byte, &start, &end))
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001156 return -2;
Antoine Pitrouac65d962011-10-20 23:54:17 +02001157
1158 if (subobj) {
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02001159 if (PyObject_GetBuffer(subobj, &subbuf, PyBUF_SIMPLE) != 0)
Antoine Pitrouac65d962011-10-20 23:54:17 +02001160 return -2;
1161
1162 sub = subbuf.buf;
1163 sub_len = subbuf.len;
1164 }
1165 else {
1166 sub = &byte;
1167 sub_len = 1;
1168 }
Serhiy Storchakad9d769f2015-03-24 21:55:47 +02001169 len = PyByteArray_GET_SIZE(self);
Antoine Pitrouac65d962011-10-20 23:54:17 +02001170
Serhiy Storchakad9d769f2015-03-24 21:55:47 +02001171 ADJUST_INDICES(start, end, len);
1172 if (end - start < sub_len)
1173 res = -1;
Victor Stinnerdabbfe72015-03-25 03:16:32 +01001174 /* Issue #23573: FIXME, windows has no memrchr() */
1175 else if (sub_len == 1 && dir > 0) {
Serhiy Storchakad9d769f2015-03-24 21:55:47 +02001176 unsigned char needle = *sub;
Serhiy Storchakad9d769f2015-03-24 21:55:47 +02001177 res = stringlib_fastsearch_memchr_1char(
1178 PyByteArray_AS_STRING(self) + start, end - start,
Christian Heimes4e259132015-04-18 05:54:02 +02001179 needle, needle, FAST_SEARCH);
Serhiy Storchakad9d769f2015-03-24 21:55:47 +02001180 if (res >= 0)
1181 res += start;
1182 }
1183 else {
1184 if (dir > 0)
1185 res = stringlib_find_slice(
1186 PyByteArray_AS_STRING(self), len,
1187 sub, sub_len, start, end);
1188 else
1189 res = stringlib_rfind_slice(
1190 PyByteArray_AS_STRING(self), len,
1191 sub, sub_len, start, end);
1192 }
Antoine Pitrouac65d962011-10-20 23:54:17 +02001193
1194 if (subobj)
1195 PyBuffer_Release(&subbuf);
1196
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001197 return res;
1198}
1199
1200PyDoc_STRVAR(find__doc__,
Georg Brandl17cb8a82008-05-30 08:20:09 +00001201"B.find(sub[, start[, end]]) -> int\n\
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001202\n\
1203Return the lowest index in B where subsection sub is found,\n\
Senthil Kumaran53516a82011-07-27 23:33:54 +08001204such that sub is contained within B[start,end]. Optional\n\
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001205arguments start and end are interpreted as in slice notation.\n\
1206\n\
1207Return -1 on failure.");
1208
1209static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001210bytearray_find(PyByteArrayObject *self, PyObject *args)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001211{
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001212 Py_ssize_t result = bytearray_find_internal(self, args, +1);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001213 if (result == -2)
1214 return NULL;
1215 return PyLong_FromSsize_t(result);
1216}
1217
1218PyDoc_STRVAR(count__doc__,
Georg Brandl17cb8a82008-05-30 08:20:09 +00001219"B.count(sub[, start[, end]]) -> int\n\
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001220\n\
1221Return the number of non-overlapping occurrences of subsection sub in\n\
1222bytes B[start:end]. Optional arguments start and end are interpreted\n\
1223as in slice notation.");
1224
1225static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001226bytearray_count(PyByteArrayObject *self, PyObject *args)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001227{
1228 PyObject *sub_obj;
Antoine Pitrouac65d962011-10-20 23:54:17 +02001229 const char *str = PyByteArray_AS_STRING(self), *sub;
1230 Py_ssize_t sub_len;
1231 char byte;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001232 Py_ssize_t start = 0, end = PY_SSIZE_T_MAX;
Antoine Pitrouac65d962011-10-20 23:54:17 +02001233
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001234 Py_buffer vsub;
1235 PyObject *count_obj;
1236
Antoine Pitrouac65d962011-10-20 23:54:17 +02001237 if (!stringlib_parse_args_finds_byte("count", args, &sub_obj, &byte,
1238 &start, &end))
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001239 return NULL;
1240
Antoine Pitrouac65d962011-10-20 23:54:17 +02001241 if (sub_obj) {
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02001242 if (PyObject_GetBuffer(sub_obj, &vsub, PyBUF_SIMPLE) != 0)
Antoine Pitrouac65d962011-10-20 23:54:17 +02001243 return NULL;
1244
1245 sub = vsub.buf;
1246 sub_len = vsub.len;
1247 }
1248 else {
1249 sub = &byte;
1250 sub_len = 1;
1251 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001252
Antoine Pitrouf2c54842010-01-13 08:07:53 +00001253 ADJUST_INDICES(start, end, PyByteArray_GET_SIZE(self));
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001254
1255 count_obj = PyLong_FromSsize_t(
Antoine Pitrouac65d962011-10-20 23:54:17 +02001256 stringlib_count(str + start, end - start, sub, sub_len, PY_SSIZE_T_MAX)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001257 );
Antoine Pitrouac65d962011-10-20 23:54:17 +02001258
1259 if (sub_obj)
1260 PyBuffer_Release(&vsub);
1261
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001262 return count_obj;
1263}
1264
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001265/*[clinic input]
1266bytearray.clear
1267
1268 self: self(type="PyByteArrayObject *")
1269
1270Remove all items from the bytearray.
1271[clinic start generated code]*/
1272
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001273static PyObject *
1274bytearray_clear_impl(PyByteArrayObject *self)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03001275/*[clinic end generated code: output=85c2fe6aede0956c input=e524fd330abcdc18]*/
Eli Bendersky4db28d32011-03-03 18:21:02 +00001276{
1277 if (PyByteArray_Resize((PyObject *)self, 0) < 0)
1278 return NULL;
1279 Py_RETURN_NONE;
1280}
1281
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001282/*[clinic input]
1283bytearray.copy
1284
1285 self: self(type="PyByteArrayObject *")
1286
1287Return a copy of B.
1288[clinic start generated code]*/
1289
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001290static PyObject *
1291bytearray_copy_impl(PyByteArrayObject *self)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03001292/*[clinic end generated code: output=68cfbcfed484c132 input=6d5d2975aa0f33f3]*/
Eli Bendersky4db28d32011-03-03 18:21:02 +00001293{
1294 return PyByteArray_FromStringAndSize(PyByteArray_AS_STRING((PyObject *)self),
1295 PyByteArray_GET_SIZE(self));
1296}
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001297
1298PyDoc_STRVAR(index__doc__,
Georg Brandl17cb8a82008-05-30 08:20:09 +00001299"B.index(sub[, start[, end]]) -> int\n\
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001300\n\
1301Like B.find() but raise ValueError when the subsection is not found.");
1302
1303static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001304bytearray_index(PyByteArrayObject *self, PyObject *args)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001305{
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001306 Py_ssize_t result = bytearray_find_internal(self, args, +1);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001307 if (result == -2)
1308 return NULL;
1309 if (result == -1) {
1310 PyErr_SetString(PyExc_ValueError,
1311 "subsection not found");
1312 return NULL;
1313 }
1314 return PyLong_FromSsize_t(result);
1315}
1316
1317
1318PyDoc_STRVAR(rfind__doc__,
Georg Brandl17cb8a82008-05-30 08:20:09 +00001319"B.rfind(sub[, start[, end]]) -> int\n\
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001320\n\
1321Return the highest index in B where subsection sub is found,\n\
Senthil Kumaran53516a82011-07-27 23:33:54 +08001322such that sub is contained within B[start,end]. Optional\n\
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001323arguments start and end are interpreted as in slice notation.\n\
1324\n\
1325Return -1 on failure.");
1326
1327static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001328bytearray_rfind(PyByteArrayObject *self, PyObject *args)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001329{
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001330 Py_ssize_t result = bytearray_find_internal(self, args, -1);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001331 if (result == -2)
1332 return NULL;
1333 return PyLong_FromSsize_t(result);
1334}
1335
1336
1337PyDoc_STRVAR(rindex__doc__,
Georg Brandl17cb8a82008-05-30 08:20:09 +00001338"B.rindex(sub[, start[, end]]) -> int\n\
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001339\n\
1340Like B.rfind() but raise ValueError when the subsection is not found.");
1341
1342static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001343bytearray_rindex(PyByteArrayObject *self, PyObject *args)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001344{
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001345 Py_ssize_t result = bytearray_find_internal(self, args, -1);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001346 if (result == -2)
1347 return NULL;
1348 if (result == -1) {
1349 PyErr_SetString(PyExc_ValueError,
1350 "subsection not found");
1351 return NULL;
1352 }
1353 return PyLong_FromSsize_t(result);
1354}
1355
1356
1357static int
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001358bytearray_contains(PyObject *self, PyObject *arg)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001359{
1360 Py_ssize_t ival = PyNumber_AsSsize_t(arg, PyExc_ValueError);
1361 if (ival == -1 && PyErr_Occurred()) {
1362 Py_buffer varg;
Antoine Pitrou0010d372010-08-15 17:12:55 +00001363 Py_ssize_t pos;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001364 PyErr_Clear();
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02001365 if (PyObject_GetBuffer(arg, &varg, PyBUF_SIMPLE) != 0)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001366 return -1;
1367 pos = stringlib_find(PyByteArray_AS_STRING(self), Py_SIZE(self),
1368 varg.buf, varg.len, 0);
Martin v. Löwis423be952008-08-13 15:53:07 +00001369 PyBuffer_Release(&varg);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001370 return pos >= 0;
1371 }
1372 if (ival < 0 || ival >= 256) {
1373 PyErr_SetString(PyExc_ValueError, "byte must be in range(0, 256)");
1374 return -1;
1375 }
1376
Antoine Pitrou0010d372010-08-15 17:12:55 +00001377 return memchr(PyByteArray_AS_STRING(self), (int) ival, Py_SIZE(self)) != NULL;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001378}
1379
1380
1381/* Matches the end (direction >= 0) or start (direction < 0) of self
1382 * against substr, using the start and end arguments. Returns
1383 * -1 on error, 0 if not found and 1 if found.
1384 */
1385Py_LOCAL(int)
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001386_bytearray_tailmatch(PyByteArrayObject *self, PyObject *substr, Py_ssize_t start,
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001387 Py_ssize_t end, int direction)
1388{
1389 Py_ssize_t len = PyByteArray_GET_SIZE(self);
1390 const char* str;
1391 Py_buffer vsubstr;
1392 int rv = 0;
1393
1394 str = PyByteArray_AS_STRING(self);
1395
Serhiy Storchaka4fdb6842015-02-03 01:21:08 +02001396 if (PyObject_GetBuffer(substr, &vsubstr, PyBUF_SIMPLE) != 0)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001397 return -1;
1398
Antoine Pitrouf2c54842010-01-13 08:07:53 +00001399 ADJUST_INDICES(start, end, len);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001400
1401 if (direction < 0) {
1402 /* startswith */
1403 if (start+vsubstr.len > len) {
1404 goto done;
1405 }
1406 } else {
1407 /* endswith */
1408 if (end-start < vsubstr.len || start > len) {
1409 goto done;
1410 }
1411
1412 if (end-vsubstr.len > start)
1413 start = end - vsubstr.len;
1414 }
1415 if (end-start >= vsubstr.len)
1416 rv = ! memcmp(str+start, vsubstr.buf, vsubstr.len);
1417
1418done:
Martin v. Löwis423be952008-08-13 15:53:07 +00001419 PyBuffer_Release(&vsubstr);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001420 return rv;
1421}
1422
1423
1424PyDoc_STRVAR(startswith__doc__,
Georg Brandl17cb8a82008-05-30 08:20:09 +00001425"B.startswith(prefix[, start[, end]]) -> bool\n\
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001426\n\
1427Return True if B starts with the specified prefix, False otherwise.\n\
1428With optional start, test B beginning at that position.\n\
1429With optional end, stop comparing B at that position.\n\
Ezio Melottiba42fd52011-04-26 06:09:45 +03001430prefix can also be a tuple of bytes to try.");
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001431
1432static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001433bytearray_startswith(PyByteArrayObject *self, PyObject *args)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001434{
1435 Py_ssize_t start = 0;
1436 Py_ssize_t end = PY_SSIZE_T_MAX;
1437 PyObject *subobj;
1438 int result;
1439
Jesus Ceaac451502011-04-20 17:09:23 +02001440 if (!stringlib_parse_args_finds("startswith", args, &subobj, &start, &end))
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001441 return NULL;
1442 if (PyTuple_Check(subobj)) {
1443 Py_ssize_t i;
1444 for (i = 0; i < PyTuple_GET_SIZE(subobj); i++) {
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001445 result = _bytearray_tailmatch(self,
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001446 PyTuple_GET_ITEM(subobj, i),
1447 start, end, -1);
1448 if (result == -1)
1449 return NULL;
1450 else if (result) {
1451 Py_RETURN_TRUE;
1452 }
1453 }
1454 Py_RETURN_FALSE;
1455 }
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001456 result = _bytearray_tailmatch(self, subobj, start, end, -1);
Ezio Melottiba42fd52011-04-26 06:09:45 +03001457 if (result == -1) {
1458 if (PyErr_ExceptionMatches(PyExc_TypeError))
1459 PyErr_Format(PyExc_TypeError, "startswith first arg must be bytes "
1460 "or a tuple of bytes, not %s", Py_TYPE(subobj)->tp_name);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001461 return NULL;
Ezio Melottiba42fd52011-04-26 06:09:45 +03001462 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001463 else
1464 return PyBool_FromLong(result);
1465}
1466
1467PyDoc_STRVAR(endswith__doc__,
Georg Brandl17cb8a82008-05-30 08:20:09 +00001468"B.endswith(suffix[, start[, end]]) -> bool\n\
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001469\n\
1470Return True if B ends with the specified suffix, False otherwise.\n\
1471With optional start, test B beginning at that position.\n\
1472With optional end, stop comparing B at that position.\n\
Ezio Melottiba42fd52011-04-26 06:09:45 +03001473suffix can also be a tuple of bytes to try.");
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001474
1475static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001476bytearray_endswith(PyByteArrayObject *self, PyObject *args)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001477{
1478 Py_ssize_t start = 0;
1479 Py_ssize_t end = PY_SSIZE_T_MAX;
1480 PyObject *subobj;
1481 int result;
1482
Jesus Ceaac451502011-04-20 17:09:23 +02001483 if (!stringlib_parse_args_finds("endswith", args, &subobj, &start, &end))
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001484 return NULL;
1485 if (PyTuple_Check(subobj)) {
1486 Py_ssize_t i;
1487 for (i = 0; i < PyTuple_GET_SIZE(subobj); i++) {
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001488 result = _bytearray_tailmatch(self,
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001489 PyTuple_GET_ITEM(subobj, i),
1490 start, end, +1);
1491 if (result == -1)
1492 return NULL;
1493 else if (result) {
1494 Py_RETURN_TRUE;
1495 }
1496 }
1497 Py_RETURN_FALSE;
1498 }
Benjamin Peterson153c70f2009-04-18 15:42:12 +00001499 result = _bytearray_tailmatch(self, subobj, start, end, +1);
Ezio Melottiba42fd52011-04-26 06:09:45 +03001500 if (result == -1) {
1501 if (PyErr_ExceptionMatches(PyExc_TypeError))
1502 PyErr_Format(PyExc_TypeError, "endswith first arg must be bytes or "
1503 "a tuple of bytes, not %s", Py_TYPE(subobj)->tp_name);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001504 return NULL;
Ezio Melottiba42fd52011-04-26 06:09:45 +03001505 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001506 else
1507 return PyBool_FromLong(result);
1508}
1509
1510
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001511/*[clinic input]
1512bytearray.translate
1513
1514 self: self(type="PyByteArrayObject *")
1515 table: object
1516 Translation table, which must be a bytes object of length 256.
1517 [
1518 deletechars: object
1519 ]
1520 /
1521
1522Return a copy with each character mapped by the given translation table.
1523
1524All characters occurring in the optional argument deletechars are removed.
1525The remaining characters are mapped through the given translation table.
1526[clinic start generated code]*/
1527
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001528static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04001529bytearray_translate_impl(PyByteArrayObject *self, PyObject *table,
1530 int group_right_1, PyObject *deletechars)
1531/*[clinic end generated code: output=2bebc86a9a1ff083 input=b749ad85f4860824]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001532{
Antoine Pitrou9ed5f272013-08-13 20:18:52 +02001533 char *input, *output;
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001534 const char *table_chars;
Antoine Pitrou9ed5f272013-08-13 20:18:52 +02001535 Py_ssize_t i, c;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001536 PyObject *input_obj = (PyObject*)self;
1537 const char *output_start;
1538 Py_ssize_t inlen;
Georg Brandlccc47b62008-12-28 11:44:14 +00001539 PyObject *result = NULL;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001540 int trans_table[256];
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001541 Py_buffer vtable, vdel;
1542
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001543 if (table == Py_None) {
1544 table_chars = NULL;
Georg Brandlccc47b62008-12-28 11:44:14 +00001545 table = NULL;
Serhiy Storchaka3dd3e262015-02-03 01:25:42 +02001546 } else if (PyObject_GetBuffer(table, &vtable, PyBUF_SIMPLE) != 0) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001547 return NULL;
Georg Brandlccc47b62008-12-28 11:44:14 +00001548 } else {
1549 if (vtable.len != 256) {
1550 PyErr_SetString(PyExc_ValueError,
1551 "translation table must be 256 characters long");
Georg Brandl953152f2009-07-22 12:03:59 +00001552 PyBuffer_Release(&vtable);
1553 return NULL;
Georg Brandlccc47b62008-12-28 11:44:14 +00001554 }
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001555 table_chars = (const char*)vtable.buf;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001556 }
1557
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001558 if (deletechars != NULL) {
Serhiy Storchaka3dd3e262015-02-03 01:25:42 +02001559 if (PyObject_GetBuffer(deletechars, &vdel, PyBUF_SIMPLE) != 0) {
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001560 if (table != NULL)
Georg Brandl953152f2009-07-22 12:03:59 +00001561 PyBuffer_Release(&vtable);
1562 return NULL;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001563 }
1564 }
1565 else {
1566 vdel.buf = NULL;
1567 vdel.len = 0;
1568 }
1569
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001570 inlen = PyByteArray_GET_SIZE(input_obj);
1571 result = PyByteArray_FromStringAndSize((char *)NULL, inlen);
1572 if (result == NULL)
1573 goto done;
1574 output_start = output = PyByteArray_AsString(result);
1575 input = PyByteArray_AS_STRING(input_obj);
1576
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001577 if (vdel.len == 0 && table_chars != NULL) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001578 /* If no deletions are required, use faster code */
1579 for (i = inlen; --i >= 0; ) {
1580 c = Py_CHARMASK(*input++);
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001581 *output++ = table_chars[c];
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001582 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001583 goto done;
1584 }
Georg Brandlccc47b62008-12-28 11:44:14 +00001585
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001586 if (table_chars == NULL) {
Georg Brandlccc47b62008-12-28 11:44:14 +00001587 for (i = 0; i < 256; i++)
1588 trans_table[i] = Py_CHARMASK(i);
1589 } else {
1590 for (i = 0; i < 256; i++)
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001591 trans_table[i] = Py_CHARMASK(table_chars[i]);
Georg Brandlccc47b62008-12-28 11:44:14 +00001592 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001593
1594 for (i = 0; i < vdel.len; i++)
1595 trans_table[(int) Py_CHARMASK( ((unsigned char*)vdel.buf)[i] )] = -1;
1596
1597 for (i = inlen; --i >= 0; ) {
1598 c = Py_CHARMASK(*input++);
1599 if (trans_table[c] != -1)
1600 if (Py_CHARMASK(*output++ = (char)trans_table[c]) == c)
1601 continue;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001602 }
1603 /* Fix the size of the resulting string */
1604 if (inlen > 0)
Christian Heimesc731bbe2013-07-21 02:04:35 +02001605 if (PyByteArray_Resize(result, output - output_start) < 0) {
1606 Py_CLEAR(result);
1607 goto done;
1608 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001609
1610done:
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001611 if (table != NULL)
Georg Brandlccc47b62008-12-28 11:44:14 +00001612 PyBuffer_Release(&vtable);
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001613 if (deletechars != NULL)
Martin v. Löwis423be952008-08-13 15:53:07 +00001614 PyBuffer_Release(&vdel);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001615 return result;
1616}
1617
1618
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001619/*[clinic input]
1620
1621@staticmethod
1622bytearray.maketrans
1623
Serhiy Storchaka3dd3e262015-02-03 01:25:42 +02001624 frm: Py_buffer
1625 to: Py_buffer
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001626 /
1627
1628Return a translation table useable for the bytes or bytearray translate method.
1629
1630The returned table will be one where each byte in frm is mapped to the byte at
1631the same position in to.
1632
1633The bytes objects frm and to must be of the same length.
1634[clinic start generated code]*/
1635
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001636static PyObject *
Serhiy Storchaka3dd3e262015-02-03 01:25:42 +02001637bytearray_maketrans_impl(Py_buffer *frm, Py_buffer *to)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03001638/*[clinic end generated code: output=1df267d99f56b15e input=5925a81d2fbbf151]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02001639{
1640 return _Py_bytes_maketrans(frm, to);
Georg Brandlabc38772009-04-12 15:51:51 +00001641}
1642
1643
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001644/* find and count characters and substrings */
1645
1646#define findchar(target, target_len, c) \
1647 ((char *)memchr((const void *)(target), c, target_len))
1648
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001649
Benjamin Peterson0f3641c2008-11-19 22:05:52 +00001650/* Bytes ops must return a string, create a copy */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001651Py_LOCAL(PyByteArrayObject *)
1652return_self(PyByteArrayObject *self)
1653{
Georg Brandl1e7217d2008-05-30 12:02:38 +00001654 /* always return a new bytearray */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001655 return (PyByteArrayObject *)PyByteArray_FromStringAndSize(
1656 PyByteArray_AS_STRING(self),
1657 PyByteArray_GET_SIZE(self));
1658}
1659
1660Py_LOCAL_INLINE(Py_ssize_t)
1661countchar(const char *target, Py_ssize_t target_len, char c, Py_ssize_t maxcount)
1662{
1663 Py_ssize_t count=0;
1664 const char *start=target;
1665 const char *end=target+target_len;
1666
1667 while ( (start=findchar(start, end-start, c)) != NULL ) {
1668 count++;
1669 if (count >= maxcount)
1670 break;
1671 start += 1;
1672 }
1673 return count;
1674}
1675
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001676
1677/* Algorithms for different cases of string replacement */
1678
1679/* len(self)>=1, from="", len(to)>=1, maxcount>=1 */
1680Py_LOCAL(PyByteArrayObject *)
1681replace_interleave(PyByteArrayObject *self,
1682 const char *to_s, Py_ssize_t to_len,
1683 Py_ssize_t maxcount)
1684{
1685 char *self_s, *result_s;
1686 Py_ssize_t self_len, result_len;
Mark Dickinsoncf940c72010-08-10 18:35:01 +00001687 Py_ssize_t count, i;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001688 PyByteArrayObject *result;
1689
1690 self_len = PyByteArray_GET_SIZE(self);
1691
Mark Dickinsoncf940c72010-08-10 18:35:01 +00001692 /* 1 at the end plus 1 after every character;
1693 count = min(maxcount, self_len + 1) */
1694 if (maxcount <= self_len)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001695 count = maxcount;
Mark Dickinsoncf940c72010-08-10 18:35:01 +00001696 else
1697 /* Can't overflow: self_len + 1 <= maxcount <= PY_SSIZE_T_MAX. */
1698 count = self_len + 1;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001699
1700 /* Check for overflow */
1701 /* result_len = count * to_len + self_len; */
Mark Dickinsoncf940c72010-08-10 18:35:01 +00001702 assert(count > 0);
1703 if (to_len > (PY_SSIZE_T_MAX - self_len) / count) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001704 PyErr_SetString(PyExc_OverflowError,
1705 "replace string is too long");
1706 return NULL;
1707 }
Mark Dickinsoncf940c72010-08-10 18:35:01 +00001708 result_len = count * to_len + self_len;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001709
1710 if (! (result = (PyByteArrayObject *)
1711 PyByteArray_FromStringAndSize(NULL, result_len)) )
1712 return NULL;
1713
1714 self_s = PyByteArray_AS_STRING(self);
1715 result_s = PyByteArray_AS_STRING(result);
1716
1717 /* TODO: special case single character, which doesn't need memcpy */
1718
1719 /* Lay the first one down (guaranteed this will occur) */
1720 Py_MEMCPY(result_s, to_s, to_len);
1721 result_s += to_len;
1722 count -= 1;
1723
1724 for (i=0; i<count; i++) {
1725 *result_s++ = *self_s++;
1726 Py_MEMCPY(result_s, to_s, to_len);
1727 result_s += to_len;
1728 }
1729
1730 /* Copy the rest of the original string */
1731 Py_MEMCPY(result_s, self_s, self_len-i);
1732
1733 return result;
1734}
1735
1736/* Special case for deleting a single character */
1737/* len(self)>=1, len(from)==1, to="", maxcount>=1 */
1738Py_LOCAL(PyByteArrayObject *)
1739replace_delete_single_character(PyByteArrayObject *self,
1740 char from_c, Py_ssize_t maxcount)
1741{
1742 char *self_s, *result_s;
1743 char *start, *next, *end;
1744 Py_ssize_t self_len, result_len;
1745 Py_ssize_t count;
1746 PyByteArrayObject *result;
1747
1748 self_len = PyByteArray_GET_SIZE(self);
1749 self_s = PyByteArray_AS_STRING(self);
1750
1751 count = countchar(self_s, self_len, from_c, maxcount);
1752 if (count == 0) {
1753 return return_self(self);
1754 }
1755
1756 result_len = self_len - count; /* from_len == 1 */
1757 assert(result_len>=0);
1758
1759 if ( (result = (PyByteArrayObject *)
1760 PyByteArray_FromStringAndSize(NULL, result_len)) == NULL)
1761 return NULL;
1762 result_s = PyByteArray_AS_STRING(result);
1763
1764 start = self_s;
1765 end = self_s + self_len;
1766 while (count-- > 0) {
1767 next = findchar(start, end-start, from_c);
1768 if (next == NULL)
1769 break;
1770 Py_MEMCPY(result_s, start, next-start);
1771 result_s += (next-start);
1772 start = next+1;
1773 }
1774 Py_MEMCPY(result_s, start, end-start);
1775
1776 return result;
1777}
1778
1779/* len(self)>=1, len(from)>=2, to="", maxcount>=1 */
1780
1781Py_LOCAL(PyByteArrayObject *)
1782replace_delete_substring(PyByteArrayObject *self,
1783 const char *from_s, Py_ssize_t from_len,
1784 Py_ssize_t maxcount)
1785{
1786 char *self_s, *result_s;
1787 char *start, *next, *end;
1788 Py_ssize_t self_len, result_len;
1789 Py_ssize_t count, offset;
1790 PyByteArrayObject *result;
1791
1792 self_len = PyByteArray_GET_SIZE(self);
1793 self_s = PyByteArray_AS_STRING(self);
1794
Antoine Pitrouf2c54842010-01-13 08:07:53 +00001795 count = stringlib_count(self_s, self_len,
1796 from_s, from_len,
1797 maxcount);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001798
1799 if (count == 0) {
1800 /* no matches */
1801 return return_self(self);
1802 }
1803
1804 result_len = self_len - (count * from_len);
1805 assert (result_len>=0);
1806
1807 if ( (result = (PyByteArrayObject *)
1808 PyByteArray_FromStringAndSize(NULL, result_len)) == NULL )
1809 return NULL;
1810
1811 result_s = PyByteArray_AS_STRING(result);
1812
1813 start = self_s;
1814 end = self_s + self_len;
1815 while (count-- > 0) {
Antoine Pitrouf2c54842010-01-13 08:07:53 +00001816 offset = stringlib_find(start, end-start,
1817 from_s, from_len,
1818 0);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001819 if (offset == -1)
1820 break;
1821 next = start + offset;
1822
1823 Py_MEMCPY(result_s, start, next-start);
1824
1825 result_s += (next-start);
1826 start = next+from_len;
1827 }
1828 Py_MEMCPY(result_s, start, end-start);
1829 return result;
1830}
1831
1832/* len(self)>=1, len(from)==len(to)==1, maxcount>=1 */
1833Py_LOCAL(PyByteArrayObject *)
1834replace_single_character_in_place(PyByteArrayObject *self,
1835 char from_c, char to_c,
1836 Py_ssize_t maxcount)
1837{
Antoine Pitroud1188562010-06-09 16:38:55 +00001838 char *self_s, *result_s, *start, *end, *next;
1839 Py_ssize_t self_len;
1840 PyByteArrayObject *result;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001841
Antoine Pitroud1188562010-06-09 16:38:55 +00001842 /* The result string will be the same size */
1843 self_s = PyByteArray_AS_STRING(self);
1844 self_len = PyByteArray_GET_SIZE(self);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001845
Antoine Pitroud1188562010-06-09 16:38:55 +00001846 next = findchar(self_s, self_len, from_c);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001847
Antoine Pitroud1188562010-06-09 16:38:55 +00001848 if (next == NULL) {
1849 /* No matches; return the original bytes */
1850 return return_self(self);
1851 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001852
Antoine Pitroud1188562010-06-09 16:38:55 +00001853 /* Need to make a new bytes */
1854 result = (PyByteArrayObject *) PyByteArray_FromStringAndSize(NULL, self_len);
1855 if (result == NULL)
1856 return NULL;
1857 result_s = PyByteArray_AS_STRING(result);
1858 Py_MEMCPY(result_s, self_s, self_len);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001859
Antoine Pitroud1188562010-06-09 16:38:55 +00001860 /* change everything in-place, starting with this one */
1861 start = result_s + (next-self_s);
1862 *start = to_c;
1863 start++;
1864 end = result_s + self_len;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001865
Antoine Pitroud1188562010-06-09 16:38:55 +00001866 while (--maxcount > 0) {
1867 next = findchar(start, end-start, from_c);
1868 if (next == NULL)
1869 break;
1870 *next = to_c;
1871 start = next+1;
1872 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001873
Antoine Pitroud1188562010-06-09 16:38:55 +00001874 return result;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001875}
1876
1877/* len(self)>=1, len(from)==len(to)>=2, maxcount>=1 */
1878Py_LOCAL(PyByteArrayObject *)
1879replace_substring_in_place(PyByteArrayObject *self,
1880 const char *from_s, Py_ssize_t from_len,
1881 const char *to_s, Py_ssize_t to_len,
1882 Py_ssize_t maxcount)
1883{
1884 char *result_s, *start, *end;
1885 char *self_s;
1886 Py_ssize_t self_len, offset;
1887 PyByteArrayObject *result;
1888
1889 /* The result bytes will be the same size */
1890
1891 self_s = PyByteArray_AS_STRING(self);
1892 self_len = PyByteArray_GET_SIZE(self);
1893
Antoine Pitrouf2c54842010-01-13 08:07:53 +00001894 offset = stringlib_find(self_s, self_len,
1895 from_s, from_len,
1896 0);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001897 if (offset == -1) {
1898 /* No matches; return the original bytes */
1899 return return_self(self);
1900 }
1901
1902 /* Need to make a new bytes */
1903 result = (PyByteArrayObject *) PyByteArray_FromStringAndSize(NULL, self_len);
1904 if (result == NULL)
1905 return NULL;
1906 result_s = PyByteArray_AS_STRING(result);
1907 Py_MEMCPY(result_s, self_s, self_len);
1908
1909 /* change everything in-place, starting with this one */
1910 start = result_s + offset;
1911 Py_MEMCPY(start, to_s, from_len);
1912 start += from_len;
1913 end = result_s + self_len;
1914
1915 while ( --maxcount > 0) {
Antoine Pitrouf2c54842010-01-13 08:07:53 +00001916 offset = stringlib_find(start, end-start,
1917 from_s, from_len,
1918 0);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001919 if (offset==-1)
1920 break;
1921 Py_MEMCPY(start+offset, to_s, from_len);
1922 start += offset+from_len;
1923 }
1924
1925 return result;
1926}
1927
1928/* len(self)>=1, len(from)==1, len(to)>=2, maxcount>=1 */
1929Py_LOCAL(PyByteArrayObject *)
1930replace_single_character(PyByteArrayObject *self,
1931 char from_c,
1932 const char *to_s, Py_ssize_t to_len,
1933 Py_ssize_t maxcount)
1934{
1935 char *self_s, *result_s;
1936 char *start, *next, *end;
1937 Py_ssize_t self_len, result_len;
Mark Dickinsoncf940c72010-08-10 18:35:01 +00001938 Py_ssize_t count;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001939 PyByteArrayObject *result;
1940
1941 self_s = PyByteArray_AS_STRING(self);
1942 self_len = PyByteArray_GET_SIZE(self);
1943
1944 count = countchar(self_s, self_len, from_c, maxcount);
1945 if (count == 0) {
1946 /* no matches, return unchanged */
1947 return return_self(self);
1948 }
1949
1950 /* use the difference between current and new, hence the "-1" */
1951 /* result_len = self_len + count * (to_len-1) */
Mark Dickinsoncf940c72010-08-10 18:35:01 +00001952 assert(count > 0);
1953 if (to_len - 1 > (PY_SSIZE_T_MAX - self_len) / count) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001954 PyErr_SetString(PyExc_OverflowError, "replace bytes is too long");
1955 return NULL;
1956 }
Mark Dickinsoncf940c72010-08-10 18:35:01 +00001957 result_len = self_len + count * (to_len - 1);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00001958
1959 if ( (result = (PyByteArrayObject *)
1960 PyByteArray_FromStringAndSize(NULL, result_len)) == NULL)
1961 return NULL;
1962 result_s = PyByteArray_AS_STRING(result);
1963
1964 start = self_s;
1965 end = self_s + self_len;
1966 while (count-- > 0) {
1967 next = findchar(start, end-start, from_c);
1968 if (next == NULL)
1969 break;
1970
1971 if (next == start) {
1972 /* replace with the 'to' */
1973 Py_MEMCPY(result_s, to_s, to_len);
1974 result_s += to_len;
1975 start += 1;
1976 } else {
1977 /* copy the unchanged old then the 'to' */
1978 Py_MEMCPY(result_s, start, next-start);
1979 result_s += (next-start);
1980 Py_MEMCPY(result_s, to_s, to_len);
1981 result_s += to_len;
1982 start = next+1;
1983 }
1984 }
1985 /* Copy the remainder of the remaining bytes */
1986 Py_MEMCPY(result_s, start, end-start);
1987
1988 return result;
1989}
1990
1991/* len(self)>=1, len(from)>=2, len(to)>=2, maxcount>=1 */
1992Py_LOCAL(PyByteArrayObject *)
1993replace_substring(PyByteArrayObject *self,
1994 const char *from_s, Py_ssize_t from_len,
1995 const char *to_s, Py_ssize_t to_len,
1996 Py_ssize_t maxcount)
1997{
1998 char *self_s, *result_s;
1999 char *start, *next, *end;
2000 Py_ssize_t self_len, result_len;
Mark Dickinsoncf940c72010-08-10 18:35:01 +00002001 Py_ssize_t count, offset;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002002 PyByteArrayObject *result;
2003
2004 self_s = PyByteArray_AS_STRING(self);
2005 self_len = PyByteArray_GET_SIZE(self);
2006
Antoine Pitrouf2c54842010-01-13 08:07:53 +00002007 count = stringlib_count(self_s, self_len,
2008 from_s, from_len,
2009 maxcount);
2010
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002011 if (count == 0) {
2012 /* no matches, return unchanged */
2013 return return_self(self);
2014 }
2015
2016 /* Check for overflow */
2017 /* result_len = self_len + count * (to_len-from_len) */
Mark Dickinsoncf940c72010-08-10 18:35:01 +00002018 assert(count > 0);
2019 if (to_len - from_len > (PY_SSIZE_T_MAX - self_len) / count) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002020 PyErr_SetString(PyExc_OverflowError, "replace bytes is too long");
2021 return NULL;
2022 }
Mark Dickinsoncf940c72010-08-10 18:35:01 +00002023 result_len = self_len + count * (to_len - from_len);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002024
2025 if ( (result = (PyByteArrayObject *)
2026 PyByteArray_FromStringAndSize(NULL, result_len)) == NULL)
2027 return NULL;
2028 result_s = PyByteArray_AS_STRING(result);
2029
2030 start = self_s;
2031 end = self_s + self_len;
2032 while (count-- > 0) {
Antoine Pitrouf2c54842010-01-13 08:07:53 +00002033 offset = stringlib_find(start, end-start,
2034 from_s, from_len,
2035 0);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002036 if (offset == -1)
2037 break;
2038 next = start+offset;
2039 if (next == start) {
2040 /* replace with the 'to' */
2041 Py_MEMCPY(result_s, to_s, to_len);
2042 result_s += to_len;
2043 start += from_len;
2044 } else {
2045 /* copy the unchanged old then the 'to' */
2046 Py_MEMCPY(result_s, start, next-start);
2047 result_s += (next-start);
2048 Py_MEMCPY(result_s, to_s, to_len);
2049 result_s += to_len;
2050 start = next+from_len;
2051 }
2052 }
2053 /* Copy the remainder of the remaining bytes */
2054 Py_MEMCPY(result_s, start, end-start);
2055
2056 return result;
2057}
2058
2059
2060Py_LOCAL(PyByteArrayObject *)
2061replace(PyByteArrayObject *self,
2062 const char *from_s, Py_ssize_t from_len,
2063 const char *to_s, Py_ssize_t to_len,
2064 Py_ssize_t maxcount)
2065{
2066 if (maxcount < 0) {
2067 maxcount = PY_SSIZE_T_MAX;
2068 } else if (maxcount == 0 || PyByteArray_GET_SIZE(self) == 0) {
2069 /* nothing to do; return the original bytes */
2070 return return_self(self);
2071 }
2072
2073 if (maxcount == 0 ||
2074 (from_len == 0 && to_len == 0)) {
2075 /* nothing to do; return the original bytes */
2076 return return_self(self);
2077 }
2078
2079 /* Handle zero-length special cases */
2080
2081 if (from_len == 0) {
2082 /* insert the 'to' bytes everywhere. */
2083 /* >>> "Python".replace("", ".") */
2084 /* '.P.y.t.h.o.n.' */
2085 return replace_interleave(self, to_s, to_len, maxcount);
2086 }
2087
2088 /* Except for "".replace("", "A") == "A" there is no way beyond this */
2089 /* point for an empty self bytes to generate a non-empty bytes */
2090 /* Special case so the remaining code always gets a non-empty bytes */
2091 if (PyByteArray_GET_SIZE(self) == 0) {
2092 return return_self(self);
2093 }
2094
2095 if (to_len == 0) {
Georg Brandl17cb8a82008-05-30 08:20:09 +00002096 /* delete all occurrences of 'from' bytes */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002097 if (from_len == 1) {
2098 return replace_delete_single_character(
2099 self, from_s[0], maxcount);
2100 } else {
2101 return replace_delete_substring(self, from_s, from_len, maxcount);
2102 }
2103 }
2104
2105 /* Handle special case where both bytes have the same length */
2106
2107 if (from_len == to_len) {
2108 if (from_len == 1) {
2109 return replace_single_character_in_place(
2110 self,
2111 from_s[0],
2112 to_s[0],
2113 maxcount);
2114 } else {
2115 return replace_substring_in_place(
2116 self, from_s, from_len, to_s, to_len, maxcount);
2117 }
2118 }
2119
2120 /* Otherwise use the more generic algorithms */
2121 if (from_len == 1) {
2122 return replace_single_character(self, from_s[0],
2123 to_s, to_len, maxcount);
2124 } else {
2125 /* len('from')>=2, len('to')>=1 */
2126 return replace_substring(self, from_s, from_len, to_s, to_len, maxcount);
2127 }
2128}
2129
2130
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002131/*[clinic input]
2132bytearray.replace
2133
Serhiy Storchaka3dd3e262015-02-03 01:25:42 +02002134 old: Py_buffer
2135 new: Py_buffer
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002136 count: Py_ssize_t = -1
2137 Maximum number of occurrences to replace.
2138 -1 (the default value) means replace all occurrences.
2139 /
2140
2141Return a copy with all occurrences of substring old replaced by new.
2142
2143If the optional argument count is given, only the first count occurrences are
2144replaced.
2145[clinic start generated code]*/
2146
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002147static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04002148bytearray_replace_impl(PyByteArrayObject *self, Py_buffer *old,
2149 Py_buffer *new, Py_ssize_t count)
2150/*[clinic end generated code: output=d39884c4dc59412a input=aa379d988637c7fb]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002151{
Serhiy Storchaka3dd3e262015-02-03 01:25:42 +02002152 return (PyObject *)replace((PyByteArrayObject *) self,
2153 old->buf, old->len,
2154 new->buf, new->len, count);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002155}
2156
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002157/*[clinic input]
2158bytearray.split
2159
2160 sep: object = None
2161 The delimiter according which to split the bytearray.
2162 None (the default value) means split on ASCII whitespace characters
2163 (space, tab, return, newline, formfeed, vertical tab).
2164 maxsplit: Py_ssize_t = -1
2165 Maximum number of splits to do.
2166 -1 (the default value) means no limit.
2167
2168Return a list of the sections in the bytearray, using sep as the delimiter.
2169[clinic start generated code]*/
2170
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002171static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04002172bytearray_split_impl(PyByteArrayObject *self, PyObject *sep,
2173 Py_ssize_t maxsplit)
2174/*[clinic end generated code: output=833e2cf385d9a04d input=24f82669f41bf523]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002175{
2176 Py_ssize_t len = PyByteArray_GET_SIZE(self), n;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002177 const char *s = PyByteArray_AS_STRING(self), *sub;
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002178 PyObject *list;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002179 Py_buffer vsub;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002180
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002181 if (maxsplit < 0)
2182 maxsplit = PY_SSIZE_T_MAX;
2183
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002184 if (sep == Py_None)
Antoine Pitrouf2c54842010-01-13 08:07:53 +00002185 return stringlib_split_whitespace((PyObject*) self, s, len, maxsplit);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002186
Serhiy Storchaka3dd3e262015-02-03 01:25:42 +02002187 if (PyObject_GetBuffer(sep, &vsub, PyBUF_SIMPLE) != 0)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002188 return NULL;
2189 sub = vsub.buf;
2190 n = vsub.len;
2191
Antoine Pitrouf2c54842010-01-13 08:07:53 +00002192 list = stringlib_split(
2193 (PyObject*) self, s, len, sub, n, maxsplit
2194 );
Martin v. Löwis423be952008-08-13 15:53:07 +00002195 PyBuffer_Release(&vsub);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002196 return list;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002197}
2198
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002199/*[clinic input]
2200bytearray.partition
2201
2202 self: self(type="PyByteArrayObject *")
2203 sep: object
2204 /
2205
2206Partition the bytearray into three parts using the given separator.
2207
2208This will search for the separator sep in the bytearray. If the separator is
2209found, returns a 3-tuple containing the part before the separator, the
2210separator itself, and the part after it.
2211
2212If the separator is not found, returns a 3-tuple containing the original
2213bytearray object and two empty bytearray objects.
2214[clinic start generated code]*/
2215
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002216static PyObject *
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002217bytearray_partition(PyByteArrayObject *self, PyObject *sep)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002218/*[clinic end generated code: output=45d2525ddd35f957 input=7d7fe37b1696d506]*/
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002219{
2220 PyObject *bytesep, *result;
2221
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002222 bytesep = PyByteArray_FromObject(sep);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002223 if (! bytesep)
2224 return NULL;
2225
2226 result = stringlib_partition(
2227 (PyObject*) self,
2228 PyByteArray_AS_STRING(self), PyByteArray_GET_SIZE(self),
2229 bytesep,
2230 PyByteArray_AS_STRING(bytesep), PyByteArray_GET_SIZE(bytesep)
2231 );
2232
2233 Py_DECREF(bytesep);
Antoine Pitrouf2c54842010-01-13 08:07:53 +00002234 return result;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002235}
2236
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002237/*[clinic input]
2238bytearray.rpartition
2239
2240 self: self(type="PyByteArrayObject *")
2241 sep: object
2242 /
2243
2244Partition the bytes into three parts using the given separator.
2245
2246This will search for the separator sep in the bytearray, starting and the end.
2247If the separator is found, returns a 3-tuple containing the part before the
2248separator, the separator itself, and the part after it.
2249
2250If the separator is not found, returns a 3-tuple containing two empty bytearray
2251objects and the original bytearray object.
2252[clinic start generated code]*/
2253
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002254static PyObject *
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002255bytearray_rpartition(PyByteArrayObject *self, PyObject *sep)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002256/*[clinic end generated code: output=440de3c9426115e8 input=9b8cd540c1b75853]*/
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002257{
2258 PyObject *bytesep, *result;
2259
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002260 bytesep = PyByteArray_FromObject(sep);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002261 if (! bytesep)
2262 return NULL;
2263
2264 result = stringlib_rpartition(
2265 (PyObject*) self,
2266 PyByteArray_AS_STRING(self), PyByteArray_GET_SIZE(self),
2267 bytesep,
2268 PyByteArray_AS_STRING(bytesep), PyByteArray_GET_SIZE(bytesep)
2269 );
2270
2271 Py_DECREF(bytesep);
Antoine Pitrouf2c54842010-01-13 08:07:53 +00002272 return result;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002273}
2274
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002275/*[clinic input]
2276bytearray.rsplit = bytearray.split
2277
2278Return a list of the sections in the bytearray, using sep as the delimiter.
2279
2280Splitting is done starting at the end of the bytearray and working to the front.
2281[clinic start generated code]*/
2282
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002283static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04002284bytearray_rsplit_impl(PyByteArrayObject *self, PyObject *sep,
2285 Py_ssize_t maxsplit)
2286/*[clinic end generated code: output=a55e0b5a03cb6190 input=a68286e4dd692ffe]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002287{
2288 Py_ssize_t len = PyByteArray_GET_SIZE(self), n;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002289 const char *s = PyByteArray_AS_STRING(self), *sub;
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002290 PyObject *list;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002291 Py_buffer vsub;
2292
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002293 if (maxsplit < 0)
2294 maxsplit = PY_SSIZE_T_MAX;
2295
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002296 if (sep == Py_None)
Antoine Pitrouf2c54842010-01-13 08:07:53 +00002297 return stringlib_rsplit_whitespace((PyObject*) self, s, len, maxsplit);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002298
Serhiy Storchaka3dd3e262015-02-03 01:25:42 +02002299 if (PyObject_GetBuffer(sep, &vsub, PyBUF_SIMPLE) != 0)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002300 return NULL;
2301 sub = vsub.buf;
2302 n = vsub.len;
2303
Antoine Pitrouf2c54842010-01-13 08:07:53 +00002304 list = stringlib_rsplit(
2305 (PyObject*) self, s, len, sub, n, maxsplit
2306 );
Martin v. Löwis423be952008-08-13 15:53:07 +00002307 PyBuffer_Release(&vsub);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002308 return list;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002309}
2310
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002311/*[clinic input]
2312bytearray.reverse
2313
2314 self: self(type="PyByteArrayObject *")
2315
2316Reverse the order of the values in B in place.
2317[clinic start generated code]*/
2318
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002319static PyObject *
2320bytearray_reverse_impl(PyByteArrayObject *self)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002321/*[clinic end generated code: output=9f7616f29ab309d3 input=7933a499b8597bd1]*/
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002322{
2323 char swap, *head, *tail;
2324 Py_ssize_t i, j, n = Py_SIZE(self);
2325
2326 j = n / 2;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002327 head = PyByteArray_AS_STRING(self);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002328 tail = head + n - 1;
2329 for (i = 0; i < j; i++) {
2330 swap = *head;
2331 *head++ = *tail;
2332 *tail-- = swap;
2333 }
2334
2335 Py_RETURN_NONE;
2336}
2337
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002338
2339/*[python input]
2340class bytesvalue_converter(CConverter):
2341 type = 'int'
2342 converter = '_getbytevalue'
2343[python start generated code]*/
2344/*[python end generated code: output=da39a3ee5e6b4b0d input=29c2e7c26c212812]*/
2345
2346
2347/*[clinic input]
2348bytearray.insert
2349
2350 self: self(type="PyByteArrayObject *")
2351 index: Py_ssize_t
2352 The index where the value is to be inserted.
2353 item: bytesvalue
2354 The item to be inserted.
2355 /
2356
2357Insert a single item into the bytearray before the given index.
2358[clinic start generated code]*/
2359
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002360static PyObject *
2361bytearray_insert_impl(PyByteArrayObject *self, Py_ssize_t index, int item)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002362/*[clinic end generated code: output=76c775a70e7b07b7 input=833766836ba30e1e]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002363{
2364 Py_ssize_t n = Py_SIZE(self);
2365 char *buf;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002366
2367 if (n == PY_SSIZE_T_MAX) {
2368 PyErr_SetString(PyExc_OverflowError,
Mark Dickinson2b6705f2009-09-06 10:34:47 +00002369 "cannot add more objects to bytearray");
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002370 return NULL;
2371 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002372 if (PyByteArray_Resize((PyObject *)self, n + 1) < 0)
2373 return NULL;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002374 buf = PyByteArray_AS_STRING(self);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002375
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002376 if (index < 0) {
2377 index += n;
2378 if (index < 0)
2379 index = 0;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002380 }
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002381 if (index > n)
2382 index = n;
2383 memmove(buf + index + 1, buf + index, n - index);
2384 buf[index] = item;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002385
2386 Py_RETURN_NONE;
2387}
2388
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002389/*[clinic input]
2390bytearray.append
2391
2392 self: self(type="PyByteArrayObject *")
2393 item: bytesvalue
2394 The item to be appended.
2395 /
2396
2397Append a single item to the end of the bytearray.
2398[clinic start generated code]*/
2399
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002400static PyObject *
2401bytearray_append_impl(PyByteArrayObject *self, int item)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002402/*[clinic end generated code: output=a154e19ed1886cb6 input=ae56ea87380407cc]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002403{
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002404 Py_ssize_t n = Py_SIZE(self);
2405
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002406 if (n == PY_SSIZE_T_MAX) {
2407 PyErr_SetString(PyExc_OverflowError,
Mark Dickinson2b6705f2009-09-06 10:34:47 +00002408 "cannot add more objects to bytearray");
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002409 return NULL;
2410 }
2411 if (PyByteArray_Resize((PyObject *)self, n + 1) < 0)
2412 return NULL;
2413
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002414 PyByteArray_AS_STRING(self)[n] = item;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002415
2416 Py_RETURN_NONE;
2417}
2418
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002419/*[clinic input]
2420bytearray.extend
2421
2422 self: self(type="PyByteArrayObject *")
2423 iterable_of_ints: object
2424 The iterable of items to append.
2425 /
2426
2427Append all the items from the iterator or sequence to the end of the bytearray.
2428[clinic start generated code]*/
2429
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002430static PyObject *
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002431bytearray_extend(PyByteArrayObject *self, PyObject *iterable_of_ints)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002432/*[clinic end generated code: output=98155dbe249170b1 input=ce83a5d75b70d850]*/
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002433{
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002434 PyObject *it, *item, *bytearray_obj;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002435 Py_ssize_t buf_size = 0, len = 0;
2436 int value;
2437 char *buf;
2438
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002439 /* bytearray_setslice code only accepts something supporting PEP 3118. */
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002440 if (PyObject_CheckBuffer(iterable_of_ints)) {
2441 if (bytearray_setslice(self, Py_SIZE(self), Py_SIZE(self), iterable_of_ints) == -1)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002442 return NULL;
2443
2444 Py_RETURN_NONE;
2445 }
2446
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002447 it = PyObject_GetIter(iterable_of_ints);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002448 if (it == NULL)
2449 return NULL;
2450
Ezio Melotti42da6632011-03-15 05:18:48 +02002451 /* Try to determine the length of the argument. 32 is arbitrary. */
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002452 buf_size = PyObject_LengthHint(iterable_of_ints, 32);
Benjamin Petersonef3e4c22009-04-11 19:48:14 +00002453 if (buf_size == -1) {
2454 Py_DECREF(it);
2455 return NULL;
2456 }
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002457
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002458 bytearray_obj = PyByteArray_FromStringAndSize(NULL, buf_size);
Antoine Pitrou58bb82e2012-04-01 16:05:46 +02002459 if (bytearray_obj == NULL) {
2460 Py_DECREF(it);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002461 return NULL;
Antoine Pitrou58bb82e2012-04-01 16:05:46 +02002462 }
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002463 buf = PyByteArray_AS_STRING(bytearray_obj);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002464
2465 while ((item = PyIter_Next(it)) != NULL) {
2466 if (! _getbytevalue(item, &value)) {
2467 Py_DECREF(item);
2468 Py_DECREF(it);
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002469 Py_DECREF(bytearray_obj);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002470 return NULL;
2471 }
2472 buf[len++] = value;
2473 Py_DECREF(item);
2474
2475 if (len >= buf_size) {
2476 buf_size = len + (len >> 1) + 1;
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002477 if (PyByteArray_Resize((PyObject *)bytearray_obj, buf_size) < 0) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002478 Py_DECREF(it);
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002479 Py_DECREF(bytearray_obj);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002480 return NULL;
2481 }
2482 /* Recompute the `buf' pointer, since the resizing operation may
2483 have invalidated it. */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002484 buf = PyByteArray_AS_STRING(bytearray_obj);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002485 }
2486 }
2487 Py_DECREF(it);
2488
2489 /* Resize down to exact size. */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002490 if (PyByteArray_Resize((PyObject *)bytearray_obj, len) < 0) {
2491 Py_DECREF(bytearray_obj);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002492 return NULL;
2493 }
2494
Antoine Pitrou58bb82e2012-04-01 16:05:46 +02002495 if (bytearray_setslice(self, Py_SIZE(self), Py_SIZE(self), bytearray_obj) == -1) {
2496 Py_DECREF(bytearray_obj);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002497 return NULL;
Antoine Pitrou58bb82e2012-04-01 16:05:46 +02002498 }
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002499 Py_DECREF(bytearray_obj);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002500
2501 Py_RETURN_NONE;
2502}
2503
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002504/*[clinic input]
2505bytearray.pop
2506
2507 self: self(type="PyByteArrayObject *")
2508 index: Py_ssize_t = -1
2509 The index from where to remove the item.
2510 -1 (the default value) means remove the last item.
2511 /
2512
2513Remove and return a single item from B.
2514
2515If no index argument is given, will pop the last item.
2516[clinic start generated code]*/
2517
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002518static PyObject *
2519bytearray_pop_impl(PyByteArrayObject *self, Py_ssize_t index)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002520/*[clinic end generated code: output=e0ccd401f8021da8 input=0797e6c0ca9d5a85]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002521{
2522 int value;
2523 Py_ssize_t n = Py_SIZE(self);
2524 char *buf;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002525
2526 if (n == 0) {
Eli Bendersky1bc4f192011-03-04 04:55:25 +00002527 PyErr_SetString(PyExc_IndexError,
2528 "pop from empty bytearray");
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002529 return NULL;
2530 }
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002531 if (index < 0)
2532 index += Py_SIZE(self);
2533 if (index < 0 || index >= Py_SIZE(self)) {
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002534 PyErr_SetString(PyExc_IndexError, "pop index out of range");
2535 return NULL;
2536 }
Antoine Pitrou5504e892008-12-06 21:27:53 +00002537 if (!_canresize(self))
2538 return NULL;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002539
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002540 buf = PyByteArray_AS_STRING(self);
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002541 value = buf[index];
2542 memmove(buf + index, buf + index + 1, n - index);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002543 if (PyByteArray_Resize((PyObject *)self, n - 1) < 0)
2544 return NULL;
2545
Mark Dickinson54a3db92009-09-06 10:19:23 +00002546 return PyLong_FromLong((unsigned char)value);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002547}
2548
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002549/*[clinic input]
2550bytearray.remove
2551
2552 self: self(type="PyByteArrayObject *")
2553 value: bytesvalue
2554 The value to remove.
2555 /
2556
2557Remove the first occurrence of a value in the bytearray.
2558[clinic start generated code]*/
2559
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002560static PyObject *
2561bytearray_remove_impl(PyByteArrayObject *self, int value)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002562/*[clinic end generated code: output=d659e37866709c13 input=47560b11fd856c24]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002563{
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002564 Py_ssize_t where, n = Py_SIZE(self);
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002565 char *buf = PyByteArray_AS_STRING(self);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002566
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002567 for (where = 0; where < n; where++) {
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002568 if (buf[where] == value)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002569 break;
2570 }
2571 if (where == n) {
Mark Dickinson2b6705f2009-09-06 10:34:47 +00002572 PyErr_SetString(PyExc_ValueError, "value not found in bytearray");
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002573 return NULL;
2574 }
Antoine Pitrou5504e892008-12-06 21:27:53 +00002575 if (!_canresize(self))
2576 return NULL;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002577
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002578 memmove(buf + where, buf + where + 1, n - where);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002579 if (PyByteArray_Resize((PyObject *)self, n - 1) < 0)
2580 return NULL;
2581
2582 Py_RETURN_NONE;
2583}
2584
2585/* XXX These two helpers could be optimized if argsize == 1 */
2586
2587static Py_ssize_t
Antoine Pitrou5b720752013-10-05 21:24:10 +02002588lstrip_helper(char *myptr, Py_ssize_t mysize,
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002589 void *argptr, Py_ssize_t argsize)
2590{
2591 Py_ssize_t i = 0;
Antoine Pitrou5b720752013-10-05 21:24:10 +02002592 while (i < mysize && memchr(argptr, (unsigned char) myptr[i], argsize))
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002593 i++;
2594 return i;
2595}
2596
2597static Py_ssize_t
Antoine Pitrou5b720752013-10-05 21:24:10 +02002598rstrip_helper(char *myptr, Py_ssize_t mysize,
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002599 void *argptr, Py_ssize_t argsize)
2600{
2601 Py_ssize_t i = mysize - 1;
Antoine Pitrou5b720752013-10-05 21:24:10 +02002602 while (i >= 0 && memchr(argptr, (unsigned char) myptr[i], argsize))
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002603 i--;
2604 return i + 1;
2605}
2606
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002607/*[clinic input]
2608bytearray.strip
2609
2610 bytes: object = None
2611 /
2612
2613Strip leading and trailing bytes contained in the argument.
2614
2615If the argument is omitted or None, strip leading and trailing ASCII whitespace.
2616[clinic start generated code]*/
2617
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002618static PyObject *
2619bytearray_strip_impl(PyByteArrayObject *self, PyObject *bytes)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002620/*[clinic end generated code: output=760412661a34ad5a input=ef7bb59b09c21d62]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002621{
2622 Py_ssize_t left, right, mysize, byteslen;
2623 char *myptr, *bytesptr;
2624 Py_buffer vbytes;
2625
2626 if (bytes == Py_None) {
2627 bytesptr = "\t\n\r\f\v ";
2628 byteslen = 6;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002629 }
2630 else {
Serhiy Storchaka3dd3e262015-02-03 01:25:42 +02002631 if (PyObject_GetBuffer(bytes, &vbytes, PyBUF_SIMPLE) != 0)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002632 return NULL;
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002633 bytesptr = (char *) vbytes.buf;
2634 byteslen = vbytes.len;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002635 }
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002636 myptr = PyByteArray_AS_STRING(self);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002637 mysize = Py_SIZE(self);
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002638 left = lstrip_helper(myptr, mysize, bytesptr, byteslen);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002639 if (left == mysize)
2640 right = left;
2641 else
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002642 right = rstrip_helper(myptr, mysize, bytesptr, byteslen);
2643 if (bytes != Py_None)
2644 PyBuffer_Release(&vbytes);
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002645 return PyByteArray_FromStringAndSize(myptr + left, right - left);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002646}
2647
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002648/*[clinic input]
2649bytearray.lstrip
2650
2651 bytes: object = None
2652 /
2653
2654Strip leading bytes contained in the argument.
2655
2656If the argument is omitted or None, strip leading ASCII whitespace.
2657[clinic start generated code]*/
2658
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002659static PyObject *
2660bytearray_lstrip_impl(PyByteArrayObject *self, PyObject *bytes)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002661/*[clinic end generated code: output=d005c9d0ab909e66 input=80843f975dd7c480]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002662{
2663 Py_ssize_t left, right, mysize, byteslen;
2664 char *myptr, *bytesptr;
2665 Py_buffer vbytes;
2666
2667 if (bytes == Py_None) {
2668 bytesptr = "\t\n\r\f\v ";
2669 byteslen = 6;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002670 }
2671 else {
Serhiy Storchaka3dd3e262015-02-03 01:25:42 +02002672 if (PyObject_GetBuffer(bytes, &vbytes, PyBUF_SIMPLE) != 0)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002673 return NULL;
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002674 bytesptr = (char *) vbytes.buf;
2675 byteslen = vbytes.len;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002676 }
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002677 myptr = PyByteArray_AS_STRING(self);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002678 mysize = Py_SIZE(self);
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002679 left = lstrip_helper(myptr, mysize, bytesptr, byteslen);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002680 right = mysize;
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002681 if (bytes != Py_None)
2682 PyBuffer_Release(&vbytes);
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002683 return PyByteArray_FromStringAndSize(myptr + left, right - left);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002684}
2685
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002686/*[clinic input]
2687bytearray.rstrip
2688
2689 bytes: object = None
2690 /
2691
2692Strip trailing bytes contained in the argument.
2693
2694If the argument is omitted or None, strip trailing ASCII whitespace.
2695[clinic start generated code]*/
2696
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002697static PyObject *
2698bytearray_rstrip_impl(PyByteArrayObject *self, PyObject *bytes)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002699/*[clinic end generated code: output=030e2fbd2f7276bd input=e728b994954cfd91]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002700{
2701 Py_ssize_t right, mysize, byteslen;
2702 char *myptr, *bytesptr;
2703 Py_buffer vbytes;
2704
2705 if (bytes == Py_None) {
2706 bytesptr = "\t\n\r\f\v ";
2707 byteslen = 6;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002708 }
2709 else {
Serhiy Storchaka3dd3e262015-02-03 01:25:42 +02002710 if (PyObject_GetBuffer(bytes, &vbytes, PyBUF_SIMPLE) != 0)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002711 return NULL;
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002712 bytesptr = (char *) vbytes.buf;
2713 byteslen = vbytes.len;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002714 }
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002715 myptr = PyByteArray_AS_STRING(self);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002716 mysize = Py_SIZE(self);
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002717 right = rstrip_helper(myptr, mysize, bytesptr, byteslen);
2718 if (bytes != Py_None)
2719 PyBuffer_Release(&vbytes);
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002720 return PyByteArray_FromStringAndSize(myptr, right);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002721}
2722
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002723/*[clinic input]
2724bytearray.decode
2725
2726 encoding: str(c_default="NULL") = 'utf-8'
2727 The encoding with which to decode the bytearray.
2728 errors: str(c_default="NULL") = 'strict'
2729 The error handling scheme to use for the handling of decoding errors.
2730 The default is 'strict' meaning that decoding errors raise a
2731 UnicodeDecodeError. Other possible values are 'ignore' and 'replace'
2732 as well as any other name registered with codecs.register_error that
2733 can handle UnicodeDecodeErrors.
2734
2735Decode the bytearray using the codec registered for encoding.
2736[clinic start generated code]*/
2737
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002738static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04002739bytearray_decode_impl(PyByteArrayObject *self, const char *encoding,
2740 const char *errors)
2741/*[clinic end generated code: output=f57d43f4a00b42c5 input=f28d8f903020257b]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002742{
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002743 if (encoding == NULL)
2744 encoding = PyUnicode_GetDefaultEncoding();
Martin v. Löwis0efea322014-07-27 17:29:17 +02002745 return PyUnicode_FromEncodedObject((PyObject*)self, encoding, errors);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002746}
2747
2748PyDoc_STRVAR(alloc_doc,
2749"B.__alloc__() -> int\n\
2750\n\
Georg Brandl17cb8a82008-05-30 08:20:09 +00002751Return the number of bytes actually allocated.");
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002752
2753static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002754bytearray_alloc(PyByteArrayObject *self)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002755{
2756 return PyLong_FromSsize_t(self->ob_alloc);
2757}
2758
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002759/*[clinic input]
2760bytearray.join
2761
2762 iterable_of_bytes: object
2763 /
2764
2765Concatenate any number of bytes/bytearray objects.
2766
2767The bytearray whose method is called is inserted in between each pair.
2768
2769The result is returned as a new bytearray object.
2770[clinic start generated code]*/
2771
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002772static PyObject *
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002773bytearray_join(PyByteArrayObject *self, PyObject *iterable_of_bytes)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002774/*[clinic end generated code: output=a8516370bf68ae08 input=aba6b1f9b30fcb8e]*/
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002775{
Martin v. Löwis0efea322014-07-27 17:29:17 +02002776 return stringlib_bytes_join((PyObject*)self, iterable_of_bytes);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002777}
2778
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002779/*[clinic input]
2780bytearray.splitlines
Antoine Pitrouf2c54842010-01-13 08:07:53 +00002781
Serhiy Storchaka8b2e8b62015-05-30 11:30:39 +03002782 keepends: int(c_default="0") = False
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002783
2784Return a list of the lines in the bytearray, breaking at line boundaries.
2785
2786Line breaks are not included in the resulting list unless keepends is given and
2787true.
2788[clinic start generated code]*/
2789
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002790static PyObject *
2791bytearray_splitlines_impl(PyByteArrayObject *self, int keepends)
Serhiy Storchaka8b2e8b62015-05-30 11:30:39 +03002792/*[clinic end generated code: output=4223c94b895f6ad9 input=8ccade941e5ea0bd]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002793{
Antoine Pitrouf2c54842010-01-13 08:07:53 +00002794 return stringlib_splitlines(
2795 (PyObject*) self, PyByteArray_AS_STRING(self),
2796 PyByteArray_GET_SIZE(self), keepends
2797 );
2798}
2799
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002800static int
Victor Stinner6430fd52011-09-29 04:02:13 +02002801hex_digit_to_int(Py_UCS4 c)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002802{
2803 if (c >= 128)
2804 return -1;
Eric Smith6dc46f52009-04-27 20:39:49 +00002805 if (Py_ISDIGIT(c))
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002806 return c - '0';
2807 else {
Eric Smith6dc46f52009-04-27 20:39:49 +00002808 if (Py_ISUPPER(c))
2809 c = Py_TOLOWER(c);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002810 if (c >= 'a' && c <= 'f')
2811 return c - 'a' + 10;
2812 }
2813 return -1;
2814}
2815
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002816/*[clinic input]
2817@classmethod
2818bytearray.fromhex
2819
2820 cls: self(type="PyObject*")
2821 string: unicode
2822 /
2823
2824Create a bytearray object from a string of hexadecimal numbers.
2825
2826Spaces between two numbers are accepted.
2827Example: bytearray.fromhex('B9 01EF') -> bytearray(b'\\xb9\\x01\\xef')
2828[clinic start generated code]*/
2829
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002830static PyObject *
2831bytearray_fromhex_impl(PyObject*cls, PyObject *string)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002832/*[clinic end generated code: output=df3da60129b3700c input=907bbd2d34d9367a]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002833{
2834 PyObject *newbytes;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002835 char *buf;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002836 Py_ssize_t hexlen, byteslen, i, j;
2837 int top, bot;
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02002838 void *data;
2839 unsigned int kind;
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002840
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002841 assert(PyUnicode_Check(string));
2842 if (PyUnicode_READY(string))
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002843 return NULL;
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002844 kind = PyUnicode_KIND(string);
2845 data = PyUnicode_DATA(string);
2846 hexlen = PyUnicode_GET_LENGTH(string);
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02002847
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002848 byteslen = hexlen/2; /* This overestimates if there are spaces */
2849 newbytes = PyByteArray_FromStringAndSize(NULL, byteslen);
2850 if (!newbytes)
2851 return NULL;
2852 buf = PyByteArray_AS_STRING(newbytes);
2853 for (i = j = 0; i < hexlen; i += 2) {
2854 /* skip over spaces in the input */
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02002855 while (PyUnicode_READ(kind, data, i) == ' ')
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002856 i++;
2857 if (i >= hexlen)
2858 break;
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02002859 top = hex_digit_to_int(PyUnicode_READ(kind, data, i));
2860 bot = hex_digit_to_int(PyUnicode_READ(kind, data, i+1));
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002861 if (top == -1 || bot == -1) {
2862 PyErr_Format(PyExc_ValueError,
2863 "non-hexadecimal number found in "
2864 "fromhex() arg at position %zd", i);
2865 goto error;
2866 }
2867 buf[j++] = (top << 4) + bot;
2868 }
2869 if (PyByteArray_Resize(newbytes, j) < 0)
2870 goto error;
2871 return newbytes;
2872
2873 error:
2874 Py_DECREF(newbytes);
2875 return NULL;
2876}
2877
Gregory P. Smith8cb65692015-04-25 23:22:26 +00002878PyDoc_STRVAR(hex__doc__,
2879"B.hex() -> string\n\
2880\n\
2881Create a string of hexadecimal numbers from a bytearray object.\n\
2882Example: bytearray([0xb9, 0x01, 0xef]).hex() -> 'b901ef'.");
2883
2884static PyObject *
2885bytearray_hex(PyBytesObject *self)
2886{
2887 char* argbuf = PyByteArray_AS_STRING(self);
2888 Py_ssize_t arglen = PyByteArray_GET_SIZE(self);
2889 return _Py_strhex(argbuf, arglen);
2890}
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002891
2892static PyObject *
Antoine Pitroub0e1f8b2011-12-05 20:40:08 +01002893_common_reduce(PyByteArrayObject *self, int proto)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002894{
Antoine Pitroub0e1f8b2011-12-05 20:40:08 +01002895 PyObject *dict;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02002896 _Py_IDENTIFIER(__dict__);
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002897 char *buf;
Martin v. Löwis1ee1b6f2011-10-10 18:11:30 +02002898
Martin v. Löwis1ee1b6f2011-10-10 18:11:30 +02002899 dict = _PyObject_GetAttrId((PyObject *)self, &PyId___dict__);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002900 if (dict == NULL) {
2901 PyErr_Clear();
2902 dict = Py_None;
2903 Py_INCREF(dict);
2904 }
2905
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002906 buf = PyByteArray_AS_STRING(self);
Antoine Pitroub0e1f8b2011-12-05 20:40:08 +01002907 if (proto < 3) {
2908 /* use str based reduction for backwards compatibility with Python 2.x */
2909 PyObject *latin1;
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002910 if (Py_SIZE(self))
2911 latin1 = PyUnicode_DecodeLatin1(buf, Py_SIZE(self), NULL);
Antoine Pitroub0e1f8b2011-12-05 20:40:08 +01002912 else
2913 latin1 = PyUnicode_FromString("");
2914 return Py_BuildValue("(O(Ns)N)", Py_TYPE(self), latin1, "latin-1", dict);
2915 }
2916 else {
2917 /* use more efficient byte based reduction */
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02002918 if (Py_SIZE(self)) {
2919 return Py_BuildValue("(O(y#)N)", Py_TYPE(self), buf, Py_SIZE(self), dict);
Antoine Pitroub0e1f8b2011-12-05 20:40:08 +01002920 }
2921 else {
2922 return Py_BuildValue("(O()N)", Py_TYPE(self), dict);
2923 }
2924 }
2925}
2926
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002927/*[clinic input]
2928bytearray.__reduce__ as bytearray_reduce
2929
2930 self: self(type="PyByteArrayObject *")
2931
2932Return state information for pickling.
2933[clinic start generated code]*/
2934
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002935static PyObject *
2936bytearray_reduce_impl(PyByteArrayObject *self)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002937/*[clinic end generated code: output=52bf304086464cab input=fbb07de4d102a03a]*/
Antoine Pitroub0e1f8b2011-12-05 20:40:08 +01002938{
2939 return _common_reduce(self, 2);
2940}
2941
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002942/*[clinic input]
2943bytearray.__reduce_ex__ as bytearray_reduce_ex
2944
2945 self: self(type="PyByteArrayObject *")
2946 proto: int = 0
2947 /
2948
2949Return state information for pickling.
2950[clinic start generated code]*/
2951
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002952static PyObject *
2953bytearray_reduce_ex_impl(PyByteArrayObject *self, int proto)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002954/*[clinic end generated code: output=52eac33377197520 input=0e091a42ca6dbd91]*/
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002955{
Antoine Pitroub0e1f8b2011-12-05 20:40:08 +01002956 return _common_reduce(self, proto);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002957}
2958
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002959/*[clinic input]
2960bytearray.__sizeof__ as bytearray_sizeof
2961
2962 self: self(type="PyByteArrayObject *")
2963
2964Returns the size of the bytearray object in memory, in bytes.
2965[clinic start generated code]*/
2966
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02002967static PyObject *
2968bytearray_sizeof_impl(PyByteArrayObject *self)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002969/*[clinic end generated code: output=738abdd17951c427 input=6b23d305362b462b]*/
Robert Schuppeniesfbe94c52008-07-14 10:13:31 +00002970{
Benjamin Petersonef3e4c22009-04-11 19:48:14 +00002971 Py_ssize_t res;
Robert Schuppeniesfbe94c52008-07-14 10:13:31 +00002972
Benjamin Petersonef3e4c22009-04-11 19:48:14 +00002973 res = sizeof(PyByteArrayObject) + self->ob_alloc * sizeof(char);
2974 return PyLong_FromSsize_t(res);
Robert Schuppeniesfbe94c52008-07-14 10:13:31 +00002975}
2976
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002977static PySequenceMethods bytearray_as_sequence = {
2978 (lenfunc)bytearray_length, /* sq_length */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002979 (binaryfunc)PyByteArray_Concat, /* sq_concat */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002980 (ssizeargfunc)bytearray_repeat, /* sq_repeat */
2981 (ssizeargfunc)bytearray_getitem, /* sq_item */
2982 0, /* sq_slice */
2983 (ssizeobjargproc)bytearray_setitem, /* sq_ass_item */
2984 0, /* sq_ass_slice */
2985 (objobjproc)bytearray_contains, /* sq_contains */
2986 (binaryfunc)bytearray_iconcat, /* sq_inplace_concat */
2987 (ssizeargfunc)bytearray_irepeat, /* sq_inplace_repeat */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002988};
2989
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002990static PyMappingMethods bytearray_as_mapping = {
2991 (lenfunc)bytearray_length,
2992 (binaryfunc)bytearray_subscript,
2993 (objobjargproc)bytearray_ass_subscript,
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002994};
2995
Benjamin Peterson153c70f2009-04-18 15:42:12 +00002996static PyBufferProcs bytearray_as_buffer = {
2997 (getbufferproc)bytearray_getbuffer,
2998 (releasebufferproc)bytearray_releasebuffer,
Christian Heimes2c9c7a52008-05-26 13:42:13 +00002999};
3000
3001static PyMethodDef
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003002bytearray_methods[] = {
3003 {"__alloc__", (PyCFunction)bytearray_alloc, METH_NOARGS, alloc_doc},
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003004 BYTEARRAY_REDUCE_METHODDEF
3005 BYTEARRAY_REDUCE_EX_METHODDEF
3006 BYTEARRAY_SIZEOF_METHODDEF
3007 BYTEARRAY_APPEND_METHODDEF
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003008 {"capitalize", (PyCFunction)stringlib_capitalize, METH_NOARGS,
3009 _Py_capitalize__doc__},
3010 {"center", (PyCFunction)stringlib_center, METH_VARARGS, center__doc__},
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003011 BYTEARRAY_CLEAR_METHODDEF
3012 BYTEARRAY_COPY_METHODDEF
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003013 {"count", (PyCFunction)bytearray_count, METH_VARARGS, count__doc__},
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003014 BYTEARRAY_DECODE_METHODDEF
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003015 {"endswith", (PyCFunction)bytearray_endswith, METH_VARARGS, endswith__doc__},
Ezio Melotti745d54d2013-11-16 19:10:57 +02003016 {"expandtabs", (PyCFunction)stringlib_expandtabs, METH_VARARGS | METH_KEYWORDS,
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003017 expandtabs__doc__},
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003018 BYTEARRAY_EXTEND_METHODDEF
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003019 {"find", (PyCFunction)bytearray_find, METH_VARARGS, find__doc__},
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003020 BYTEARRAY_FROMHEX_METHODDEF
Gregory P. Smith8cb65692015-04-25 23:22:26 +00003021 {"hex", (PyCFunction)bytearray_hex, METH_NOARGS, hex__doc__},
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003022 {"index", (PyCFunction)bytearray_index, METH_VARARGS, index__doc__},
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003023 BYTEARRAY_INSERT_METHODDEF
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003024 {"isalnum", (PyCFunction)stringlib_isalnum, METH_NOARGS,
3025 _Py_isalnum__doc__},
3026 {"isalpha", (PyCFunction)stringlib_isalpha, METH_NOARGS,
3027 _Py_isalpha__doc__},
3028 {"isdigit", (PyCFunction)stringlib_isdigit, METH_NOARGS,
3029 _Py_isdigit__doc__},
3030 {"islower", (PyCFunction)stringlib_islower, METH_NOARGS,
3031 _Py_islower__doc__},
3032 {"isspace", (PyCFunction)stringlib_isspace, METH_NOARGS,
3033 _Py_isspace__doc__},
3034 {"istitle", (PyCFunction)stringlib_istitle, METH_NOARGS,
3035 _Py_istitle__doc__},
3036 {"isupper", (PyCFunction)stringlib_isupper, METH_NOARGS,
3037 _Py_isupper__doc__},
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003038 BYTEARRAY_JOIN_METHODDEF
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003039 {"ljust", (PyCFunction)stringlib_ljust, METH_VARARGS, ljust__doc__},
3040 {"lower", (PyCFunction)stringlib_lower, METH_NOARGS, _Py_lower__doc__},
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003041 BYTEARRAY_LSTRIP_METHODDEF
3042 BYTEARRAY_MAKETRANS_METHODDEF
3043 BYTEARRAY_PARTITION_METHODDEF
3044 BYTEARRAY_POP_METHODDEF
3045 BYTEARRAY_REMOVE_METHODDEF
3046 BYTEARRAY_REPLACE_METHODDEF
3047 BYTEARRAY_REVERSE_METHODDEF
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003048 {"rfind", (PyCFunction)bytearray_rfind, METH_VARARGS, rfind__doc__},
3049 {"rindex", (PyCFunction)bytearray_rindex, METH_VARARGS, rindex__doc__},
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003050 {"rjust", (PyCFunction)stringlib_rjust, METH_VARARGS, rjust__doc__},
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003051 BYTEARRAY_RPARTITION_METHODDEF
3052 BYTEARRAY_RSPLIT_METHODDEF
3053 BYTEARRAY_RSTRIP_METHODDEF
3054 BYTEARRAY_SPLIT_METHODDEF
3055 BYTEARRAY_SPLITLINES_METHODDEF
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003056 {"startswith", (PyCFunction)bytearray_startswith, METH_VARARGS ,
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003057 startswith__doc__},
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003058 BYTEARRAY_STRIP_METHODDEF
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003059 {"swapcase", (PyCFunction)stringlib_swapcase, METH_NOARGS,
3060 _Py_swapcase__doc__},
3061 {"title", (PyCFunction)stringlib_title, METH_NOARGS, _Py_title__doc__},
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003062 BYTEARRAY_TRANSLATE_METHODDEF
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003063 {"upper", (PyCFunction)stringlib_upper, METH_NOARGS, _Py_upper__doc__},
3064 {"zfill", (PyCFunction)stringlib_zfill, METH_VARARGS, zfill__doc__},
3065 {NULL}
3066};
3067
Ethan Furmanb95b5612015-01-23 20:05:18 -08003068static PyObject *
3069bytearray_mod(PyObject *v, PyObject *w)
3070{
3071 if (!PyByteArray_Check(v))
3072 Py_RETURN_NOTIMPLEMENTED;
3073 return bytearray_format((PyByteArrayObject *)v, w);
3074}
3075
3076static PyNumberMethods bytearray_as_number = {
3077 0, /*nb_add*/
3078 0, /*nb_subtract*/
3079 0, /*nb_multiply*/
3080 bytearray_mod, /*nb_remainder*/
3081};
3082
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003083PyDoc_STRVAR(bytearray_doc,
Georg Brandl17cb8a82008-05-30 08:20:09 +00003084"bytearray(iterable_of_ints) -> bytearray\n\
3085bytearray(string, encoding[, errors]) -> bytearray\n\
Victor Stinnerbb2e9c42011-12-17 23:18:07 +01003086bytearray(bytes_or_buffer) -> mutable copy of bytes_or_buffer\n\
3087bytearray(int) -> bytes array of size given by the parameter initialized with null bytes\n\
3088bytearray() -> empty bytes array\n\
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003089\n\
3090Construct an mutable bytearray object from:\n\
3091 - an iterable yielding integers in range(256)\n\
3092 - a text string encoded using the specified encoding\n\
Victor Stinnerbb2e9c42011-12-17 23:18:07 +01003093 - a bytes or a buffer object\n\
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003094 - any object implementing the buffer API.\n\
Victor Stinnerbb2e9c42011-12-17 23:18:07 +01003095 - an integer");
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003096
3097
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003098static PyObject *bytearray_iter(PyObject *seq);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003099
3100PyTypeObject PyByteArray_Type = {
3101 PyVarObject_HEAD_INIT(&PyType_Type, 0)
3102 "bytearray",
3103 sizeof(PyByteArrayObject),
3104 0,
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003105 (destructor)bytearray_dealloc, /* tp_dealloc */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003106 0, /* tp_print */
3107 0, /* tp_getattr */
3108 0, /* tp_setattr */
Mark Dickinsone94c6792009-02-02 20:36:42 +00003109 0, /* tp_reserved */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003110 (reprfunc)bytearray_repr, /* tp_repr */
Ethan Furmanb95b5612015-01-23 20:05:18 -08003111 &bytearray_as_number, /* tp_as_number */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003112 &bytearray_as_sequence, /* tp_as_sequence */
3113 &bytearray_as_mapping, /* tp_as_mapping */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003114 0, /* tp_hash */
3115 0, /* tp_call */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003116 bytearray_str, /* tp_str */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003117 PyObject_GenericGetAttr, /* tp_getattro */
3118 0, /* tp_setattro */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003119 &bytearray_as_buffer, /* tp_as_buffer */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003120 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003121 bytearray_doc, /* tp_doc */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003122 0, /* tp_traverse */
3123 0, /* tp_clear */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003124 (richcmpfunc)bytearray_richcompare, /* tp_richcompare */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003125 0, /* tp_weaklistoffset */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003126 bytearray_iter, /* tp_iter */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003127 0, /* tp_iternext */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003128 bytearray_methods, /* tp_methods */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003129 0, /* tp_members */
3130 0, /* tp_getset */
3131 0, /* tp_base */
3132 0, /* tp_dict */
3133 0, /* tp_descr_get */
3134 0, /* tp_descr_set */
3135 0, /* tp_dictoffset */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003136 (initproc)bytearray_init, /* tp_init */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003137 PyType_GenericAlloc, /* tp_alloc */
3138 PyType_GenericNew, /* tp_new */
3139 PyObject_Del, /* tp_free */
3140};
3141
3142/*********************** Bytes Iterator ****************************/
3143
3144typedef struct {
3145 PyObject_HEAD
3146 Py_ssize_t it_index;
3147 PyByteArrayObject *it_seq; /* Set to NULL when iterator is exhausted */
3148} bytesiterobject;
3149
3150static void
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003151bytearrayiter_dealloc(bytesiterobject *it)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003152{
3153 _PyObject_GC_UNTRACK(it);
3154 Py_XDECREF(it->it_seq);
3155 PyObject_GC_Del(it);
3156}
3157
3158static int
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003159bytearrayiter_traverse(bytesiterobject *it, visitproc visit, void *arg)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003160{
3161 Py_VISIT(it->it_seq);
3162 return 0;
3163}
3164
3165static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003166bytearrayiter_next(bytesiterobject *it)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003167{
3168 PyByteArrayObject *seq;
3169 PyObject *item;
3170
3171 assert(it != NULL);
3172 seq = it->it_seq;
3173 if (seq == NULL)
3174 return NULL;
3175 assert(PyByteArray_Check(seq));
3176
3177 if (it->it_index < PyByteArray_GET_SIZE(seq)) {
3178 item = PyLong_FromLong(
Antoine Pitrou5df8a8a2013-10-05 21:12:18 +02003179 (unsigned char)PyByteArray_AS_STRING(seq)[it->it_index]);
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003180 if (item != NULL)
3181 ++it->it_index;
3182 return item;
3183 }
3184
3185 Py_DECREF(seq);
3186 it->it_seq = NULL;
3187 return NULL;
3188}
3189
3190static PyObject *
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00003191bytearrayiter_length_hint(bytesiterobject *it)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003192{
3193 Py_ssize_t len = 0;
3194 if (it->it_seq)
3195 len = PyByteArray_GET_SIZE(it->it_seq) - it->it_index;
3196 return PyLong_FromSsize_t(len);
3197}
3198
3199PyDoc_STRVAR(length_hint_doc,
3200 "Private method returning an estimate of len(list(it)).");
3201
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00003202static PyObject *
3203bytearrayiter_reduce(bytesiterobject *it)
3204{
3205 if (it->it_seq != NULL) {
Antoine Pitroua7013882012-04-05 00:04:20 +02003206 return Py_BuildValue("N(O)n", _PyObject_GetBuiltin("iter"),
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00003207 it->it_seq, it->it_index);
3208 } else {
3209 PyObject *u = PyUnicode_FromUnicode(NULL, 0);
3210 if (u == NULL)
3211 return NULL;
Antoine Pitroua7013882012-04-05 00:04:20 +02003212 return Py_BuildValue("N(N)", _PyObject_GetBuiltin("iter"), u);
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00003213 }
3214}
3215
3216static PyObject *
3217bytearrayiter_setstate(bytesiterobject *it, PyObject *state)
3218{
3219 Py_ssize_t index = PyLong_AsSsize_t(state);
3220 if (index == -1 && PyErr_Occurred())
3221 return NULL;
Kristján Valur Jónsson25dded02014-03-05 13:47:57 +00003222 if (it->it_seq != NULL) {
3223 if (index < 0)
3224 index = 0;
3225 else if (index > PyByteArray_GET_SIZE(it->it_seq))
3226 index = PyByteArray_GET_SIZE(it->it_seq); /* iterator exhausted */
3227 it->it_index = index;
3228 }
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00003229 Py_RETURN_NONE;
3230}
3231
3232PyDoc_STRVAR(setstate_doc, "Set state information for unpickling.");
3233
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003234static PyMethodDef bytearrayiter_methods[] = {
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00003235 {"__length_hint__", (PyCFunction)bytearrayiter_length_hint, METH_NOARGS,
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003236 length_hint_doc},
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00003237 {"__reduce__", (PyCFunction)bytearrayiter_reduce, METH_NOARGS,
Martin v. Löwis7252a6e2014-07-27 16:25:09 +02003238 bytearray_reduce__doc__},
Kristján Valur Jónsson31668b82012-04-03 10:49:41 +00003239 {"__setstate__", (PyCFunction)bytearrayiter_setstate, METH_O,
3240 setstate_doc},
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003241 {NULL, NULL} /* sentinel */
3242};
3243
3244PyTypeObject PyByteArrayIter_Type = {
3245 PyVarObject_HEAD_INIT(&PyType_Type, 0)
3246 "bytearray_iterator", /* tp_name */
3247 sizeof(bytesiterobject), /* tp_basicsize */
3248 0, /* tp_itemsize */
3249 /* methods */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003250 (destructor)bytearrayiter_dealloc, /* tp_dealloc */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003251 0, /* tp_print */
3252 0, /* tp_getattr */
3253 0, /* tp_setattr */
Mark Dickinsone94c6792009-02-02 20:36:42 +00003254 0, /* tp_reserved */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003255 0, /* tp_repr */
3256 0, /* tp_as_number */
3257 0, /* tp_as_sequence */
3258 0, /* tp_as_mapping */
3259 0, /* tp_hash */
3260 0, /* tp_call */
3261 0, /* tp_str */
3262 PyObject_GenericGetAttr, /* tp_getattro */
3263 0, /* tp_setattro */
3264 0, /* tp_as_buffer */
3265 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /* tp_flags */
3266 0, /* tp_doc */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003267 (traverseproc)bytearrayiter_traverse, /* tp_traverse */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003268 0, /* tp_clear */
3269 0, /* tp_richcompare */
3270 0, /* tp_weaklistoffset */
3271 PyObject_SelfIter, /* tp_iter */
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003272 (iternextfunc)bytearrayiter_next, /* tp_iternext */
3273 bytearrayiter_methods, /* tp_methods */
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003274 0,
3275};
3276
3277static PyObject *
Benjamin Peterson153c70f2009-04-18 15:42:12 +00003278bytearray_iter(PyObject *seq)
Christian Heimes2c9c7a52008-05-26 13:42:13 +00003279{
3280 bytesiterobject *it;
3281
3282 if (!PyByteArray_Check(seq)) {
3283 PyErr_BadInternalCall();
3284 return NULL;
3285 }
3286 it = PyObject_GC_New(bytesiterobject, &PyByteArrayIter_Type);
3287 if (it == NULL)
3288 return NULL;
3289 it->it_index = 0;
3290 Py_INCREF(seq);
3291 it->it_seq = (PyByteArrayObject *)seq;
3292 _PyObject_GC_TRACK(it);
3293 return (PyObject *)it;
3294}