summaryrefslogtreecommitdiff
path: root/Objects/bytearrayobject.c
diff options
context:
space:
mode:
authorMartin v. Löwis <martin@v.loewis.de>2011-09-28 07:41:54 +0200
committerMartin v. Löwis <martin@v.loewis.de>2011-09-28 07:41:54 +0200
commitd63a3b8beb4a0841cb59fb3515347ccaab34b733 (patch)
tree3b4e3cc63151c5a5a910c3550a190aefaea96ad4 /Objects/bytearrayobject.c
parent48d49497c50e79d14e9df9527d766ca3a0a38be5 (diff)
downloadcpython-git-d63a3b8beb4a0841cb59fb3515347ccaab34b733.tar.gz
Implement PEP 393.
Diffstat (limited to 'Objects/bytearrayobject.c')
-rw-r--r--Objects/bytearrayobject.c145
1 files changed, 74 insertions, 71 deletions
diff --git a/Objects/bytearrayobject.c b/Objects/bytearrayobject.c
index 11a0101bef..d294cd67b1 100644
--- a/Objects/bytearrayobject.c
+++ b/Objects/bytearrayobject.c
@@ -854,83 +854,79 @@ bytearray_repr(PyByteArrayObject *self)
const char *quote_prefix = "bytearray(b";
const char *quote_postfix = ")";
Py_ssize_t length = Py_SIZE(self);
- /* 14 == strlen(quote_prefix) + 2 + strlen(quote_postfix) */
+ /* 15 == strlen(quote_prefix) + 2 + strlen(quote_postfix) + 1 */
size_t newsize;
PyObject *v;
- if (length > (PY_SSIZE_T_MAX - 14) / 4) {
+ register Py_ssize_t i;
+ register char c;
+ register char *p;
+ int quote;
+ char *test, *start;
+ char *buffer;
+
+ if (length > (PY_SSIZE_T_MAX - 15) / 4) {
PyErr_SetString(PyExc_OverflowError,
"bytearray object is too large to make repr");
return NULL;
}
- newsize = 14 + 4 * length;
- v = PyUnicode_FromUnicode(NULL, newsize);
- if (v == NULL) {
+
+ newsize = 15 + length * 4;
+ buffer = PyMem_Malloc(newsize);
+ if (buffer == NULL) {
+ PyErr_NoMemory();
return NULL;
}
- else {
- register Py_ssize_t i;
- register Py_UNICODE c;
- register Py_UNICODE *p;
- int quote;
-
- /* Figure out which quote to use; single is preferred */
- quote = '\'';
- {
- char *test, *start;
- start = PyByteArray_AS_STRING(self);
- for (test = start; test < start+length; ++test) {
- if (*test == '"') {
- quote = '\''; /* back to single */
- goto decided;
- }
- else if (*test == '\'')
- quote = '"';
- }
- decided:
- ;
- }
- p = PyUnicode_AS_UNICODE(v);
- while (*quote_prefix)
- *p++ = *quote_prefix++;
- *p++ = quote;
-
- for (i = 0; i < length; i++) {
- /* There's at least enough room for a hex escape
- and a closing quote. */
- assert(newsize - (p - PyUnicode_AS_UNICODE(v)) >= 5);
- c = self->ob_bytes[i];
- if (c == '\'' || c == '\\')
- *p++ = '\\', *p++ = c;
- else if (c == '\t')
- *p++ = '\\', *p++ = 't';
- else if (c == '\n')
- *p++ = '\\', *p++ = 'n';
- else if (c == '\r')
- *p++ = '\\', *p++ = 'r';
- else if (c == 0)
- *p++ = '\\', *p++ = 'x', *p++ = '0', *p++ = '0';
- else if (c < ' ' || c >= 0x7f) {
- *p++ = '\\';
- *p++ = 'x';
- *p++ = hexdigits[(c & 0xf0) >> 4];
- *p++ = hexdigits[c & 0xf];
- }
- else
- *p++ = c;
- }
- assert(newsize - (p - PyUnicode_AS_UNICODE(v)) >= 1);
- *p++ = quote;
- while (*quote_postfix) {
- *p++ = *quote_postfix++;
+ /* Figure out which quote to use; single is preferred */
+ quote = '\'';
+ start = PyByteArray_AS_STRING(self);
+ for (test = start; test < start+length; ++test) {
+ if (*test == '"') {
+ quote = '\''; /* back to single */
+ break;
}
- *p = '\0';
- if (PyUnicode_Resize(&v, (p - PyUnicode_AS_UNICODE(v)))) {
- Py_DECREF(v);
- return NULL;
+ else if (*test == '\'')
+ quote = '"';
+ }
+
+ p = buffer;
+ while (*quote_prefix)
+ *p++ = *quote_prefix++;
+ *p++ = quote;
+
+ for (i = 0; i < length; i++) {
+ /* There's at least enough room for a hex escape
+ and a closing quote. */
+ assert(newsize - (p - buffer) >= 5);
+ c = self->ob_bytes[i];
+ if (c == '\'' || c == '\\')
+ *p++ = '\\', *p++ = c;
+ else if (c == '\t')
+ *p++ = '\\', *p++ = 't';
+ else if (c == '\n')
+ *p++ = '\\', *p++ = 'n';
+ else if (c == '\r')
+ *p++ = '\\', *p++ = 'r';
+ else if (c == 0)
+ *p++ = '\\', *p++ = 'x', *p++ = '0', *p++ = '0';
+ else if (c < ' ' || c >= 0x7f) {
+ *p++ = '\\';
+ *p++ = 'x';
+ *p++ = hexdigits[(c & 0xf0) >> 4];
+ *p++ = hexdigits[c & 0xf];
}
- return v;
+ else
+ *p++ = c;
+ }
+ assert(newsize - (p - buffer) >= 1);
+ *p++ = quote;
+ while (*quote_postfix) {
+ *p++ = *quote_postfix++;
}
+
+ v = PyUnicode_DecodeASCII(buffer, p - buffer, NULL);
+ PyMem_Free(buffer);
+ return v;
}
static PyObject *
@@ -1034,6 +1030,8 @@ bytearray_dealloc(PyByteArrayObject *self)
/* -------------------------------------------------------------------- */
/* Methods */
+#define FASTSEARCH fastsearch
+#define STRINGLIB(F) stringlib_##F
#define STRINGLIB_CHAR char
#define STRINGLIB_LEN PyByteArray_GET_SIZE
#define STRINGLIB_STR PyByteArray_AS_STRING
@@ -2651,15 +2649,20 @@ bytearray_fromhex(PyObject *cls, PyObject *args)
{
PyObject *newbytes, *hexobj;
char *buf;
- Py_UNICODE *hex;
Py_ssize_t hexlen, byteslen, i, j;
int top, bot;
+ void *data;
+ unsigned int kind;
if (!PyArg_ParseTuple(args, "U:fromhex", &hexobj))
return NULL;
assert(PyUnicode_Check(hexobj));
- hexlen = PyUnicode_GET_SIZE(hexobj);
- hex = PyUnicode_AS_UNICODE(hexobj);
+ if (PyUnicode_READY(hexobj))
+ return NULL;
+ kind = PyUnicode_KIND(hexobj);
+ data = PyUnicode_DATA(hexobj);
+ hexlen = PyUnicode_GET_LENGTH(hexobj);
+
byteslen = hexlen/2; /* This overestimates if there are spaces */
newbytes = PyByteArray_FromStringAndSize(NULL, byteslen);
if (!newbytes)
@@ -2667,12 +2670,12 @@ bytearray_fromhex(PyObject *cls, PyObject *args)
buf = PyByteArray_AS_STRING(newbytes);
for (i = j = 0; i < hexlen; i += 2) {
/* skip over spaces in the input */
- while (hex[i] == ' ')
+ while (PyUnicode_READ(kind, data, i) == ' ')
i++;
if (i >= hexlen)
break;
- top = hex_digit_to_int(hex[i]);
- bot = hex_digit_to_int(hex[i+1]);
+ top = hex_digit_to_int(PyUnicode_READ(kind, data, i));
+ bot = hex_digit_to_int(PyUnicode_READ(kind, data, i+1));
if (top == -1 || bot == -1) {
PyErr_Format(PyExc_ValueError,
"non-hexadecimal number found in "