Issue #5262: Fixed bug in next roll over time computation in TimedRotatingFileHandler.
[python.git] / Objects / bytearrayobject.c
blob5591847640d21ca0500a4540120bf15c3824b3d7
1 /* PyBytes (bytearray) implementation */
3 #define PY_SSIZE_T_CLEAN
4 #include "Python.h"
5 #include "structmember.h"
6 #include "bytes_methods.h"
8 static PyByteArrayObject *nullbytes = NULL;
10 void
11 PyByteArray_Fini(void)
13 Py_CLEAR(nullbytes);
16 int
17 PyByteArray_Init(void)
19 nullbytes = PyObject_New(PyByteArrayObject, &PyByteArray_Type);
20 if (nullbytes == NULL)
21 return 0;
22 nullbytes->ob_bytes = NULL;
23 Py_SIZE(nullbytes) = nullbytes->ob_alloc = 0;
24 nullbytes->ob_exports = 0;
25 return 1;
28 /* end nullbytes support */
30 /* Helpers */
32 static int
33 _getbytevalue(PyObject* arg, int *value)
35 long face_value;
37 if (PyBytes_CheckExact(arg)) {
38 if (Py_SIZE(arg) != 1) {
39 PyErr_SetString(PyExc_ValueError, "string must be of size 1");
40 return 0;
42 *value = Py_CHARMASK(((PyBytesObject*)arg)->ob_sval[0]);
43 return 1;
45 else if (PyInt_Check(arg) || PyLong_Check(arg)) {
46 face_value = PyLong_AsLong(arg);
48 else {
49 PyObject *index = PyNumber_Index(arg);
50 if (index == NULL) {
51 PyErr_Format(PyExc_TypeError,
52 "an integer or string of size 1 is required");
53 return 0;
55 face_value = PyLong_AsLong(index);
56 Py_DECREF(index);
59 if (face_value < 0 || face_value >= 256) {
60 /* this includes the OverflowError in case the long is too large */
61 PyErr_SetString(PyExc_ValueError, "byte must be in range(0, 256)");
62 return 0;
65 *value = face_value;
66 return 1;
69 static Py_ssize_t
70 bytearray_buffer_getreadbuf(PyByteArrayObject *self, Py_ssize_t index, const void **ptr)
72 if ( index != 0 ) {
73 PyErr_SetString(PyExc_SystemError,
74 "accessing non-existent bytes segment");
75 return -1;
77 *ptr = (void *)self->ob_bytes;
78 return Py_SIZE(self);
81 static Py_ssize_t
82 bytearray_buffer_getwritebuf(PyByteArrayObject *self, Py_ssize_t index, const void **ptr)
84 if ( index != 0 ) {
85 PyErr_SetString(PyExc_SystemError,
86 "accessing non-existent bytes segment");
87 return -1;
89 *ptr = (void *)self->ob_bytes;
90 return Py_SIZE(self);
93 static Py_ssize_t
94 bytearray_buffer_getsegcount(PyByteArrayObject *self, Py_ssize_t *lenp)
96 if ( lenp )
97 *lenp = Py_SIZE(self);
98 return 1;
101 static Py_ssize_t
102 bytearray_buffer_getcharbuf(PyByteArrayObject *self, Py_ssize_t index, const char **ptr)
104 if ( index != 0 ) {
105 PyErr_SetString(PyExc_SystemError,
106 "accessing non-existent bytes segment");
107 return -1;
109 *ptr = self->ob_bytes;
110 return Py_SIZE(self);
113 static int
114 bytearray_getbuffer(PyByteArrayObject *obj, Py_buffer *view, int flags)
116 int ret;
117 void *ptr;
118 if (view == NULL) {
119 obj->ob_exports++;
120 return 0;
122 if (obj->ob_bytes == NULL)
123 ptr = "";
124 else
125 ptr = obj->ob_bytes;
126 ret = PyBuffer_FillInfo(view, (PyObject*)obj, ptr, Py_SIZE(obj), 0, flags);
127 if (ret >= 0) {
128 obj->ob_exports++;
130 return ret;
133 static void
134 bytearray_releasebuffer(PyByteArrayObject *obj, Py_buffer *view)
136 obj->ob_exports--;
139 static Py_ssize_t
140 _getbuffer(PyObject *obj, Py_buffer *view)
142 PyBufferProcs *buffer = Py_TYPE(obj)->tp_as_buffer;
144 if (buffer == NULL || buffer->bf_getbuffer == NULL)
146 PyErr_Format(PyExc_TypeError,
147 "Type %.100s doesn't support the buffer API",
148 Py_TYPE(obj)->tp_name);
149 return -1;
152 if (buffer->bf_getbuffer(obj, view, PyBUF_SIMPLE) < 0)
153 return -1;
154 return view->len;
157 static int
158 _canresize(PyByteArrayObject *self)
160 if (self->ob_exports > 0) {
161 PyErr_SetString(PyExc_BufferError,
162 "Existing exports of data: object cannot be re-sized");
163 return 0;
165 return 1;
168 /* Direct API functions */
170 PyObject *
171 PyByteArray_FromObject(PyObject *input)
173 return PyObject_CallFunctionObjArgs((PyObject *)&PyByteArray_Type,
174 input, NULL);
177 PyObject *
178 PyByteArray_FromStringAndSize(const char *bytes, Py_ssize_t size)
180 PyByteArrayObject *new;
181 Py_ssize_t alloc;
183 if (size < 0) {
184 PyErr_SetString(PyExc_SystemError,
185 "Negative size passed to PyByteArray_FromStringAndSize");
186 return NULL;
189 new = PyObject_New(PyByteArrayObject, &PyByteArray_Type);
190 if (new == NULL)
191 return NULL;
193 if (size == 0) {
194 new->ob_bytes = NULL;
195 alloc = 0;
197 else {
198 alloc = size + 1;
199 new->ob_bytes = PyMem_Malloc(alloc);
200 if (new->ob_bytes == NULL) {
201 Py_DECREF(new);
202 return PyErr_NoMemory();
204 if (bytes != NULL)
205 memcpy(new->ob_bytes, bytes, size);
206 new->ob_bytes[size] = '\0'; /* Trailing null byte */
208 Py_SIZE(new) = size;
209 new->ob_alloc = alloc;
210 new->ob_exports = 0;
212 return (PyObject *)new;
215 Py_ssize_t
216 PyByteArray_Size(PyObject *self)
218 assert(self != NULL);
219 assert(PyByteArray_Check(self));
221 return PyByteArray_GET_SIZE(self);
224 char *
225 PyByteArray_AsString(PyObject *self)
227 assert(self != NULL);
228 assert(PyByteArray_Check(self));
230 return PyByteArray_AS_STRING(self);
234 PyByteArray_Resize(PyObject *self, Py_ssize_t size)
236 void *sval;
237 Py_ssize_t alloc = ((PyByteArrayObject *)self)->ob_alloc;
239 assert(self != NULL);
240 assert(PyByteArray_Check(self));
241 assert(size >= 0);
243 if (size == Py_SIZE(self)) {
244 return 0;
246 if (!_canresize((PyByteArrayObject *)self)) {
247 return -1;
250 if (size < alloc / 2) {
251 /* Major downsize; resize down to exact size */
252 alloc = size + 1;
254 else if (size < alloc) {
255 /* Within allocated size; quick exit */
256 Py_SIZE(self) = size;
257 ((PyByteArrayObject *)self)->ob_bytes[size] = '\0'; /* Trailing null */
258 return 0;
260 else if (size <= alloc * 1.125) {
261 /* Moderate upsize; overallocate similar to list_resize() */
262 alloc = size + (size >> 3) + (size < 9 ? 3 : 6);
264 else {
265 /* Major upsize; resize up to exact size */
266 alloc = size + 1;
269 sval = PyMem_Realloc(((PyByteArrayObject *)self)->ob_bytes, alloc);
270 if (sval == NULL) {
271 PyErr_NoMemory();
272 return -1;
275 ((PyByteArrayObject *)self)->ob_bytes = sval;
276 Py_SIZE(self) = size;
277 ((PyByteArrayObject *)self)->ob_alloc = alloc;
278 ((PyByteArrayObject *)self)->ob_bytes[size] = '\0'; /* Trailing null byte */
280 return 0;
283 PyObject *
284 PyByteArray_Concat(PyObject *a, PyObject *b)
286 Py_ssize_t size;
287 Py_buffer va, vb;
288 PyByteArrayObject *result = NULL;
290 va.len = -1;
291 vb.len = -1;
292 if (_getbuffer(a, &va) < 0 ||
293 _getbuffer(b, &vb) < 0) {
294 PyErr_Format(PyExc_TypeError, "can't concat %.100s to %.100s",
295 Py_TYPE(a)->tp_name, Py_TYPE(b)->tp_name);
296 goto done;
299 size = va.len + vb.len;
300 if (size < 0) {
301 PyErr_NoMemory();
302 goto done;
305 result = (PyByteArrayObject *) PyByteArray_FromStringAndSize(NULL, size);
306 if (result != NULL) {
307 memcpy(result->ob_bytes, va.buf, va.len);
308 memcpy(result->ob_bytes + va.len, vb.buf, vb.len);
311 done:
312 if (va.len != -1)
313 PyBuffer_Release(&va);
314 if (vb.len != -1)
315 PyBuffer_Release(&vb);
316 return (PyObject *)result;
319 /* Functions stuffed into the type object */
321 static Py_ssize_t
322 bytearray_length(PyByteArrayObject *self)
324 return Py_SIZE(self);
327 static PyObject *
328 bytearray_iconcat(PyByteArrayObject *self, PyObject *other)
330 Py_ssize_t mysize;
331 Py_ssize_t size;
332 Py_buffer vo;
334 if (_getbuffer(other, &vo) < 0) {
335 PyErr_Format(PyExc_TypeError, "can't concat %.100s to %.100s",
336 Py_TYPE(other)->tp_name, Py_TYPE(self)->tp_name);
337 return NULL;
340 mysize = Py_SIZE(self);
341 size = mysize + vo.len;
342 if (size < 0) {
343 PyBuffer_Release(&vo);
344 return PyErr_NoMemory();
346 if (size < self->ob_alloc) {
347 Py_SIZE(self) = size;
348 self->ob_bytes[Py_SIZE(self)] = '\0'; /* Trailing null byte */
350 else if (PyByteArray_Resize((PyObject *)self, size) < 0) {
351 PyBuffer_Release(&vo);
352 return NULL;
354 memcpy(self->ob_bytes + mysize, vo.buf, vo.len);
355 PyBuffer_Release(&vo);
356 Py_INCREF(self);
357 return (PyObject *)self;
360 static PyObject *
361 bytearray_repeat(PyByteArrayObject *self, Py_ssize_t count)
363 PyByteArrayObject *result;
364 Py_ssize_t mysize;
365 Py_ssize_t size;
367 if (count < 0)
368 count = 0;
369 mysize = Py_SIZE(self);
370 size = mysize * count;
371 if (count != 0 && size / count != mysize)
372 return PyErr_NoMemory();
373 result = (PyByteArrayObject *)PyByteArray_FromStringAndSize(NULL, size);
374 if (result != NULL && size != 0) {
375 if (mysize == 1)
376 memset(result->ob_bytes, self->ob_bytes[0], size);
377 else {
378 Py_ssize_t i;
379 for (i = 0; i < count; i++)
380 memcpy(result->ob_bytes + i*mysize, self->ob_bytes, mysize);
383 return (PyObject *)result;
386 static PyObject *
387 bytearray_irepeat(PyByteArrayObject *self, Py_ssize_t count)
389 Py_ssize_t mysize;
390 Py_ssize_t size;
392 if (count < 0)
393 count = 0;
394 mysize = Py_SIZE(self);
395 size = mysize * count;
396 if (count != 0 && size / count != mysize)
397 return PyErr_NoMemory();
398 if (size < self->ob_alloc) {
399 Py_SIZE(self) = size;
400 self->ob_bytes[Py_SIZE(self)] = '\0'; /* Trailing null byte */
402 else if (PyByteArray_Resize((PyObject *)self, size) < 0)
403 return NULL;
405 if (mysize == 1)
406 memset(self->ob_bytes, self->ob_bytes[0], size);
407 else {
408 Py_ssize_t i;
409 for (i = 1; i < count; i++)
410 memcpy(self->ob_bytes + i*mysize, self->ob_bytes, mysize);
413 Py_INCREF(self);
414 return (PyObject *)self;
417 static PyObject *
418 bytearray_getitem(PyByteArrayObject *self, Py_ssize_t i)
420 if (i < 0)
421 i += Py_SIZE(self);
422 if (i < 0 || i >= Py_SIZE(self)) {
423 PyErr_SetString(PyExc_IndexError, "bytearray index out of range");
424 return NULL;
426 return PyInt_FromLong((unsigned char)(self->ob_bytes[i]));
429 static PyObject *
430 bytearray_subscript(PyByteArrayObject *self, PyObject *index)
432 if (PyIndex_Check(index)) {
433 Py_ssize_t i = PyNumber_AsSsize_t(index, PyExc_IndexError);
435 if (i == -1 && PyErr_Occurred())
436 return NULL;
438 if (i < 0)
439 i += PyByteArray_GET_SIZE(self);
441 if (i < 0 || i >= Py_SIZE(self)) {
442 PyErr_SetString(PyExc_IndexError, "bytearray index out of range");
443 return NULL;
445 return PyInt_FromLong((unsigned char)(self->ob_bytes[i]));
447 else if (PySlice_Check(index)) {
448 Py_ssize_t start, stop, step, slicelength, cur, i;
449 if (PySlice_GetIndicesEx((PySliceObject *)index,
450 PyByteArray_GET_SIZE(self),
451 &start, &stop, &step, &slicelength) < 0) {
452 return NULL;
455 if (slicelength <= 0)
456 return PyByteArray_FromStringAndSize("", 0);
457 else if (step == 1) {
458 return PyByteArray_FromStringAndSize(self->ob_bytes + start,
459 slicelength);
461 else {
462 char *source_buf = PyByteArray_AS_STRING(self);
463 char *result_buf = (char *)PyMem_Malloc(slicelength);
464 PyObject *result;
466 if (result_buf == NULL)
467 return PyErr_NoMemory();
469 for (cur = start, i = 0; i < slicelength;
470 cur += step, i++) {
471 result_buf[i] = source_buf[cur];
473 result = PyByteArray_FromStringAndSize(result_buf, slicelength);
474 PyMem_Free(result_buf);
475 return result;
478 else {
479 PyErr_SetString(PyExc_TypeError, "bytearray indices must be integers");
480 return NULL;
484 static int
485 bytearray_setslice(PyByteArrayObject *self, Py_ssize_t lo, Py_ssize_t hi,
486 PyObject *values)
488 Py_ssize_t avail, needed;
489 void *bytes;
490 Py_buffer vbytes;
491 int res = 0;
493 vbytes.len = -1;
494 if (values == (PyObject *)self) {
495 /* Make a copy and call this function recursively */
496 int err;
497 values = PyByteArray_FromObject(values);
498 if (values == NULL)
499 return -1;
500 err = bytearray_setslice(self, lo, hi, values);
501 Py_DECREF(values);
502 return err;
504 if (values == NULL) {
505 /* del b[lo:hi] */
506 bytes = NULL;
507 needed = 0;
509 else {
510 if (_getbuffer(values, &vbytes) < 0) {
511 PyErr_Format(PyExc_TypeError,
512 "can't set bytearray slice from %.100s",
513 Py_TYPE(values)->tp_name);
514 return -1;
516 needed = vbytes.len;
517 bytes = vbytes.buf;
520 if (lo < 0)
521 lo = 0;
522 if (hi < lo)
523 hi = lo;
524 if (hi > Py_SIZE(self))
525 hi = Py_SIZE(self);
527 avail = hi - lo;
528 if (avail < 0)
529 lo = hi = avail = 0;
531 if (avail != needed) {
532 if (avail > needed) {
533 if (!_canresize(self)) {
534 res = -1;
535 goto finish;
538 0 lo hi old_size
539 | |<----avail----->|<-----tomove------>|
540 | |<-needed->|<-----tomove------>|
541 0 lo new_hi new_size
543 memmove(self->ob_bytes + lo + needed, self->ob_bytes + hi,
544 Py_SIZE(self) - hi);
546 /* XXX(nnorwitz): need to verify this can't overflow! */
547 if (PyByteArray_Resize((PyObject *)self,
548 Py_SIZE(self) + needed - avail) < 0) {
549 res = -1;
550 goto finish;
552 if (avail < needed) {
554 0 lo hi old_size
555 | |<-avail->|<-----tomove------>|
556 | |<----needed---->|<-----tomove------>|
557 0 lo new_hi new_size
559 memmove(self->ob_bytes + lo + needed, self->ob_bytes + hi,
560 Py_SIZE(self) - lo - needed);
564 if (needed > 0)
565 memcpy(self->ob_bytes + lo, bytes, needed);
568 finish:
569 if (vbytes.len != -1)
570 PyBuffer_Release(&vbytes);
571 return res;
574 static int
575 bytearray_setitem(PyByteArrayObject *self, Py_ssize_t i, PyObject *value)
577 int ival;
579 if (i < 0)
580 i += Py_SIZE(self);
582 if (i < 0 || i >= Py_SIZE(self)) {
583 PyErr_SetString(PyExc_IndexError, "bytearray index out of range");
584 return -1;
587 if (value == NULL)
588 return bytearray_setslice(self, i, i+1, NULL);
590 if (!_getbytevalue(value, &ival))
591 return -1;
593 self->ob_bytes[i] = ival;
594 return 0;
597 static int
598 bytearray_ass_subscript(PyByteArrayObject *self, PyObject *index, PyObject *values)
600 Py_ssize_t start, stop, step, slicelen, needed;
601 char *bytes;
603 if (PyIndex_Check(index)) {
604 Py_ssize_t i = PyNumber_AsSsize_t(index, PyExc_IndexError);
606 if (i == -1 && PyErr_Occurred())
607 return -1;
609 if (i < 0)
610 i += PyByteArray_GET_SIZE(self);
612 if (i < 0 || i >= Py_SIZE(self)) {
613 PyErr_SetString(PyExc_IndexError, "bytearray index out of range");
614 return -1;
617 if (values == NULL) {
618 /* Fall through to slice assignment */
619 start = i;
620 stop = i + 1;
621 step = 1;
622 slicelen = 1;
624 else {
625 int ival;
626 if (!_getbytevalue(values, &ival))
627 return -1;
628 self->ob_bytes[i] = (char)ival;
629 return 0;
632 else if (PySlice_Check(index)) {
633 if (PySlice_GetIndicesEx((PySliceObject *)index,
634 PyByteArray_GET_SIZE(self),
635 &start, &stop, &step, &slicelen) < 0) {
636 return -1;
639 else {
640 PyErr_SetString(PyExc_TypeError, "bytearray indices must be integer");
641 return -1;
644 if (values == NULL) {
645 bytes = NULL;
646 needed = 0;
648 else if (values == (PyObject *)self || !PyByteArray_Check(values)) {
649 /* Make a copy an call this function recursively */
650 int err;
651 values = PyByteArray_FromObject(values);
652 if (values == NULL)
653 return -1;
654 err = bytearray_ass_subscript(self, index, values);
655 Py_DECREF(values);
656 return err;
658 else {
659 assert(PyByteArray_Check(values));
660 bytes = ((PyByteArrayObject *)values)->ob_bytes;
661 needed = Py_SIZE(values);
663 /* Make sure b[5:2] = ... inserts before 5, not before 2. */
664 if ((step < 0 && start < stop) ||
665 (step > 0 && start > stop))
666 stop = start;
667 if (step == 1) {
668 if (slicelen != needed) {
669 if (!_canresize(self))
670 return -1;
671 if (slicelen > needed) {
673 0 start stop old_size
674 | |<---slicelen--->|<-----tomove------>|
675 | |<-needed->|<-----tomove------>|
676 0 lo new_hi new_size
678 memmove(self->ob_bytes + start + needed, self->ob_bytes + stop,
679 Py_SIZE(self) - stop);
681 if (PyByteArray_Resize((PyObject *)self,
682 Py_SIZE(self) + needed - slicelen) < 0)
683 return -1;
684 if (slicelen < needed) {
686 0 lo hi old_size
687 | |<-avail->|<-----tomove------>|
688 | |<----needed---->|<-----tomove------>|
689 0 lo new_hi new_size
691 memmove(self->ob_bytes + start + needed, self->ob_bytes + stop,
692 Py_SIZE(self) - start - needed);
696 if (needed > 0)
697 memcpy(self->ob_bytes + start, bytes, needed);
699 return 0;
701 else {
702 if (needed == 0) {
703 /* Delete slice */
704 Py_ssize_t cur, i;
706 if (!_canresize(self))
707 return -1;
708 if (step < 0) {
709 stop = start + 1;
710 start = stop + step * (slicelen - 1) - 1;
711 step = -step;
713 for (cur = start, i = 0;
714 i < slicelen; cur += step, i++) {
715 Py_ssize_t lim = step - 1;
717 if (cur + step >= PyByteArray_GET_SIZE(self))
718 lim = PyByteArray_GET_SIZE(self) - cur - 1;
720 memmove(self->ob_bytes + cur - i,
721 self->ob_bytes + cur + 1, lim);
723 /* Move the tail of the bytes, in one chunk */
724 cur = start + slicelen*step;
725 if (cur < PyByteArray_GET_SIZE(self)) {
726 memmove(self->ob_bytes + cur - slicelen,
727 self->ob_bytes + cur,
728 PyByteArray_GET_SIZE(self) - cur);
730 if (PyByteArray_Resize((PyObject *)self,
731 PyByteArray_GET_SIZE(self) - slicelen) < 0)
732 return -1;
734 return 0;
736 else {
737 /* Assign slice */
738 Py_ssize_t cur, i;
740 if (needed != slicelen) {
741 PyErr_Format(PyExc_ValueError,
742 "attempt to assign bytes of size %zd "
743 "to extended slice of size %zd",
744 needed, slicelen);
745 return -1;
747 for (cur = start, i = 0; i < slicelen; cur += step, i++)
748 self->ob_bytes[cur] = bytes[i];
749 return 0;
754 static int
755 bytearray_init(PyByteArrayObject *self, PyObject *args, PyObject *kwds)
757 static char *kwlist[] = {"source", "encoding", "errors", 0};
758 PyObject *arg = NULL;
759 const char *encoding = NULL;
760 const char *errors = NULL;
761 Py_ssize_t count;
762 PyObject *it;
763 PyObject *(*iternext)(PyObject *);
765 if (Py_SIZE(self) != 0) {
766 /* Empty previous contents (yes, do this first of all!) */
767 if (PyByteArray_Resize((PyObject *)self, 0) < 0)
768 return -1;
771 /* Parse arguments */
772 if (!PyArg_ParseTupleAndKeywords(args, kwds, "|Oss:bytearray", kwlist,
773 &arg, &encoding, &errors))
774 return -1;
776 /* Make a quick exit if no first argument */
777 if (arg == NULL) {
778 if (encoding != NULL || errors != NULL) {
779 PyErr_SetString(PyExc_TypeError,
780 "encoding or errors without sequence argument");
781 return -1;
783 return 0;
786 if (PyBytes_Check(arg)) {
787 PyObject *new, *encoded;
788 if (encoding != NULL) {
789 encoded = PyCodec_Encode(arg, encoding, errors);
790 if (encoded == NULL)
791 return -1;
792 assert(PyBytes_Check(encoded));
794 else {
795 encoded = arg;
796 Py_INCREF(arg);
798 new = bytearray_iconcat(self, arg);
799 Py_DECREF(encoded);
800 if (new == NULL)
801 return -1;
802 Py_DECREF(new);
803 return 0;
806 #ifdef Py_USING_UNICODE
807 if (PyUnicode_Check(arg)) {
808 /* Encode via the codec registry */
809 PyObject *encoded, *new;
810 if (encoding == NULL) {
811 PyErr_SetString(PyExc_TypeError,
812 "unicode argument without an encoding");
813 return -1;
815 encoded = PyCodec_Encode(arg, encoding, errors);
816 if (encoded == NULL)
817 return -1;
818 assert(PyBytes_Check(encoded));
819 new = bytearray_iconcat(self, encoded);
820 Py_DECREF(encoded);
821 if (new == NULL)
822 return -1;
823 Py_DECREF(new);
824 return 0;
826 #endif
828 /* If it's not unicode, there can't be encoding or errors */
829 if (encoding != NULL || errors != NULL) {
830 PyErr_SetString(PyExc_TypeError,
831 "encoding or errors without a string argument");
832 return -1;
835 /* Is it an int? */
836 count = PyNumber_AsSsize_t(arg, PyExc_ValueError);
837 if (count == -1 && PyErr_Occurred())
838 PyErr_Clear();
839 else {
840 if (count < 0) {
841 PyErr_SetString(PyExc_ValueError, "negative count");
842 return -1;
844 if (count > 0) {
845 if (PyByteArray_Resize((PyObject *)self, count))
846 return -1;
847 memset(self->ob_bytes, 0, count);
849 return 0;
852 /* Use the buffer API */
853 if (PyObject_CheckBuffer(arg)) {
854 Py_ssize_t size;
855 Py_buffer view;
856 if (PyObject_GetBuffer(arg, &view, PyBUF_FULL_RO) < 0)
857 return -1;
858 size = view.len;
859 if (PyByteArray_Resize((PyObject *)self, size) < 0) goto fail;
860 if (PyBuffer_ToContiguous(self->ob_bytes, &view, size, 'C') < 0)
861 goto fail;
862 PyBuffer_Release(&view);
863 return 0;
864 fail:
865 PyBuffer_Release(&view);
866 return -1;
869 /* XXX Optimize this if the arguments is a list, tuple */
871 /* Get the iterator */
872 it = PyObject_GetIter(arg);
873 if (it == NULL)
874 return -1;
875 iternext = *Py_TYPE(it)->tp_iternext;
877 /* Run the iterator to exhaustion */
878 for (;;) {
879 PyObject *item;
880 int rc, value;
882 /* Get the next item */
883 item = iternext(it);
884 if (item == NULL) {
885 if (PyErr_Occurred()) {
886 if (!PyErr_ExceptionMatches(PyExc_StopIteration))
887 goto error;
888 PyErr_Clear();
890 break;
893 /* Interpret it as an int (__index__) */
894 rc = _getbytevalue(item, &value);
895 Py_DECREF(item);
896 if (!rc)
897 goto error;
899 /* Append the byte */
900 if (Py_SIZE(self) < self->ob_alloc)
901 Py_SIZE(self)++;
902 else if (PyByteArray_Resize((PyObject *)self, Py_SIZE(self)+1) < 0)
903 goto error;
904 self->ob_bytes[Py_SIZE(self)-1] = value;
907 /* Clean up and return success */
908 Py_DECREF(it);
909 return 0;
911 error:
912 /* Error handling when it != NULL */
913 Py_DECREF(it);
914 return -1;
917 /* Mostly copied from string_repr, but without the
918 "smart quote" functionality. */
919 static PyObject *
920 bytearray_repr(PyByteArrayObject *self)
922 static const char *hexdigits = "0123456789abcdef";
923 const char *quote_prefix = "bytearray(b";
924 const char *quote_postfix = ")";
925 Py_ssize_t length = Py_SIZE(self);
926 /* 14 == strlen(quote_prefix) + 2 + strlen(quote_postfix) */
927 size_t newsize = 14 + 4 * length;
928 PyObject *v;
929 if (newsize > PY_SSIZE_T_MAX || newsize / 4 - 3 != length) {
930 PyErr_SetString(PyExc_OverflowError,
931 "bytearray object is too large to make repr");
932 return NULL;
934 v = PyString_FromStringAndSize(NULL, newsize);
935 if (v == NULL) {
936 return NULL;
938 else {
939 register Py_ssize_t i;
940 register char c;
941 register char *p;
942 int quote;
944 /* Figure out which quote to use; single is preferred */
945 quote = '\'';
947 char *test, *start;
948 start = PyByteArray_AS_STRING(self);
949 for (test = start; test < start+length; ++test) {
950 if (*test == '"') {
951 quote = '\''; /* back to single */
952 goto decided;
954 else if (*test == '\'')
955 quote = '"';
957 decided:
961 p = PyString_AS_STRING(v);
962 while (*quote_prefix)
963 *p++ = *quote_prefix++;
964 *p++ = quote;
966 for (i = 0; i < length; i++) {
967 /* There's at least enough room for a hex escape
968 and a closing quote. */
969 assert(newsize - (p - PyString_AS_STRING(v)) >= 5);
970 c = self->ob_bytes[i];
971 if (c == '\'' || c == '\\')
972 *p++ = '\\', *p++ = c;
973 else if (c == '\t')
974 *p++ = '\\', *p++ = 't';
975 else if (c == '\n')
976 *p++ = '\\', *p++ = 'n';
977 else if (c == '\r')
978 *p++ = '\\', *p++ = 'r';
979 else if (c == 0)
980 *p++ = '\\', *p++ = 'x', *p++ = '0', *p++ = '0';
981 else if (c < ' ' || c >= 0x7f) {
982 *p++ = '\\';
983 *p++ = 'x';
984 *p++ = hexdigits[(c & 0xf0) >> 4];
985 *p++ = hexdigits[c & 0xf];
987 else
988 *p++ = c;
990 assert(newsize - (p - PyString_AS_STRING(v)) >= 1);
991 *p++ = quote;
992 while (*quote_postfix) {
993 *p++ = *quote_postfix++;
995 *p = '\0';
996 if (_PyString_Resize(&v, (p - PyString_AS_STRING(v)))) {
997 Py_DECREF(v);
998 return NULL;
1000 return v;
1004 static PyObject *
1005 bytearray_str(PyObject *op)
1007 #if 0
1008 if (Py_BytesWarningFlag) {
1009 if (PyErr_WarnEx(PyExc_BytesWarning,
1010 "str() on a bytearray instance", 1))
1011 return NULL;
1013 return bytearray_repr((PyByteArrayObject*)op);
1014 #endif
1015 return PyBytes_FromStringAndSize(((PyByteArrayObject*)op)->ob_bytes, Py_SIZE(op));
1018 static PyObject *
1019 bytearray_richcompare(PyObject *self, PyObject *other, int op)
1021 Py_ssize_t self_size, other_size;
1022 Py_buffer self_bytes, other_bytes;
1023 PyObject *res;
1024 Py_ssize_t minsize;
1025 int cmp;
1027 /* Bytes can be compared to anything that supports the (binary)
1028 buffer API. Except that a comparison with Unicode is always an
1029 error, even if the comparison is for equality. */
1030 #ifdef Py_USING_UNICODE
1031 if (PyObject_IsInstance(self, (PyObject*)&PyUnicode_Type) ||
1032 PyObject_IsInstance(other, (PyObject*)&PyUnicode_Type)) {
1033 if (Py_BytesWarningFlag && op == Py_EQ) {
1034 if (PyErr_WarnEx(PyExc_BytesWarning,
1035 "Comparsion between bytearray and string", 1))
1036 return NULL;
1039 Py_INCREF(Py_NotImplemented);
1040 return Py_NotImplemented;
1042 #endif
1044 self_size = _getbuffer(self, &self_bytes);
1045 if (self_size < 0) {
1046 PyErr_Clear();
1047 Py_INCREF(Py_NotImplemented);
1048 return Py_NotImplemented;
1051 other_size = _getbuffer(other, &other_bytes);
1052 if (other_size < 0) {
1053 PyErr_Clear();
1054 PyBuffer_Release(&self_bytes);
1055 Py_INCREF(Py_NotImplemented);
1056 return Py_NotImplemented;
1059 if (self_size != other_size && (op == Py_EQ || op == Py_NE)) {
1060 /* Shortcut: if the lengths differ, the objects differ */
1061 cmp = (op == Py_NE);
1063 else {
1064 minsize = self_size;
1065 if (other_size < minsize)
1066 minsize = other_size;
1068 cmp = memcmp(self_bytes.buf, other_bytes.buf, minsize);
1069 /* In ISO C, memcmp() guarantees to use unsigned bytes! */
1071 if (cmp == 0) {
1072 if (self_size < other_size)
1073 cmp = -1;
1074 else if (self_size > other_size)
1075 cmp = 1;
1078 switch (op) {
1079 case Py_LT: cmp = cmp < 0; break;
1080 case Py_LE: cmp = cmp <= 0; break;
1081 case Py_EQ: cmp = cmp == 0; break;
1082 case Py_NE: cmp = cmp != 0; break;
1083 case Py_GT: cmp = cmp > 0; break;
1084 case Py_GE: cmp = cmp >= 0; break;
1088 res = cmp ? Py_True : Py_False;
1089 PyBuffer_Release(&self_bytes);
1090 PyBuffer_Release(&other_bytes);
1091 Py_INCREF(res);
1092 return res;
1095 static void
1096 bytearray_dealloc(PyByteArrayObject *self)
1098 if (self->ob_exports > 0) {
1099 PyErr_SetString(PyExc_SystemError,
1100 "deallocated bytearray object has exported buffers");
1101 PyErr_Print();
1103 if (self->ob_bytes != 0) {
1104 PyMem_Free(self->ob_bytes);
1106 Py_TYPE(self)->tp_free((PyObject *)self);
1110 /* -------------------------------------------------------------------- */
1111 /* Methods */
1113 #define STRINGLIB_CHAR char
1114 #define STRINGLIB_CMP memcmp
1115 #define STRINGLIB_LEN PyByteArray_GET_SIZE
1116 #define STRINGLIB_STR PyByteArray_AS_STRING
1117 #define STRINGLIB_NEW PyByteArray_FromStringAndSize
1118 #define STRINGLIB_EMPTY nullbytes
1119 #define STRINGLIB_CHECK_EXACT PyByteArray_CheckExact
1120 #define STRINGLIB_MUTABLE 1
1121 #define FROM_BYTEARRAY 1
1123 #include "stringlib/fastsearch.h"
1124 #include "stringlib/count.h"
1125 #include "stringlib/find.h"
1126 #include "stringlib/partition.h"
1127 #include "stringlib/ctype.h"
1128 #include "stringlib/transmogrify.h"
1131 /* The following Py_LOCAL_INLINE and Py_LOCAL functions
1132 were copied from the old char* style string object. */
1134 Py_LOCAL_INLINE(void)
1135 _adjust_indices(Py_ssize_t *start, Py_ssize_t *end, Py_ssize_t len)
1137 if (*end > len)
1138 *end = len;
1139 else if (*end < 0)
1140 *end += len;
1141 if (*end < 0)
1142 *end = 0;
1143 if (*start < 0)
1144 *start += len;
1145 if (*start < 0)
1146 *start = 0;
1150 Py_LOCAL_INLINE(Py_ssize_t)
1151 bytearray_find_internal(PyByteArrayObject *self, PyObject *args, int dir)
1153 PyObject *subobj;
1154 Py_buffer subbuf;
1155 Py_ssize_t start=0, end=PY_SSIZE_T_MAX;
1156 Py_ssize_t res;
1158 if (!PyArg_ParseTuple(args, "O|O&O&:find/rfind/index/rindex", &subobj,
1159 _PyEval_SliceIndex, &start, _PyEval_SliceIndex, &end))
1160 return -2;
1161 if (_getbuffer(subobj, &subbuf) < 0)
1162 return -2;
1163 if (dir > 0)
1164 res = stringlib_find_slice(
1165 PyByteArray_AS_STRING(self), PyByteArray_GET_SIZE(self),
1166 subbuf.buf, subbuf.len, start, end);
1167 else
1168 res = stringlib_rfind_slice(
1169 PyByteArray_AS_STRING(self), PyByteArray_GET_SIZE(self),
1170 subbuf.buf, subbuf.len, start, end);
1171 PyBuffer_Release(&subbuf);
1172 return res;
1175 PyDoc_STRVAR(find__doc__,
1176 "B.find(sub [,start [,end]]) -> int\n\
1178 Return the lowest index in B where subsection sub is found,\n\
1179 such that sub is contained within s[start,end]. Optional\n\
1180 arguments start and end are interpreted as in slice notation.\n\
1182 Return -1 on failure.");
1184 static PyObject *
1185 bytearray_find(PyByteArrayObject *self, PyObject *args)
1187 Py_ssize_t result = bytearray_find_internal(self, args, +1);
1188 if (result == -2)
1189 return NULL;
1190 return PyInt_FromSsize_t(result);
1193 PyDoc_STRVAR(count__doc__,
1194 "B.count(sub [,start [,end]]) -> int\n\
1196 Return the number of non-overlapping occurrences of subsection sub in\n\
1197 bytes B[start:end]. Optional arguments start and end are interpreted\n\
1198 as in slice notation.");
1200 static PyObject *
1201 bytearray_count(PyByteArrayObject *self, PyObject *args)
1203 PyObject *sub_obj;
1204 const char *str = PyByteArray_AS_STRING(self);
1205 Py_ssize_t start = 0, end = PY_SSIZE_T_MAX;
1206 Py_buffer vsub;
1207 PyObject *count_obj;
1209 if (!PyArg_ParseTuple(args, "O|O&O&:count", &sub_obj,
1210 _PyEval_SliceIndex, &start, _PyEval_SliceIndex, &end))
1211 return NULL;
1213 if (_getbuffer(sub_obj, &vsub) < 0)
1214 return NULL;
1216 _adjust_indices(&start, &end, PyByteArray_GET_SIZE(self));
1218 count_obj = PyInt_FromSsize_t(
1219 stringlib_count(str + start, end - start, vsub.buf, vsub.len)
1221 PyBuffer_Release(&vsub);
1222 return count_obj;
1226 PyDoc_STRVAR(index__doc__,
1227 "B.index(sub [,start [,end]]) -> int\n\
1229 Like B.find() but raise ValueError when the subsection is not found.");
1231 static PyObject *
1232 bytearray_index(PyByteArrayObject *self, PyObject *args)
1234 Py_ssize_t result = bytearray_find_internal(self, args, +1);
1235 if (result == -2)
1236 return NULL;
1237 if (result == -1) {
1238 PyErr_SetString(PyExc_ValueError,
1239 "subsection not found");
1240 return NULL;
1242 return PyInt_FromSsize_t(result);
1246 PyDoc_STRVAR(rfind__doc__,
1247 "B.rfind(sub [,start [,end]]) -> int\n\
1249 Return the highest index in B where subsection sub is found,\n\
1250 such that sub is contained within s[start,end]. Optional\n\
1251 arguments start and end are interpreted as in slice notation.\n\
1253 Return -1 on failure.");
1255 static PyObject *
1256 bytearray_rfind(PyByteArrayObject *self, PyObject *args)
1258 Py_ssize_t result = bytearray_find_internal(self, args, -1);
1259 if (result == -2)
1260 return NULL;
1261 return PyInt_FromSsize_t(result);
1265 PyDoc_STRVAR(rindex__doc__,
1266 "B.rindex(sub [,start [,end]]) -> int\n\
1268 Like B.rfind() but raise ValueError when the subsection is not found.");
1270 static PyObject *
1271 bytearray_rindex(PyByteArrayObject *self, PyObject *args)
1273 Py_ssize_t result = bytearray_find_internal(self, args, -1);
1274 if (result == -2)
1275 return NULL;
1276 if (result == -1) {
1277 PyErr_SetString(PyExc_ValueError,
1278 "subsection not found");
1279 return NULL;
1281 return PyInt_FromSsize_t(result);
1285 static int
1286 bytearray_contains(PyObject *self, PyObject *arg)
1288 Py_ssize_t ival = PyNumber_AsSsize_t(arg, PyExc_ValueError);
1289 if (ival == -1 && PyErr_Occurred()) {
1290 Py_buffer varg;
1291 int pos;
1292 PyErr_Clear();
1293 if (_getbuffer(arg, &varg) < 0)
1294 return -1;
1295 pos = stringlib_find(PyByteArray_AS_STRING(self), Py_SIZE(self),
1296 varg.buf, varg.len, 0);
1297 PyBuffer_Release(&varg);
1298 return pos >= 0;
1300 if (ival < 0 || ival >= 256) {
1301 PyErr_SetString(PyExc_ValueError, "byte must be in range(0, 256)");
1302 return -1;
1305 return memchr(PyByteArray_AS_STRING(self), ival, Py_SIZE(self)) != NULL;
1309 /* Matches the end (direction >= 0) or start (direction < 0) of self
1310 * against substr, using the start and end arguments. Returns
1311 * -1 on error, 0 if not found and 1 if found.
1313 Py_LOCAL(int)
1314 _bytearray_tailmatch(PyByteArrayObject *self, PyObject *substr, Py_ssize_t start,
1315 Py_ssize_t end, int direction)
1317 Py_ssize_t len = PyByteArray_GET_SIZE(self);
1318 const char* str;
1319 Py_buffer vsubstr;
1320 int rv = 0;
1322 str = PyByteArray_AS_STRING(self);
1324 if (_getbuffer(substr, &vsubstr) < 0)
1325 return -1;
1327 _adjust_indices(&start, &end, len);
1329 if (direction < 0) {
1330 /* startswith */
1331 if (start+vsubstr.len > len) {
1332 goto done;
1334 } else {
1335 /* endswith */
1336 if (end-start < vsubstr.len || start > len) {
1337 goto done;
1340 if (end-vsubstr.len > start)
1341 start = end - vsubstr.len;
1343 if (end-start >= vsubstr.len)
1344 rv = ! memcmp(str+start, vsubstr.buf, vsubstr.len);
1346 done:
1347 PyBuffer_Release(&vsubstr);
1348 return rv;
1352 PyDoc_STRVAR(startswith__doc__,
1353 "B.startswith(prefix [,start [,end]]) -> bool\n\
1355 Return True if B starts with the specified prefix, False otherwise.\n\
1356 With optional start, test B beginning at that position.\n\
1357 With optional end, stop comparing B at that position.\n\
1358 prefix can also be a tuple of strings to try.");
1360 static PyObject *
1361 bytearray_startswith(PyByteArrayObject *self, PyObject *args)
1363 Py_ssize_t start = 0;
1364 Py_ssize_t end = PY_SSIZE_T_MAX;
1365 PyObject *subobj;
1366 int result;
1368 if (!PyArg_ParseTuple(args, "O|O&O&:startswith", &subobj,
1369 _PyEval_SliceIndex, &start, _PyEval_SliceIndex, &end))
1370 return NULL;
1371 if (PyTuple_Check(subobj)) {
1372 Py_ssize_t i;
1373 for (i = 0; i < PyTuple_GET_SIZE(subobj); i++) {
1374 result = _bytearray_tailmatch(self,
1375 PyTuple_GET_ITEM(subobj, i),
1376 start, end, -1);
1377 if (result == -1)
1378 return NULL;
1379 else if (result) {
1380 Py_RETURN_TRUE;
1383 Py_RETURN_FALSE;
1385 result = _bytearray_tailmatch(self, subobj, start, end, -1);
1386 if (result == -1)
1387 return NULL;
1388 else
1389 return PyBool_FromLong(result);
1392 PyDoc_STRVAR(endswith__doc__,
1393 "B.endswith(suffix [,start [,end]]) -> bool\n\
1395 Return True if B ends with the specified suffix, False otherwise.\n\
1396 With optional start, test B beginning at that position.\n\
1397 With optional end, stop comparing B at that position.\n\
1398 suffix can also be a tuple of strings to try.");
1400 static PyObject *
1401 bytearray_endswith(PyByteArrayObject *self, PyObject *args)
1403 Py_ssize_t start = 0;
1404 Py_ssize_t end = PY_SSIZE_T_MAX;
1405 PyObject *subobj;
1406 int result;
1408 if (!PyArg_ParseTuple(args, "O|O&O&:endswith", &subobj,
1409 _PyEval_SliceIndex, &start, _PyEval_SliceIndex, &end))
1410 return NULL;
1411 if (PyTuple_Check(subobj)) {
1412 Py_ssize_t i;
1413 for (i = 0; i < PyTuple_GET_SIZE(subobj); i++) {
1414 result = _bytearray_tailmatch(self,
1415 PyTuple_GET_ITEM(subobj, i),
1416 start, end, +1);
1417 if (result == -1)
1418 return NULL;
1419 else if (result) {
1420 Py_RETURN_TRUE;
1423 Py_RETURN_FALSE;
1425 result = _bytearray_tailmatch(self, subobj, start, end, +1);
1426 if (result == -1)
1427 return NULL;
1428 else
1429 return PyBool_FromLong(result);
1433 PyDoc_STRVAR(translate__doc__,
1434 "B.translate(table[, deletechars]) -> bytearray\n\
1436 Return a copy of B, where all characters occurring in the\n\
1437 optional argument deletechars are removed, and the remaining\n\
1438 characters have been mapped through the given translation\n\
1439 table, which must be a bytes object of length 256.");
1441 static PyObject *
1442 bytearray_translate(PyByteArrayObject *self, PyObject *args)
1444 register char *input, *output;
1445 register const char *table;
1446 register Py_ssize_t i, c;
1447 PyObject *input_obj = (PyObject*)self;
1448 const char *output_start;
1449 Py_ssize_t inlen;
1450 PyObject *result = NULL;
1451 int trans_table[256];
1452 PyObject *tableobj = NULL, *delobj = NULL;
1453 Py_buffer vtable, vdel;
1455 if (!PyArg_UnpackTuple(args, "translate", 1, 2,
1456 &tableobj, &delobj))
1457 return NULL;
1459 if (tableobj == Py_None) {
1460 table = NULL;
1461 tableobj = NULL;
1462 } else if (_getbuffer(tableobj, &vtable) < 0) {
1463 return NULL;
1464 } else {
1465 if (vtable.len != 256) {
1466 PyErr_SetString(PyExc_ValueError,
1467 "translation table must be 256 characters long");
1468 goto done;
1470 table = (const char*)vtable.buf;
1473 if (delobj != NULL) {
1474 if (_getbuffer(delobj, &vdel) < 0) {
1475 delobj = NULL; /* don't try to release vdel buffer on exit */
1476 goto done;
1479 else {
1480 vdel.buf = NULL;
1481 vdel.len = 0;
1484 inlen = PyByteArray_GET_SIZE(input_obj);
1485 result = PyByteArray_FromStringAndSize((char *)NULL, inlen);
1486 if (result == NULL)
1487 goto done;
1488 output_start = output = PyByteArray_AsString(result);
1489 input = PyByteArray_AS_STRING(input_obj);
1491 if (vdel.len == 0 && table != NULL) {
1492 /* If no deletions are required, use faster code */
1493 for (i = inlen; --i >= 0; ) {
1494 c = Py_CHARMASK(*input++);
1495 *output++ = table[c];
1497 goto done;
1500 if (table == NULL) {
1501 for (i = 0; i < 256; i++)
1502 trans_table[i] = Py_CHARMASK(i);
1503 } else {
1504 for (i = 0; i < 256; i++)
1505 trans_table[i] = Py_CHARMASK(table[i]);
1508 for (i = 0; i < vdel.len; i++)
1509 trans_table[(int) Py_CHARMASK( ((unsigned char*)vdel.buf)[i] )] = -1;
1511 for (i = inlen; --i >= 0; ) {
1512 c = Py_CHARMASK(*input++);
1513 if (trans_table[c] != -1)
1514 if (Py_CHARMASK(*output++ = (char)trans_table[c]) == c)
1515 continue;
1517 /* Fix the size of the resulting string */
1518 if (inlen > 0)
1519 PyByteArray_Resize(result, output - output_start);
1521 done:
1522 if (tableobj != NULL)
1523 PyBuffer_Release(&vtable);
1524 if (delobj != NULL)
1525 PyBuffer_Release(&vdel);
1526 return result;
1530 #define FORWARD 1
1531 #define REVERSE -1
1533 /* find and count characters and substrings */
1535 #define findchar(target, target_len, c) \
1536 ((char *)memchr((const void *)(target), c, target_len))
1538 /* Don't call if length < 2 */
1539 #define Py_STRING_MATCH(target, offset, pattern, length) \
1540 (target[offset] == pattern[0] && \
1541 target[offset+length-1] == pattern[length-1] && \
1542 !memcmp(target+offset+1, pattern+1, length-2) )
1545 /* Bytes ops must return a string, create a copy */
1546 Py_LOCAL(PyByteArrayObject *)
1547 return_self(PyByteArrayObject *self)
1549 return (PyByteArrayObject *)PyByteArray_FromStringAndSize(
1550 PyByteArray_AS_STRING(self),
1551 PyByteArray_GET_SIZE(self));
1554 Py_LOCAL_INLINE(Py_ssize_t)
1555 countchar(const char *target, Py_ssize_t target_len, char c, Py_ssize_t maxcount)
1557 Py_ssize_t count=0;
1558 const char *start=target;
1559 const char *end=target+target_len;
1561 while ( (start=findchar(start, end-start, c)) != NULL ) {
1562 count++;
1563 if (count >= maxcount)
1564 break;
1565 start += 1;
1567 return count;
1570 Py_LOCAL(Py_ssize_t)
1571 findstring(const char *target, Py_ssize_t target_len,
1572 const char *pattern, Py_ssize_t pattern_len,
1573 Py_ssize_t start,
1574 Py_ssize_t end,
1575 int direction)
1577 if (start < 0) {
1578 start += target_len;
1579 if (start < 0)
1580 start = 0;
1582 if (end > target_len) {
1583 end = target_len;
1584 } else if (end < 0) {
1585 end += target_len;
1586 if (end < 0)
1587 end = 0;
1590 /* zero-length substrings always match at the first attempt */
1591 if (pattern_len == 0)
1592 return (direction > 0) ? start : end;
1594 end -= pattern_len;
1596 if (direction < 0) {
1597 for (; end >= start; end--)
1598 if (Py_STRING_MATCH(target, end, pattern, pattern_len))
1599 return end;
1600 } else {
1601 for (; start <= end; start++)
1602 if (Py_STRING_MATCH(target, start, pattern, pattern_len))
1603 return start;
1605 return -1;
1608 Py_LOCAL_INLINE(Py_ssize_t)
1609 countstring(const char *target, Py_ssize_t target_len,
1610 const char *pattern, Py_ssize_t pattern_len,
1611 Py_ssize_t start,
1612 Py_ssize_t end,
1613 int direction, Py_ssize_t maxcount)
1615 Py_ssize_t count=0;
1617 if (start < 0) {
1618 start += target_len;
1619 if (start < 0)
1620 start = 0;
1622 if (end > target_len) {
1623 end = target_len;
1624 } else if (end < 0) {
1625 end += target_len;
1626 if (end < 0)
1627 end = 0;
1630 /* zero-length substrings match everywhere */
1631 if (pattern_len == 0 || maxcount == 0) {
1632 if (target_len+1 < maxcount)
1633 return target_len+1;
1634 return maxcount;
1637 end -= pattern_len;
1638 if (direction < 0) {
1639 for (; (end >= start); end--)
1640 if (Py_STRING_MATCH(target, end, pattern, pattern_len)) {
1641 count++;
1642 if (--maxcount <= 0) break;
1643 end -= pattern_len-1;
1645 } else {
1646 for (; (start <= end); start++)
1647 if (Py_STRING_MATCH(target, start, pattern, pattern_len)) {
1648 count++;
1649 if (--maxcount <= 0)
1650 break;
1651 start += pattern_len-1;
1654 return count;
1658 /* Algorithms for different cases of string replacement */
1660 /* len(self)>=1, from="", len(to)>=1, maxcount>=1 */
1661 Py_LOCAL(PyByteArrayObject *)
1662 replace_interleave(PyByteArrayObject *self,
1663 const char *to_s, Py_ssize_t to_len,
1664 Py_ssize_t maxcount)
1666 char *self_s, *result_s;
1667 Py_ssize_t self_len, result_len;
1668 Py_ssize_t count, i, product;
1669 PyByteArrayObject *result;
1671 self_len = PyByteArray_GET_SIZE(self);
1673 /* 1 at the end plus 1 after every character */
1674 count = self_len+1;
1675 if (maxcount < count)
1676 count = maxcount;
1678 /* Check for overflow */
1679 /* result_len = count * to_len + self_len; */
1680 product = count * to_len;
1681 if (product / to_len != count) {
1682 PyErr_SetString(PyExc_OverflowError,
1683 "replace string is too long");
1684 return NULL;
1686 result_len = product + self_len;
1687 if (result_len < 0) {
1688 PyErr_SetString(PyExc_OverflowError,
1689 "replace string is too long");
1690 return NULL;
1693 if (! (result = (PyByteArrayObject *)
1694 PyByteArray_FromStringAndSize(NULL, result_len)) )
1695 return NULL;
1697 self_s = PyByteArray_AS_STRING(self);
1698 result_s = PyByteArray_AS_STRING(result);
1700 /* TODO: special case single character, which doesn't need memcpy */
1702 /* Lay the first one down (guaranteed this will occur) */
1703 Py_MEMCPY(result_s, to_s, to_len);
1704 result_s += to_len;
1705 count -= 1;
1707 for (i=0; i<count; i++) {
1708 *result_s++ = *self_s++;
1709 Py_MEMCPY(result_s, to_s, to_len);
1710 result_s += to_len;
1713 /* Copy the rest of the original string */
1714 Py_MEMCPY(result_s, self_s, self_len-i);
1716 return result;
1719 /* Special case for deleting a single character */
1720 /* len(self)>=1, len(from)==1, to="", maxcount>=1 */
1721 Py_LOCAL(PyByteArrayObject *)
1722 replace_delete_single_character(PyByteArrayObject *self,
1723 char from_c, Py_ssize_t maxcount)
1725 char *self_s, *result_s;
1726 char *start, *next, *end;
1727 Py_ssize_t self_len, result_len;
1728 Py_ssize_t count;
1729 PyByteArrayObject *result;
1731 self_len = PyByteArray_GET_SIZE(self);
1732 self_s = PyByteArray_AS_STRING(self);
1734 count = countchar(self_s, self_len, from_c, maxcount);
1735 if (count == 0) {
1736 return return_self(self);
1739 result_len = self_len - count; /* from_len == 1 */
1740 assert(result_len>=0);
1742 if ( (result = (PyByteArrayObject *)
1743 PyByteArray_FromStringAndSize(NULL, result_len)) == NULL)
1744 return NULL;
1745 result_s = PyByteArray_AS_STRING(result);
1747 start = self_s;
1748 end = self_s + self_len;
1749 while (count-- > 0) {
1750 next = findchar(start, end-start, from_c);
1751 if (next == NULL)
1752 break;
1753 Py_MEMCPY(result_s, start, next-start);
1754 result_s += (next-start);
1755 start = next+1;
1757 Py_MEMCPY(result_s, start, end-start);
1759 return result;
1762 /* len(self)>=1, len(from)>=2, to="", maxcount>=1 */
1764 Py_LOCAL(PyByteArrayObject *)
1765 replace_delete_substring(PyByteArrayObject *self,
1766 const char *from_s, Py_ssize_t from_len,
1767 Py_ssize_t maxcount)
1769 char *self_s, *result_s;
1770 char *start, *next, *end;
1771 Py_ssize_t self_len, result_len;
1772 Py_ssize_t count, offset;
1773 PyByteArrayObject *result;
1775 self_len = PyByteArray_GET_SIZE(self);
1776 self_s = PyByteArray_AS_STRING(self);
1778 count = countstring(self_s, self_len,
1779 from_s, from_len,
1780 0, self_len, 1,
1781 maxcount);
1783 if (count == 0) {
1784 /* no matches */
1785 return return_self(self);
1788 result_len = self_len - (count * from_len);
1789 assert (result_len>=0);
1791 if ( (result = (PyByteArrayObject *)
1792 PyByteArray_FromStringAndSize(NULL, result_len)) == NULL )
1793 return NULL;
1795 result_s = PyByteArray_AS_STRING(result);
1797 start = self_s;
1798 end = self_s + self_len;
1799 while (count-- > 0) {
1800 offset = findstring(start, end-start,
1801 from_s, from_len,
1802 0, end-start, FORWARD);
1803 if (offset == -1)
1804 break;
1805 next = start + offset;
1807 Py_MEMCPY(result_s, start, next-start);
1809 result_s += (next-start);
1810 start = next+from_len;
1812 Py_MEMCPY(result_s, start, end-start);
1813 return result;
1816 /* len(self)>=1, len(from)==len(to)==1, maxcount>=1 */
1817 Py_LOCAL(PyByteArrayObject *)
1818 replace_single_character_in_place(PyByteArrayObject *self,
1819 char from_c, char to_c,
1820 Py_ssize_t maxcount)
1822 char *self_s, *result_s, *start, *end, *next;
1823 Py_ssize_t self_len;
1824 PyByteArrayObject *result;
1826 /* The result string will be the same size */
1827 self_s = PyByteArray_AS_STRING(self);
1828 self_len = PyByteArray_GET_SIZE(self);
1830 next = findchar(self_s, self_len, from_c);
1832 if (next == NULL) {
1833 /* No matches; return the original bytes */
1834 return return_self(self);
1837 /* Need to make a new bytes */
1838 result = (PyByteArrayObject *) PyByteArray_FromStringAndSize(NULL, self_len);
1839 if (result == NULL)
1840 return NULL;
1841 result_s = PyByteArray_AS_STRING(result);
1842 Py_MEMCPY(result_s, self_s, self_len);
1844 /* change everything in-place, starting with this one */
1845 start = result_s + (next-self_s);
1846 *start = to_c;
1847 start++;
1848 end = result_s + self_len;
1850 while (--maxcount > 0) {
1851 next = findchar(start, end-start, from_c);
1852 if (next == NULL)
1853 break;
1854 *next = to_c;
1855 start = next+1;
1858 return result;
1861 /* len(self)>=1, len(from)==len(to)>=2, maxcount>=1 */
1862 Py_LOCAL(PyByteArrayObject *)
1863 replace_substring_in_place(PyByteArrayObject *self,
1864 const char *from_s, Py_ssize_t from_len,
1865 const char *to_s, Py_ssize_t to_len,
1866 Py_ssize_t maxcount)
1868 char *result_s, *start, *end;
1869 char *self_s;
1870 Py_ssize_t self_len, offset;
1871 PyByteArrayObject *result;
1873 /* The result bytes will be the same size */
1875 self_s = PyByteArray_AS_STRING(self);
1876 self_len = PyByteArray_GET_SIZE(self);
1878 offset = findstring(self_s, self_len,
1879 from_s, from_len,
1880 0, self_len, FORWARD);
1881 if (offset == -1) {
1882 /* No matches; return the original bytes */
1883 return return_self(self);
1886 /* Need to make a new bytes */
1887 result = (PyByteArrayObject *) PyByteArray_FromStringAndSize(NULL, self_len);
1888 if (result == NULL)
1889 return NULL;
1890 result_s = PyByteArray_AS_STRING(result);
1891 Py_MEMCPY(result_s, self_s, self_len);
1893 /* change everything in-place, starting with this one */
1894 start = result_s + offset;
1895 Py_MEMCPY(start, to_s, from_len);
1896 start += from_len;
1897 end = result_s + self_len;
1899 while ( --maxcount > 0) {
1900 offset = findstring(start, end-start,
1901 from_s, from_len,
1902 0, end-start, FORWARD);
1903 if (offset==-1)
1904 break;
1905 Py_MEMCPY(start+offset, to_s, from_len);
1906 start += offset+from_len;
1909 return result;
1912 /* len(self)>=1, len(from)==1, len(to)>=2, maxcount>=1 */
1913 Py_LOCAL(PyByteArrayObject *)
1914 replace_single_character(PyByteArrayObject *self,
1915 char from_c,
1916 const char *to_s, Py_ssize_t to_len,
1917 Py_ssize_t maxcount)
1919 char *self_s, *result_s;
1920 char *start, *next, *end;
1921 Py_ssize_t self_len, result_len;
1922 Py_ssize_t count, product;
1923 PyByteArrayObject *result;
1925 self_s = PyByteArray_AS_STRING(self);
1926 self_len = PyByteArray_GET_SIZE(self);
1928 count = countchar(self_s, self_len, from_c, maxcount);
1929 if (count == 0) {
1930 /* no matches, return unchanged */
1931 return return_self(self);
1934 /* use the difference between current and new, hence the "-1" */
1935 /* result_len = self_len + count * (to_len-1) */
1936 product = count * (to_len-1);
1937 if (product / (to_len-1) != count) {
1938 PyErr_SetString(PyExc_OverflowError, "replace bytes is too long");
1939 return NULL;
1941 result_len = self_len + product;
1942 if (result_len < 0) {
1943 PyErr_SetString(PyExc_OverflowError, "replace bytes is too long");
1944 return NULL;
1947 if ( (result = (PyByteArrayObject *)
1948 PyByteArray_FromStringAndSize(NULL, result_len)) == NULL)
1949 return NULL;
1950 result_s = PyByteArray_AS_STRING(result);
1952 start = self_s;
1953 end = self_s + self_len;
1954 while (count-- > 0) {
1955 next = findchar(start, end-start, from_c);
1956 if (next == NULL)
1957 break;
1959 if (next == start) {
1960 /* replace with the 'to' */
1961 Py_MEMCPY(result_s, to_s, to_len);
1962 result_s += to_len;
1963 start += 1;
1964 } else {
1965 /* copy the unchanged old then the 'to' */
1966 Py_MEMCPY(result_s, start, next-start);
1967 result_s += (next-start);
1968 Py_MEMCPY(result_s, to_s, to_len);
1969 result_s += to_len;
1970 start = next+1;
1973 /* Copy the remainder of the remaining bytes */
1974 Py_MEMCPY(result_s, start, end-start);
1976 return result;
1979 /* len(self)>=1, len(from)>=2, len(to)>=2, maxcount>=1 */
1980 Py_LOCAL(PyByteArrayObject *)
1981 replace_substring(PyByteArrayObject *self,
1982 const char *from_s, Py_ssize_t from_len,
1983 const char *to_s, Py_ssize_t to_len,
1984 Py_ssize_t maxcount)
1986 char *self_s, *result_s;
1987 char *start, *next, *end;
1988 Py_ssize_t self_len, result_len;
1989 Py_ssize_t count, offset, product;
1990 PyByteArrayObject *result;
1992 self_s = PyByteArray_AS_STRING(self);
1993 self_len = PyByteArray_GET_SIZE(self);
1995 count = countstring(self_s, self_len,
1996 from_s, from_len,
1997 0, self_len, FORWARD, maxcount);
1998 if (count == 0) {
1999 /* no matches, return unchanged */
2000 return return_self(self);
2003 /* Check for overflow */
2004 /* result_len = self_len + count * (to_len-from_len) */
2005 product = count * (to_len-from_len);
2006 if (product / (to_len-from_len) != count) {
2007 PyErr_SetString(PyExc_OverflowError, "replace bytes is too long");
2008 return NULL;
2010 result_len = self_len + product;
2011 if (result_len < 0) {
2012 PyErr_SetString(PyExc_OverflowError, "replace bytes is too long");
2013 return NULL;
2016 if ( (result = (PyByteArrayObject *)
2017 PyByteArray_FromStringAndSize(NULL, result_len)) == NULL)
2018 return NULL;
2019 result_s = PyByteArray_AS_STRING(result);
2021 start = self_s;
2022 end = self_s + self_len;
2023 while (count-- > 0) {
2024 offset = findstring(start, end-start,
2025 from_s, from_len,
2026 0, end-start, FORWARD);
2027 if (offset == -1)
2028 break;
2029 next = start+offset;
2030 if (next == start) {
2031 /* replace with the 'to' */
2032 Py_MEMCPY(result_s, to_s, to_len);
2033 result_s += to_len;
2034 start += from_len;
2035 } else {
2036 /* copy the unchanged old then the 'to' */
2037 Py_MEMCPY(result_s, start, next-start);
2038 result_s += (next-start);
2039 Py_MEMCPY(result_s, to_s, to_len);
2040 result_s += to_len;
2041 start = next+from_len;
2044 /* Copy the remainder of the remaining bytes */
2045 Py_MEMCPY(result_s, start, end-start);
2047 return result;
2051 Py_LOCAL(PyByteArrayObject *)
2052 replace(PyByteArrayObject *self,
2053 const char *from_s, Py_ssize_t from_len,
2054 const char *to_s, Py_ssize_t to_len,
2055 Py_ssize_t maxcount)
2057 if (maxcount < 0) {
2058 maxcount = PY_SSIZE_T_MAX;
2059 } else if (maxcount == 0 || PyByteArray_GET_SIZE(self) == 0) {
2060 /* nothing to do; return the original bytes */
2061 return return_self(self);
2064 if (maxcount == 0 ||
2065 (from_len == 0 && to_len == 0)) {
2066 /* nothing to do; return the original bytes */
2067 return return_self(self);
2070 /* Handle zero-length special cases */
2072 if (from_len == 0) {
2073 /* insert the 'to' bytes everywhere. */
2074 /* >>> "Python".replace("", ".") */
2075 /* '.P.y.t.h.o.n.' */
2076 return replace_interleave(self, to_s, to_len, maxcount);
2079 /* Except for "".replace("", "A") == "A" there is no way beyond this */
2080 /* point for an empty self bytes to generate a non-empty bytes */
2081 /* Special case so the remaining code always gets a non-empty bytes */
2082 if (PyByteArray_GET_SIZE(self) == 0) {
2083 return return_self(self);
2086 if (to_len == 0) {
2087 /* delete all occurances of 'from' bytes */
2088 if (from_len == 1) {
2089 return replace_delete_single_character(
2090 self, from_s[0], maxcount);
2091 } else {
2092 return replace_delete_substring(self, from_s, from_len, maxcount);
2096 /* Handle special case where both bytes have the same length */
2098 if (from_len == to_len) {
2099 if (from_len == 1) {
2100 return replace_single_character_in_place(
2101 self,
2102 from_s[0],
2103 to_s[0],
2104 maxcount);
2105 } else {
2106 return replace_substring_in_place(
2107 self, from_s, from_len, to_s, to_len, maxcount);
2111 /* Otherwise use the more generic algorithms */
2112 if (from_len == 1) {
2113 return replace_single_character(self, from_s[0],
2114 to_s, to_len, maxcount);
2115 } else {
2116 /* len('from')>=2, len('to')>=1 */
2117 return replace_substring(self, from_s, from_len, to_s, to_len, maxcount);
2122 PyDoc_STRVAR(replace__doc__,
2123 "B.replace(old, new[, count]) -> bytes\n\
2125 Return a copy of B with all occurrences of subsection\n\
2126 old replaced by new. If the optional argument count is\n\
2127 given, only the first count occurrences are replaced.");
2129 static PyObject *
2130 bytearray_replace(PyByteArrayObject *self, PyObject *args)
2132 Py_ssize_t count = -1;
2133 PyObject *from, *to, *res;
2134 Py_buffer vfrom, vto;
2136 if (!PyArg_ParseTuple(args, "OO|n:replace", &from, &to, &count))
2137 return NULL;
2139 if (_getbuffer(from, &vfrom) < 0)
2140 return NULL;
2141 if (_getbuffer(to, &vto) < 0) {
2142 PyBuffer_Release(&vfrom);
2143 return NULL;
2146 res = (PyObject *)replace((PyByteArrayObject *) self,
2147 vfrom.buf, vfrom.len,
2148 vto.buf, vto.len, count);
2150 PyBuffer_Release(&vfrom);
2151 PyBuffer_Release(&vto);
2152 return res;
2156 /* Overallocate the initial list to reduce the number of reallocs for small
2157 split sizes. Eg, "A A A A A A A A A A".split() (10 elements) has three
2158 resizes, to sizes 4, 8, then 16. Most observed string splits are for human
2159 text (roughly 11 words per line) and field delimited data (usually 1-10
2160 fields). For large strings the split algorithms are bandwidth limited
2161 so increasing the preallocation likely will not improve things.*/
2163 #define MAX_PREALLOC 12
2165 /* 5 splits gives 6 elements */
2166 #define PREALLOC_SIZE(maxsplit) \
2167 (maxsplit >= MAX_PREALLOC ? MAX_PREALLOC : maxsplit+1)
2169 #define SPLIT_APPEND(data, left, right) \
2170 str = PyByteArray_FromStringAndSize((data) + (left), \
2171 (right) - (left)); \
2172 if (str == NULL) \
2173 goto onError; \
2174 if (PyList_Append(list, str)) { \
2175 Py_DECREF(str); \
2176 goto onError; \
2178 else \
2179 Py_DECREF(str);
2181 #define SPLIT_ADD(data, left, right) { \
2182 str = PyByteArray_FromStringAndSize((data) + (left), \
2183 (right) - (left)); \
2184 if (str == NULL) \
2185 goto onError; \
2186 if (count < MAX_PREALLOC) { \
2187 PyList_SET_ITEM(list, count, str); \
2188 } else { \
2189 if (PyList_Append(list, str)) { \
2190 Py_DECREF(str); \
2191 goto onError; \
2193 else \
2194 Py_DECREF(str); \
2196 count++; }
2198 /* Always force the list to the expected size. */
2199 #define FIX_PREALLOC_SIZE(list) Py_SIZE(list) = count
2202 Py_LOCAL_INLINE(PyObject *)
2203 split_char(const char *s, Py_ssize_t len, char ch, Py_ssize_t maxcount)
2205 register Py_ssize_t i, j, count = 0;
2206 PyObject *str;
2207 PyObject *list = PyList_New(PREALLOC_SIZE(maxcount));
2209 if (list == NULL)
2210 return NULL;
2212 i = j = 0;
2213 while ((j < len) && (maxcount-- > 0)) {
2214 for(; j < len; j++) {
2215 /* I found that using memchr makes no difference */
2216 if (s[j] == ch) {
2217 SPLIT_ADD(s, i, j);
2218 i = j = j + 1;
2219 break;
2223 if (i <= len) {
2224 SPLIT_ADD(s, i, len);
2226 FIX_PREALLOC_SIZE(list);
2227 return list;
2229 onError:
2230 Py_DECREF(list);
2231 return NULL;
2235 Py_LOCAL_INLINE(PyObject *)
2236 split_whitespace(const char *s, Py_ssize_t len, Py_ssize_t maxcount)
2238 register Py_ssize_t i, j, count = 0;
2239 PyObject *str;
2240 PyObject *list = PyList_New(PREALLOC_SIZE(maxcount));
2242 if (list == NULL)
2243 return NULL;
2245 for (i = j = 0; i < len; ) {
2246 /* find a token */
2247 while (i < len && Py_ISSPACE(s[i]))
2248 i++;
2249 j = i;
2250 while (i < len && !Py_ISSPACE(s[i]))
2251 i++;
2252 if (j < i) {
2253 if (maxcount-- <= 0)
2254 break;
2255 SPLIT_ADD(s, j, i);
2256 while (i < len && Py_ISSPACE(s[i]))
2257 i++;
2258 j = i;
2261 if (j < len) {
2262 SPLIT_ADD(s, j, len);
2264 FIX_PREALLOC_SIZE(list);
2265 return list;
2267 onError:
2268 Py_DECREF(list);
2269 return NULL;
2272 PyDoc_STRVAR(split__doc__,
2273 "B.split([sep[, maxsplit]]) -> list of bytearray\n\
2275 Return a list of the sections in B, using sep as the delimiter.\n\
2276 If sep is not given, B is split on ASCII whitespace characters\n\
2277 (space, tab, return, newline, formfeed, vertical tab).\n\
2278 If maxsplit is given, at most maxsplit splits are done.");
2280 static PyObject *
2281 bytearray_split(PyByteArrayObject *self, PyObject *args)
2283 Py_ssize_t len = PyByteArray_GET_SIZE(self), n, i, j;
2284 Py_ssize_t maxsplit = -1, count = 0;
2285 const char *s = PyByteArray_AS_STRING(self), *sub;
2286 PyObject *list, *str, *subobj = Py_None;
2287 Py_buffer vsub;
2288 #ifdef USE_FAST
2289 Py_ssize_t pos;
2290 #endif
2292 if (!PyArg_ParseTuple(args, "|On:split", &subobj, &maxsplit))
2293 return NULL;
2294 if (maxsplit < 0)
2295 maxsplit = PY_SSIZE_T_MAX;
2297 if (subobj == Py_None)
2298 return split_whitespace(s, len, maxsplit);
2300 if (_getbuffer(subobj, &vsub) < 0)
2301 return NULL;
2302 sub = vsub.buf;
2303 n = vsub.len;
2305 if (n == 0) {
2306 PyErr_SetString(PyExc_ValueError, "empty separator");
2307 PyBuffer_Release(&vsub);
2308 return NULL;
2310 if (n == 1) {
2311 list = split_char(s, len, sub[0], maxsplit);
2312 PyBuffer_Release(&vsub);
2313 return list;
2316 list = PyList_New(PREALLOC_SIZE(maxsplit));
2317 if (list == NULL) {
2318 PyBuffer_Release(&vsub);
2319 return NULL;
2322 #ifdef USE_FAST
2323 i = j = 0;
2324 while (maxsplit-- > 0) {
2325 pos = fastsearch(s+i, len-i, sub, n, FAST_SEARCH);
2326 if (pos < 0)
2327 break;
2328 j = i+pos;
2329 SPLIT_ADD(s, i, j);
2330 i = j + n;
2332 #else
2333 i = j = 0;
2334 while ((j+n <= len) && (maxsplit-- > 0)) {
2335 for (; j+n <= len; j++) {
2336 if (Py_STRING_MATCH(s, j, sub, n)) {
2337 SPLIT_ADD(s, i, j);
2338 i = j = j + n;
2339 break;
2343 #endif
2344 SPLIT_ADD(s, i, len);
2345 FIX_PREALLOC_SIZE(list);
2346 PyBuffer_Release(&vsub);
2347 return list;
2349 onError:
2350 Py_DECREF(list);
2351 PyBuffer_Release(&vsub);
2352 return NULL;
2355 /* stringlib's partition shares nullbytes in some cases.
2356 undo this, we don't want the nullbytes to be shared. */
2357 static PyObject *
2358 make_nullbytes_unique(PyObject *result)
2360 if (result != NULL) {
2361 int i;
2362 assert(PyTuple_Check(result));
2363 assert(PyTuple_GET_SIZE(result) == 3);
2364 for (i = 0; i < 3; i++) {
2365 if (PyTuple_GET_ITEM(result, i) == (PyObject *)nullbytes) {
2366 PyObject *new = PyByteArray_FromStringAndSize(NULL, 0);
2367 if (new == NULL) {
2368 Py_DECREF(result);
2369 result = NULL;
2370 break;
2372 Py_DECREF(nullbytes);
2373 PyTuple_SET_ITEM(result, i, new);
2377 return result;
2380 PyDoc_STRVAR(partition__doc__,
2381 "B.partition(sep) -> (head, sep, tail)\n\
2383 Searches for the separator sep in B, and returns the part before it,\n\
2384 the separator itself, and the part after it. If the separator is not\n\
2385 found, returns B and two empty bytearray objects.");
2387 static PyObject *
2388 bytearray_partition(PyByteArrayObject *self, PyObject *sep_obj)
2390 PyObject *bytesep, *result;
2392 bytesep = PyByteArray_FromObject(sep_obj);
2393 if (! bytesep)
2394 return NULL;
2396 result = stringlib_partition(
2397 (PyObject*) self,
2398 PyByteArray_AS_STRING(self), PyByteArray_GET_SIZE(self),
2399 bytesep,
2400 PyByteArray_AS_STRING(bytesep), PyByteArray_GET_SIZE(bytesep)
2403 Py_DECREF(bytesep);
2404 return make_nullbytes_unique(result);
2407 PyDoc_STRVAR(rpartition__doc__,
2408 "B.rpartition(sep) -> (tail, sep, head)\n\
2410 Searches for the separator sep in B, starting at the end of B,\n\
2411 and returns the part before it, the separator itself, and the\n\
2412 part after it. If the separator is not found, returns two empty\n\
2413 bytearray objects and B.");
2415 static PyObject *
2416 bytearray_rpartition(PyByteArrayObject *self, PyObject *sep_obj)
2418 PyObject *bytesep, *result;
2420 bytesep = PyByteArray_FromObject(sep_obj);
2421 if (! bytesep)
2422 return NULL;
2424 result = stringlib_rpartition(
2425 (PyObject*) self,
2426 PyByteArray_AS_STRING(self), PyByteArray_GET_SIZE(self),
2427 bytesep,
2428 PyByteArray_AS_STRING(bytesep), PyByteArray_GET_SIZE(bytesep)
2431 Py_DECREF(bytesep);
2432 return make_nullbytes_unique(result);
2435 Py_LOCAL_INLINE(PyObject *)
2436 rsplit_char(const char *s, Py_ssize_t len, char ch, Py_ssize_t maxcount)
2438 register Py_ssize_t i, j, count=0;
2439 PyObject *str;
2440 PyObject *list = PyList_New(PREALLOC_SIZE(maxcount));
2442 if (list == NULL)
2443 return NULL;
2445 i = j = len - 1;
2446 while ((i >= 0) && (maxcount-- > 0)) {
2447 for (; i >= 0; i--) {
2448 if (s[i] == ch) {
2449 SPLIT_ADD(s, i + 1, j + 1);
2450 j = i = i - 1;
2451 break;
2455 if (j >= -1) {
2456 SPLIT_ADD(s, 0, j + 1);
2458 FIX_PREALLOC_SIZE(list);
2459 if (PyList_Reverse(list) < 0)
2460 goto onError;
2462 return list;
2464 onError:
2465 Py_DECREF(list);
2466 return NULL;
2469 Py_LOCAL_INLINE(PyObject *)
2470 rsplit_whitespace(const char *s, Py_ssize_t len, Py_ssize_t maxcount)
2472 register Py_ssize_t i, j, count = 0;
2473 PyObject *str;
2474 PyObject *list = PyList_New(PREALLOC_SIZE(maxcount));
2476 if (list == NULL)
2477 return NULL;
2479 for (i = j = len - 1; i >= 0; ) {
2480 /* find a token */
2481 while (i >= 0 && Py_ISSPACE(s[i]))
2482 i--;
2483 j = i;
2484 while (i >= 0 && !Py_ISSPACE(s[i]))
2485 i--;
2486 if (j > i) {
2487 if (maxcount-- <= 0)
2488 break;
2489 SPLIT_ADD(s, i + 1, j + 1);
2490 while (i >= 0 && Py_ISSPACE(s[i]))
2491 i--;
2492 j = i;
2495 if (j >= 0) {
2496 SPLIT_ADD(s, 0, j + 1);
2498 FIX_PREALLOC_SIZE(list);
2499 if (PyList_Reverse(list) < 0)
2500 goto onError;
2502 return list;
2504 onError:
2505 Py_DECREF(list);
2506 return NULL;
2509 PyDoc_STRVAR(rsplit__doc__,
2510 "B.rsplit(sep[, maxsplit]) -> list of bytearray\n\
2512 Return a list of the sections in B, using sep as the delimiter,\n\
2513 starting at the end of B and working to the front.\n\
2514 If sep is not given, B is split on ASCII whitespace characters\n\
2515 (space, tab, return, newline, formfeed, vertical tab).\n\
2516 If maxsplit is given, at most maxsplit splits are done.");
2518 static PyObject *
2519 bytearray_rsplit(PyByteArrayObject *self, PyObject *args)
2521 Py_ssize_t len = PyByteArray_GET_SIZE(self), n, i, j;
2522 Py_ssize_t maxsplit = -1, count = 0;
2523 const char *s = PyByteArray_AS_STRING(self), *sub;
2524 PyObject *list, *str, *subobj = Py_None;
2525 Py_buffer vsub;
2527 if (!PyArg_ParseTuple(args, "|On:rsplit", &subobj, &maxsplit))
2528 return NULL;
2529 if (maxsplit < 0)
2530 maxsplit = PY_SSIZE_T_MAX;
2532 if (subobj == Py_None)
2533 return rsplit_whitespace(s, len, maxsplit);
2535 if (_getbuffer(subobj, &vsub) < 0)
2536 return NULL;
2537 sub = vsub.buf;
2538 n = vsub.len;
2540 if (n == 0) {
2541 PyErr_SetString(PyExc_ValueError, "empty separator");
2542 PyBuffer_Release(&vsub);
2543 return NULL;
2545 else if (n == 1) {
2546 list = rsplit_char(s, len, sub[0], maxsplit);
2547 PyBuffer_Release(&vsub);
2548 return list;
2551 list = PyList_New(PREALLOC_SIZE(maxsplit));
2552 if (list == NULL) {
2553 PyBuffer_Release(&vsub);
2554 return NULL;
2557 j = len;
2558 i = j - n;
2560 while ( (i >= 0) && (maxsplit-- > 0) ) {
2561 for (; i>=0; i--) {
2562 if (Py_STRING_MATCH(s, i, sub, n)) {
2563 SPLIT_ADD(s, i + n, j);
2564 j = i;
2565 i -= n;
2566 break;
2570 SPLIT_ADD(s, 0, j);
2571 FIX_PREALLOC_SIZE(list);
2572 if (PyList_Reverse(list) < 0)
2573 goto onError;
2574 PyBuffer_Release(&vsub);
2575 return list;
2577 onError:
2578 Py_DECREF(list);
2579 PyBuffer_Release(&vsub);
2580 return NULL;
2583 PyDoc_STRVAR(reverse__doc__,
2584 "B.reverse() -> None\n\
2586 Reverse the order of the values in B in place.");
2587 static PyObject *
2588 bytearray_reverse(PyByteArrayObject *self, PyObject *unused)
2590 char swap, *head, *tail;
2591 Py_ssize_t i, j, n = Py_SIZE(self);
2593 j = n / 2;
2594 head = self->ob_bytes;
2595 tail = head + n - 1;
2596 for (i = 0; i < j; i++) {
2597 swap = *head;
2598 *head++ = *tail;
2599 *tail-- = swap;
2602 Py_RETURN_NONE;
2605 PyDoc_STRVAR(insert__doc__,
2606 "B.insert(index, int) -> None\n\
2608 Insert a single item into the bytearray before the given index.");
2609 static PyObject *
2610 bytearray_insert(PyByteArrayObject *self, PyObject *args)
2612 PyObject *value;
2613 int ival;
2614 Py_ssize_t where, n = Py_SIZE(self);
2616 if (!PyArg_ParseTuple(args, "nO:insert", &where, &value))
2617 return NULL;
2619 if (n == PY_SSIZE_T_MAX) {
2620 PyErr_SetString(PyExc_OverflowError,
2621 "cannot add more objects to bytes");
2622 return NULL;
2624 if (!_getbytevalue(value, &ival))
2625 return NULL;
2626 if (PyByteArray_Resize((PyObject *)self, n + 1) < 0)
2627 return NULL;
2629 if (where < 0) {
2630 where += n;
2631 if (where < 0)
2632 where = 0;
2634 if (where > n)
2635 where = n;
2636 memmove(self->ob_bytes + where + 1, self->ob_bytes + where, n - where);
2637 self->ob_bytes[where] = ival;
2639 Py_RETURN_NONE;
2642 PyDoc_STRVAR(append__doc__,
2643 "B.append(int) -> None\n\
2645 Append a single item to the end of B.");
2646 static PyObject *
2647 bytearray_append(PyByteArrayObject *self, PyObject *arg)
2649 int value;
2650 Py_ssize_t n = Py_SIZE(self);
2652 if (! _getbytevalue(arg, &value))
2653 return NULL;
2654 if (n == PY_SSIZE_T_MAX) {
2655 PyErr_SetString(PyExc_OverflowError,
2656 "cannot add more objects to bytes");
2657 return NULL;
2659 if (PyByteArray_Resize((PyObject *)self, n + 1) < 0)
2660 return NULL;
2662 self->ob_bytes[n] = value;
2664 Py_RETURN_NONE;
2667 PyDoc_STRVAR(extend__doc__,
2668 "B.extend(iterable int) -> None\n\
2670 Append all the elements from the iterator or sequence to the\n\
2671 end of B.");
2672 static PyObject *
2673 bytearray_extend(PyByteArrayObject *self, PyObject *arg)
2675 PyObject *it, *item, *bytearray_obj;
2676 Py_ssize_t buf_size = 0, len = 0;
2677 int value;
2678 char *buf;
2680 /* bytearray_setslice code only accepts something supporting PEP 3118. */
2681 if (PyObject_CheckBuffer(arg)) {
2682 if (bytearray_setslice(self, Py_SIZE(self), Py_SIZE(self), arg) == -1)
2683 return NULL;
2685 Py_RETURN_NONE;
2688 it = PyObject_GetIter(arg);
2689 if (it == NULL)
2690 return NULL;
2692 /* Try to determine the length of the argument. 32 is abitrary. */
2693 buf_size = _PyObject_LengthHint(arg, 32);
2694 if (buf_size == -1) {
2695 Py_DECREF(it);
2696 return NULL;
2699 bytearray_obj = PyByteArray_FromStringAndSize(NULL, buf_size);
2700 if (bytearray_obj == NULL)
2701 return NULL;
2702 buf = PyByteArray_AS_STRING(bytearray_obj);
2704 while ((item = PyIter_Next(it)) != NULL) {
2705 if (! _getbytevalue(item, &value)) {
2706 Py_DECREF(item);
2707 Py_DECREF(it);
2708 Py_DECREF(bytearray_obj);
2709 return NULL;
2711 buf[len++] = value;
2712 Py_DECREF(item);
2714 if (len >= buf_size) {
2715 buf_size = len + (len >> 1) + 1;
2716 if (PyByteArray_Resize((PyObject *)bytearray_obj, buf_size) < 0) {
2717 Py_DECREF(it);
2718 Py_DECREF(bytearray_obj);
2719 return NULL;
2721 /* Recompute the `buf' pointer, since the resizing operation may
2722 have invalidated it. */
2723 buf = PyByteArray_AS_STRING(bytearray_obj);
2726 Py_DECREF(it);
2728 /* Resize down to exact size. */
2729 if (PyByteArray_Resize((PyObject *)bytearray_obj, len) < 0) {
2730 Py_DECREF(bytearray_obj);
2731 return NULL;
2734 if (bytearray_setslice(self, Py_SIZE(self), Py_SIZE(self), bytearray_obj) == -1)
2735 return NULL;
2736 Py_DECREF(bytearray_obj);
2738 Py_RETURN_NONE;
2741 PyDoc_STRVAR(pop__doc__,
2742 "B.pop([index]) -> int\n\
2744 Remove and return a single item from B. If no index\n\
2745 argument is given, will pop the last value.");
2746 static PyObject *
2747 bytearray_pop(PyByteArrayObject *self, PyObject *args)
2749 int value;
2750 Py_ssize_t where = -1, n = Py_SIZE(self);
2752 if (!PyArg_ParseTuple(args, "|n:pop", &where))
2753 return NULL;
2755 if (n == 0) {
2756 PyErr_SetString(PyExc_OverflowError,
2757 "cannot pop an empty bytes");
2758 return NULL;
2760 if (where < 0)
2761 where += Py_SIZE(self);
2762 if (where < 0 || where >= Py_SIZE(self)) {
2763 PyErr_SetString(PyExc_IndexError, "pop index out of range");
2764 return NULL;
2766 if (!_canresize(self))
2767 return NULL;
2769 value = self->ob_bytes[where];
2770 memmove(self->ob_bytes + where, self->ob_bytes + where + 1, n - where);
2771 if (PyByteArray_Resize((PyObject *)self, n - 1) < 0)
2772 return NULL;
2774 return PyInt_FromLong(value);
2777 PyDoc_STRVAR(remove__doc__,
2778 "B.remove(int) -> None\n\
2780 Remove the first occurance of a value in B.");
2781 static PyObject *
2782 bytearray_remove(PyByteArrayObject *self, PyObject *arg)
2784 int value;
2785 Py_ssize_t where, n = Py_SIZE(self);
2787 if (! _getbytevalue(arg, &value))
2788 return NULL;
2790 for (where = 0; where < n; where++) {
2791 if (self->ob_bytes[where] == value)
2792 break;
2794 if (where == n) {
2795 PyErr_SetString(PyExc_ValueError, "value not found in bytes");
2796 return NULL;
2798 if (!_canresize(self))
2799 return NULL;
2801 memmove(self->ob_bytes + where, self->ob_bytes + where + 1, n - where);
2802 if (PyByteArray_Resize((PyObject *)self, n - 1) < 0)
2803 return NULL;
2805 Py_RETURN_NONE;
2808 /* XXX These two helpers could be optimized if argsize == 1 */
2810 static Py_ssize_t
2811 lstrip_helper(unsigned char *myptr, Py_ssize_t mysize,
2812 void *argptr, Py_ssize_t argsize)
2814 Py_ssize_t i = 0;
2815 while (i < mysize && memchr(argptr, myptr[i], argsize))
2816 i++;
2817 return i;
2820 static Py_ssize_t
2821 rstrip_helper(unsigned char *myptr, Py_ssize_t mysize,
2822 void *argptr, Py_ssize_t argsize)
2824 Py_ssize_t i = mysize - 1;
2825 while (i >= 0 && memchr(argptr, myptr[i], argsize))
2826 i--;
2827 return i + 1;
2830 PyDoc_STRVAR(strip__doc__,
2831 "B.strip([bytes]) -> bytearray\n\
2833 Strip leading and trailing bytes contained in the argument.\n\
2834 If the argument is omitted, strip ASCII whitespace.");
2835 static PyObject *
2836 bytearray_strip(PyByteArrayObject *self, PyObject *args)
2838 Py_ssize_t left, right, mysize, argsize;
2839 void *myptr, *argptr;
2840 PyObject *arg = Py_None;
2841 Py_buffer varg;
2842 if (!PyArg_ParseTuple(args, "|O:strip", &arg))
2843 return NULL;
2844 if (arg == Py_None) {
2845 argptr = "\t\n\r\f\v ";
2846 argsize = 6;
2848 else {
2849 if (_getbuffer(arg, &varg) < 0)
2850 return NULL;
2851 argptr = varg.buf;
2852 argsize = varg.len;
2854 myptr = self->ob_bytes;
2855 mysize = Py_SIZE(self);
2856 left = lstrip_helper(myptr, mysize, argptr, argsize);
2857 if (left == mysize)
2858 right = left;
2859 else
2860 right = rstrip_helper(myptr, mysize, argptr, argsize);
2861 if (arg != Py_None)
2862 PyBuffer_Release(&varg);
2863 return PyByteArray_FromStringAndSize(self->ob_bytes + left, right - left);
2866 PyDoc_STRVAR(lstrip__doc__,
2867 "B.lstrip([bytes]) -> bytearray\n\
2869 Strip leading bytes contained in the argument.\n\
2870 If the argument is omitted, strip leading ASCII whitespace.");
2871 static PyObject *
2872 bytearray_lstrip(PyByteArrayObject *self, PyObject *args)
2874 Py_ssize_t left, right, mysize, argsize;
2875 void *myptr, *argptr;
2876 PyObject *arg = Py_None;
2877 Py_buffer varg;
2878 if (!PyArg_ParseTuple(args, "|O:lstrip", &arg))
2879 return NULL;
2880 if (arg == Py_None) {
2881 argptr = "\t\n\r\f\v ";
2882 argsize = 6;
2884 else {
2885 if (_getbuffer(arg, &varg) < 0)
2886 return NULL;
2887 argptr = varg.buf;
2888 argsize = varg.len;
2890 myptr = self->ob_bytes;
2891 mysize = Py_SIZE(self);
2892 left = lstrip_helper(myptr, mysize, argptr, argsize);
2893 right = mysize;
2894 if (arg != Py_None)
2895 PyBuffer_Release(&varg);
2896 return PyByteArray_FromStringAndSize(self->ob_bytes + left, right - left);
2899 PyDoc_STRVAR(rstrip__doc__,
2900 "B.rstrip([bytes]) -> bytearray\n\
2902 Strip trailing bytes contained in the argument.\n\
2903 If the argument is omitted, strip trailing ASCII whitespace.");
2904 static PyObject *
2905 bytearray_rstrip(PyByteArrayObject *self, PyObject *args)
2907 Py_ssize_t left, right, mysize, argsize;
2908 void *myptr, *argptr;
2909 PyObject *arg = Py_None;
2910 Py_buffer varg;
2911 if (!PyArg_ParseTuple(args, "|O:rstrip", &arg))
2912 return NULL;
2913 if (arg == Py_None) {
2914 argptr = "\t\n\r\f\v ";
2915 argsize = 6;
2917 else {
2918 if (_getbuffer(arg, &varg) < 0)
2919 return NULL;
2920 argptr = varg.buf;
2921 argsize = varg.len;
2923 myptr = self->ob_bytes;
2924 mysize = Py_SIZE(self);
2925 left = 0;
2926 right = rstrip_helper(myptr, mysize, argptr, argsize);
2927 if (arg != Py_None)
2928 PyBuffer_Release(&varg);
2929 return PyByteArray_FromStringAndSize(self->ob_bytes + left, right - left);
2932 PyDoc_STRVAR(decode_doc,
2933 "B.decode([encoding[, errors]]) -> unicode object.\n\
2935 Decodes B using the codec registered for encoding. encoding defaults\n\
2936 to the default encoding. errors may be given to set a different error\n\
2937 handling scheme. Default is 'strict' meaning that encoding errors raise\n\
2938 a UnicodeDecodeError. Other possible values are 'ignore' and 'replace'\n\
2939 as well as any other name registered with codecs.register_error that is\n\
2940 able to handle UnicodeDecodeErrors.");
2942 static PyObject *
2943 bytearray_decode(PyObject *self, PyObject *args)
2945 const char *encoding = NULL;
2946 const char *errors = NULL;
2948 if (!PyArg_ParseTuple(args, "|ss:decode", &encoding, &errors))
2949 return NULL;
2950 if (encoding == NULL) {
2951 #ifdef Py_USING_UNICODE
2952 encoding = PyUnicode_GetDefaultEncoding();
2953 #else
2954 PyErr_SetString(PyExc_ValueError, "no encoding specified");
2955 return NULL;
2956 #endif
2958 return PyCodec_Decode(self, encoding, errors);
2961 PyDoc_STRVAR(alloc_doc,
2962 "B.__alloc__() -> int\n\
2964 Returns the number of bytes actually allocated.");
2966 static PyObject *
2967 bytearray_alloc(PyByteArrayObject *self)
2969 return PyInt_FromSsize_t(self->ob_alloc);
2972 PyDoc_STRVAR(join_doc,
2973 "B.join(iterable_of_bytes) -> bytes\n\
2975 Concatenates any number of bytearray objects, with B in between each pair.");
2977 static PyObject *
2978 bytearray_join(PyByteArrayObject *self, PyObject *it)
2980 PyObject *seq;
2981 Py_ssize_t mysize = Py_SIZE(self);
2982 Py_ssize_t i;
2983 Py_ssize_t n;
2984 PyObject **items;
2985 Py_ssize_t totalsize = 0;
2986 PyObject *result;
2987 char *dest;
2989 seq = PySequence_Fast(it, "can only join an iterable");
2990 if (seq == NULL)
2991 return NULL;
2992 n = PySequence_Fast_GET_SIZE(seq);
2993 items = PySequence_Fast_ITEMS(seq);
2995 /* Compute the total size, and check that they are all bytes */
2996 /* XXX Shouldn't we use _getbuffer() on these items instead? */
2997 for (i = 0; i < n; i++) {
2998 PyObject *obj = items[i];
2999 if (!PyByteArray_Check(obj) && !PyBytes_Check(obj)) {
3000 PyErr_Format(PyExc_TypeError,
3001 "can only join an iterable of bytes "
3002 "(item %ld has type '%.100s')",
3003 /* XXX %ld isn't right on Win64 */
3004 (long)i, Py_TYPE(obj)->tp_name);
3005 goto error;
3007 if (i > 0)
3008 totalsize += mysize;
3009 totalsize += Py_SIZE(obj);
3010 if (totalsize < 0) {
3011 PyErr_NoMemory();
3012 goto error;
3016 /* Allocate the result, and copy the bytes */
3017 result = PyByteArray_FromStringAndSize(NULL, totalsize);
3018 if (result == NULL)
3019 goto error;
3020 dest = PyByteArray_AS_STRING(result);
3021 for (i = 0; i < n; i++) {
3022 PyObject *obj = items[i];
3023 Py_ssize_t size = Py_SIZE(obj);
3024 char *buf;
3025 if (PyByteArray_Check(obj))
3026 buf = PyByteArray_AS_STRING(obj);
3027 else
3028 buf = PyBytes_AS_STRING(obj);
3029 if (i) {
3030 memcpy(dest, self->ob_bytes, mysize);
3031 dest += mysize;
3033 memcpy(dest, buf, size);
3034 dest += size;
3037 /* Done */
3038 Py_DECREF(seq);
3039 return result;
3041 /* Error handling */
3042 error:
3043 Py_DECREF(seq);
3044 return NULL;
3047 PyDoc_STRVAR(fromhex_doc,
3048 "bytearray.fromhex(string) -> bytearray\n\
3050 Create a bytearray object from a string of hexadecimal numbers.\n\
3051 Spaces between two numbers are accepted.\n\
3052 Example: bytearray.fromhex('B9 01EF') -> bytearray(b'\\xb9\\x01\\xef').");
3054 static int
3055 hex_digit_to_int(char c)
3057 if (Py_ISDIGIT(c))
3058 return c - '0';
3059 else {
3060 if (Py_ISUPPER(c))
3061 c = Py_TOLOWER(c);
3062 if (c >= 'a' && c <= 'f')
3063 return c - 'a' + 10;
3065 return -1;
3068 static PyObject *
3069 bytearray_fromhex(PyObject *cls, PyObject *args)
3071 PyObject *newbytes;
3072 char *buf;
3073 char *hex;
3074 Py_ssize_t hexlen, byteslen, i, j;
3075 int top, bot;
3077 if (!PyArg_ParseTuple(args, "s#:fromhex", &hex, &hexlen))
3078 return NULL;
3079 byteslen = hexlen/2; /* This overestimates if there are spaces */
3080 newbytes = PyByteArray_FromStringAndSize(NULL, byteslen);
3081 if (!newbytes)
3082 return NULL;
3083 buf = PyByteArray_AS_STRING(newbytes);
3084 for (i = j = 0; i < hexlen; i += 2) {
3085 /* skip over spaces in the input */
3086 while (hex[i] == ' ')
3087 i++;
3088 if (i >= hexlen)
3089 break;
3090 top = hex_digit_to_int(hex[i]);
3091 bot = hex_digit_to_int(hex[i+1]);
3092 if (top == -1 || bot == -1) {
3093 PyErr_Format(PyExc_ValueError,
3094 "non-hexadecimal number found in "
3095 "fromhex() arg at position %zd", i);
3096 goto error;
3098 buf[j++] = (top << 4) + bot;
3100 if (PyByteArray_Resize(newbytes, j) < 0)
3101 goto error;
3102 return newbytes;
3104 error:
3105 Py_DECREF(newbytes);
3106 return NULL;
3109 PyDoc_STRVAR(reduce_doc, "Return state information for pickling.");
3111 static PyObject *
3112 bytearray_reduce(PyByteArrayObject *self)
3114 PyObject *latin1, *dict;
3115 if (self->ob_bytes)
3116 #ifdef Py_USING_UNICODE
3117 latin1 = PyUnicode_DecodeLatin1(self->ob_bytes,
3118 Py_SIZE(self), NULL);
3119 #else
3120 latin1 = PyString_FromStringAndSize(self->ob_bytes, Py_SIZE(self))
3121 #endif
3122 else
3123 #ifdef Py_USING_UNICODE
3124 latin1 = PyUnicode_FromString("");
3125 #else
3126 latin1 = PyString_FromString("");
3127 #endif
3129 dict = PyObject_GetAttrString((PyObject *)self, "__dict__");
3130 if (dict == NULL) {
3131 PyErr_Clear();
3132 dict = Py_None;
3133 Py_INCREF(dict);
3136 return Py_BuildValue("(O(Ns)N)", Py_TYPE(self), latin1, "latin-1", dict);
3139 PyDoc_STRVAR(sizeof_doc,
3140 "B.__sizeof__() -> int\n\
3142 Returns the size of B in memory, in bytes");
3143 static PyObject *
3144 bytearray_sizeof(PyByteArrayObject *self)
3146 Py_ssize_t res;
3148 res = sizeof(PyByteArrayObject) + self->ob_alloc * sizeof(char);
3149 return PyInt_FromSsize_t(res);
3152 static PySequenceMethods bytearray_as_sequence = {
3153 (lenfunc)bytearray_length, /* sq_length */
3154 (binaryfunc)PyByteArray_Concat, /* sq_concat */
3155 (ssizeargfunc)bytearray_repeat, /* sq_repeat */
3156 (ssizeargfunc)bytearray_getitem, /* sq_item */
3157 0, /* sq_slice */
3158 (ssizeobjargproc)bytearray_setitem, /* sq_ass_item */
3159 0, /* sq_ass_slice */
3160 (objobjproc)bytearray_contains, /* sq_contains */
3161 (binaryfunc)bytearray_iconcat, /* sq_inplace_concat */
3162 (ssizeargfunc)bytearray_irepeat, /* sq_inplace_repeat */
3165 static PyMappingMethods bytearray_as_mapping = {
3166 (lenfunc)bytearray_length,
3167 (binaryfunc)bytearray_subscript,
3168 (objobjargproc)bytearray_ass_subscript,
3171 static PyBufferProcs bytearray_as_buffer = {
3172 (readbufferproc)bytearray_buffer_getreadbuf,
3173 (writebufferproc)bytearray_buffer_getwritebuf,
3174 (segcountproc)bytearray_buffer_getsegcount,
3175 (charbufferproc)bytearray_buffer_getcharbuf,
3176 (getbufferproc)bytearray_getbuffer,
3177 (releasebufferproc)bytearray_releasebuffer,
3180 static PyMethodDef
3181 bytearray_methods[] = {
3182 {"__alloc__", (PyCFunction)bytearray_alloc, METH_NOARGS, alloc_doc},
3183 {"__reduce__", (PyCFunction)bytearray_reduce, METH_NOARGS, reduce_doc},
3184 {"__sizeof__", (PyCFunction)bytearray_sizeof, METH_NOARGS, sizeof_doc},
3185 {"append", (PyCFunction)bytearray_append, METH_O, append__doc__},
3186 {"capitalize", (PyCFunction)stringlib_capitalize, METH_NOARGS,
3187 _Py_capitalize__doc__},
3188 {"center", (PyCFunction)stringlib_center, METH_VARARGS, center__doc__},
3189 {"count", (PyCFunction)bytearray_count, METH_VARARGS, count__doc__},
3190 {"decode", (PyCFunction)bytearray_decode, METH_VARARGS, decode_doc},
3191 {"endswith", (PyCFunction)bytearray_endswith, METH_VARARGS, endswith__doc__},
3192 {"expandtabs", (PyCFunction)stringlib_expandtabs, METH_VARARGS,
3193 expandtabs__doc__},
3194 {"extend", (PyCFunction)bytearray_extend, METH_O, extend__doc__},
3195 {"find", (PyCFunction)bytearray_find, METH_VARARGS, find__doc__},
3196 {"fromhex", (PyCFunction)bytearray_fromhex, METH_VARARGS|METH_CLASS,
3197 fromhex_doc},
3198 {"index", (PyCFunction)bytearray_index, METH_VARARGS, index__doc__},
3199 {"insert", (PyCFunction)bytearray_insert, METH_VARARGS, insert__doc__},
3200 {"isalnum", (PyCFunction)stringlib_isalnum, METH_NOARGS,
3201 _Py_isalnum__doc__},
3202 {"isalpha", (PyCFunction)stringlib_isalpha, METH_NOARGS,
3203 _Py_isalpha__doc__},
3204 {"isdigit", (PyCFunction)stringlib_isdigit, METH_NOARGS,
3205 _Py_isdigit__doc__},
3206 {"islower", (PyCFunction)stringlib_islower, METH_NOARGS,
3207 _Py_islower__doc__},
3208 {"isspace", (PyCFunction)stringlib_isspace, METH_NOARGS,
3209 _Py_isspace__doc__},
3210 {"istitle", (PyCFunction)stringlib_istitle, METH_NOARGS,
3211 _Py_istitle__doc__},
3212 {"isupper", (PyCFunction)stringlib_isupper, METH_NOARGS,
3213 _Py_isupper__doc__},
3214 {"join", (PyCFunction)bytearray_join, METH_O, join_doc},
3215 {"ljust", (PyCFunction)stringlib_ljust, METH_VARARGS, ljust__doc__},
3216 {"lower", (PyCFunction)stringlib_lower, METH_NOARGS, _Py_lower__doc__},
3217 {"lstrip", (PyCFunction)bytearray_lstrip, METH_VARARGS, lstrip__doc__},
3218 {"partition", (PyCFunction)bytearray_partition, METH_O, partition__doc__},
3219 {"pop", (PyCFunction)bytearray_pop, METH_VARARGS, pop__doc__},
3220 {"remove", (PyCFunction)bytearray_remove, METH_O, remove__doc__},
3221 {"replace", (PyCFunction)bytearray_replace, METH_VARARGS, replace__doc__},
3222 {"reverse", (PyCFunction)bytearray_reverse, METH_NOARGS, reverse__doc__},
3223 {"rfind", (PyCFunction)bytearray_rfind, METH_VARARGS, rfind__doc__},
3224 {"rindex", (PyCFunction)bytearray_rindex, METH_VARARGS, rindex__doc__},
3225 {"rjust", (PyCFunction)stringlib_rjust, METH_VARARGS, rjust__doc__},
3226 {"rpartition", (PyCFunction)bytearray_rpartition, METH_O, rpartition__doc__},
3227 {"rsplit", (PyCFunction)bytearray_rsplit, METH_VARARGS, rsplit__doc__},
3228 {"rstrip", (PyCFunction)bytearray_rstrip, METH_VARARGS, rstrip__doc__},
3229 {"split", (PyCFunction)bytearray_split, METH_VARARGS, split__doc__},
3230 {"splitlines", (PyCFunction)stringlib_splitlines, METH_VARARGS,
3231 splitlines__doc__},
3232 {"startswith", (PyCFunction)bytearray_startswith, METH_VARARGS ,
3233 startswith__doc__},
3234 {"strip", (PyCFunction)bytearray_strip, METH_VARARGS, strip__doc__},
3235 {"swapcase", (PyCFunction)stringlib_swapcase, METH_NOARGS,
3236 _Py_swapcase__doc__},
3237 {"title", (PyCFunction)stringlib_title, METH_NOARGS, _Py_title__doc__},
3238 {"translate", (PyCFunction)bytearray_translate, METH_VARARGS,
3239 translate__doc__},
3240 {"upper", (PyCFunction)stringlib_upper, METH_NOARGS, _Py_upper__doc__},
3241 {"zfill", (PyCFunction)stringlib_zfill, METH_VARARGS, zfill__doc__},
3242 {NULL}
3245 PyDoc_STRVAR(bytearray_doc,
3246 "bytearray(iterable_of_ints) -> bytearray.\n\
3247 bytearray(string, encoding[, errors]) -> bytearray.\n\
3248 bytearray(bytes_or_bytearray) -> mutable copy of bytes_or_bytearray.\n\
3249 bytearray(memory_view) -> bytearray.\n\
3251 Construct an mutable bytearray object from:\n\
3252 - an iterable yielding integers in range(256)\n\
3253 - a text string encoded using the specified encoding\n\
3254 - a bytes or a bytearray object\n\
3255 - any object implementing the buffer API.\n\
3257 bytearray(int) -> bytearray.\n\
3259 Construct a zero-initialized bytearray of the given length.");
3262 static PyObject *bytearray_iter(PyObject *seq);
3264 PyTypeObject PyByteArray_Type = {
3265 PyVarObject_HEAD_INIT(&PyType_Type, 0)
3266 "bytearray",
3267 sizeof(PyByteArrayObject),
3269 (destructor)bytearray_dealloc, /* tp_dealloc */
3270 0, /* tp_print */
3271 0, /* tp_getattr */
3272 0, /* tp_setattr */
3273 0, /* tp_compare */
3274 (reprfunc)bytearray_repr, /* tp_repr */
3275 0, /* tp_as_number */
3276 &bytearray_as_sequence, /* tp_as_sequence */
3277 &bytearray_as_mapping, /* tp_as_mapping */
3278 0, /* tp_hash */
3279 0, /* tp_call */
3280 bytearray_str, /* tp_str */
3281 PyObject_GenericGetAttr, /* tp_getattro */
3282 0, /* tp_setattro */
3283 &bytearray_as_buffer, /* tp_as_buffer */
3284 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE |
3285 Py_TPFLAGS_HAVE_NEWBUFFER, /* tp_flags */
3286 bytearray_doc, /* tp_doc */
3287 0, /* tp_traverse */
3288 0, /* tp_clear */
3289 (richcmpfunc)bytearray_richcompare, /* tp_richcompare */
3290 0, /* tp_weaklistoffset */
3291 bytearray_iter, /* tp_iter */
3292 0, /* tp_iternext */
3293 bytearray_methods, /* tp_methods */
3294 0, /* tp_members */
3295 0, /* tp_getset */
3296 0, /* tp_base */
3297 0, /* tp_dict */
3298 0, /* tp_descr_get */
3299 0, /* tp_descr_set */
3300 0, /* tp_dictoffset */
3301 (initproc)bytearray_init, /* tp_init */
3302 PyType_GenericAlloc, /* tp_alloc */
3303 PyType_GenericNew, /* tp_new */
3304 PyObject_Del, /* tp_free */
3307 /*********************** Bytes Iterator ****************************/
3309 typedef struct {
3310 PyObject_HEAD
3311 Py_ssize_t it_index;
3312 PyByteArrayObject *it_seq; /* Set to NULL when iterator is exhausted */
3313 } bytesiterobject;
3315 static void
3316 bytearrayiter_dealloc(bytesiterobject *it)
3318 _PyObject_GC_UNTRACK(it);
3319 Py_XDECREF(it->it_seq);
3320 PyObject_GC_Del(it);
3323 static int
3324 bytearrayiter_traverse(bytesiterobject *it, visitproc visit, void *arg)
3326 Py_VISIT(it->it_seq);
3327 return 0;
3330 static PyObject *
3331 bytearrayiter_next(bytesiterobject *it)
3333 PyByteArrayObject *seq;
3334 PyObject *item;
3336 assert(it != NULL);
3337 seq = it->it_seq;
3338 if (seq == NULL)
3339 return NULL;
3340 assert(PyByteArray_Check(seq));
3342 if (it->it_index < PyByteArray_GET_SIZE(seq)) {
3343 item = PyInt_FromLong(
3344 (unsigned char)seq->ob_bytes[it->it_index]);
3345 if (item != NULL)
3346 ++it->it_index;
3347 return item;
3350 Py_DECREF(seq);
3351 it->it_seq = NULL;
3352 return NULL;
3355 static PyObject *
3356 bytesarrayiter_length_hint(bytesiterobject *it)
3358 Py_ssize_t len = 0;
3359 if (it->it_seq)
3360 len = PyByteArray_GET_SIZE(it->it_seq) - it->it_index;
3361 return PyInt_FromSsize_t(len);
3364 PyDoc_STRVAR(length_hint_doc,
3365 "Private method returning an estimate of len(list(it)).");
3367 static PyMethodDef bytearrayiter_methods[] = {
3368 {"__length_hint__", (PyCFunction)bytesarrayiter_length_hint, METH_NOARGS,
3369 length_hint_doc},
3370 {NULL, NULL} /* sentinel */
3373 PyTypeObject PyByteArrayIter_Type = {
3374 PyVarObject_HEAD_INIT(&PyType_Type, 0)
3375 "bytearray_iterator", /* tp_name */
3376 sizeof(bytesiterobject), /* tp_basicsize */
3377 0, /* tp_itemsize */
3378 /* methods */
3379 (destructor)bytearrayiter_dealloc, /* tp_dealloc */
3380 0, /* tp_print */
3381 0, /* tp_getattr */
3382 0, /* tp_setattr */
3383 0, /* tp_compare */
3384 0, /* tp_repr */
3385 0, /* tp_as_number */
3386 0, /* tp_as_sequence */
3387 0, /* tp_as_mapping */
3388 0, /* tp_hash */
3389 0, /* tp_call */
3390 0, /* tp_str */
3391 PyObject_GenericGetAttr, /* tp_getattro */
3392 0, /* tp_setattro */
3393 0, /* tp_as_buffer */
3394 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /* tp_flags */
3395 0, /* tp_doc */
3396 (traverseproc)bytearrayiter_traverse, /* tp_traverse */
3397 0, /* tp_clear */
3398 0, /* tp_richcompare */
3399 0, /* tp_weaklistoffset */
3400 PyObject_SelfIter, /* tp_iter */
3401 (iternextfunc)bytearrayiter_next, /* tp_iternext */
3402 bytearrayiter_methods, /* tp_methods */
3406 static PyObject *
3407 bytearray_iter(PyObject *seq)
3409 bytesiterobject *it;
3411 if (!PyByteArray_Check(seq)) {
3412 PyErr_BadInternalCall();
3413 return NULL;
3415 it = PyObject_GC_New(bytesiterobject, &PyByteArrayIter_Type);
3416 if (it == NULL)
3417 return NULL;
3418 it->it_index = 0;
3419 Py_INCREF(seq);
3420 it->it_seq = (PyByteArrayObject *)seq;
3421 _PyObject_GC_TRACK(it);
3422 return (PyObject *)it;