summaryrefslogtreecommitdiff
path: root/Modules/binascii.c
diff options
context:
space:
mode:
Diffstat (limited to 'Modules/binascii.c')
-rw-r--r--Modules/binascii.c287
1 files changed, 137 insertions, 150 deletions
diff --git a/Modules/binascii.c b/Modules/binascii.c
index 125c1cb02d..ee66a48ebc 100644
--- a/Modules/binascii.c
+++ b/Modules/binascii.c
@@ -74,7 +74,7 @@ static PyObject *Incomplete;
#define SKIP 0x7E
#define FAIL 0x7D
-static unsigned char table_a2b_hqx[256] = {
+static const unsigned char table_a2b_hqx[256] = {
/* ^@ ^A ^B ^C ^D ^E ^F ^G */
/* 0*/ FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
/* \b \t \n ^K ^L \r ^N ^O */
@@ -125,10 +125,10 @@ static unsigned char table_a2b_hqx[256] = {
FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL, FAIL,
};
-static unsigned char table_b2a_hqx[] =
+static const unsigned char table_b2a_hqx[] =
"!\"#$%&'()*+,-012345689@ABCDEFGHIJKLMNPQRSTUVXYZ[`abcdefhijklmpqr";
-static char table_a2b_base64[] = {
+static const char table_a2b_base64[] = {
-1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1,
-1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1,
-1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,62, -1,-1,-1,63,
@@ -144,12 +144,12 @@ static char table_a2b_base64[] = {
/* Max binary chunk size; limited only by available memory */
#define BASE64_MAXBIN ((PY_SSIZE_T_MAX - 3) / 2)
-static unsigned char table_b2a_base64[] =
+static const unsigned char table_b2a_base64[] =
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
-static unsigned short crctab_hqx[256] = {
+static const unsigned short crctab_hqx[256] = {
0x0000, 0x1021, 0x2042, 0x3063, 0x4084, 0x50a5, 0x60c6, 0x70e7,
0x8108, 0x9129, 0xa14a, 0xb16b, 0xc18c, 0xd1ad, 0xe1ce, 0xf1ef,
0x1231, 0x0210, 0x3273, 0x2252, 0x52b5, 0x4294, 0x72f7, 0x62d6,
@@ -256,7 +256,8 @@ static PyObject *
binascii_a2b_uu_impl(PyObject *module, Py_buffer *data)
/*[clinic end generated code: output=e027f8e0b0598742 input=7cafeaf73df63d1c]*/
{
- unsigned char *ascii_data, *bin_data;
+ const unsigned char *ascii_data;
+ unsigned char *bin_data;
int leftbits = 0;
unsigned char this_ch;
unsigned int leftchar = 0;
@@ -342,13 +343,15 @@ static PyObject *
binascii_b2a_uu_impl(PyObject *module, Py_buffer *data)
/*[clinic end generated code: output=0070670e52e4aa6b input=00fdf458ce8b465b]*/
{
- unsigned char *ascii_data, *bin_data;
+ unsigned char *ascii_data;
+ const unsigned char *bin_data;
int leftbits = 0;
unsigned char this_ch;
unsigned int leftchar = 0;
- PyObject *rv;
- Py_ssize_t bin_len;
+ Py_ssize_t bin_len, out_len;
+ _PyBytesWriter writer;
+ _PyBytesWriter_Init(&writer);
bin_data = data->buf;
bin_len = data->len;
if ( bin_len > 45 ) {
@@ -358,9 +361,10 @@ binascii_b2a_uu_impl(PyObject *module, Py_buffer *data)
}
/* We're lazy and allocate to much (fixed up later) */
- if ( (rv=PyBytes_FromStringAndSize(NULL, 2 + (bin_len+2)/3*4)) == NULL )
+ out_len = 2 + (bin_len + 2) / 3 * 4;
+ ascii_data = _PyBytesWriter_Alloc(&writer, out_len);
+ if (ascii_data == NULL)
return NULL;
- ascii_data = (unsigned char *)PyBytes_AS_STRING(rv);
/* Store the length */
*ascii_data++ = ' ' + (bin_len & 077);
@@ -382,17 +386,12 @@ binascii_b2a_uu_impl(PyObject *module, Py_buffer *data)
}
*ascii_data++ = '\n'; /* Append a courtesy newline */
- if (_PyBytes_Resize(&rv,
- (ascii_data -
- (unsigned char *)PyBytes_AS_STRING(rv))) < 0) {
- Py_CLEAR(rv);
- }
- return rv;
+ return _PyBytesWriter_Finish(&writer, ascii_data);
}
static int
-binascii_find_valid(unsigned char *s, Py_ssize_t slen, int num)
+binascii_find_valid(const unsigned char *s, Py_ssize_t slen, int num)
{
/* Finds & returns the (num+1)th
** valid character for base64, or -1 if none.
@@ -429,13 +428,14 @@ static PyObject *
binascii_a2b_base64_impl(PyObject *module, Py_buffer *data)
/*[clinic end generated code: output=0628223f19fd3f9b input=5872acf6e1cac243]*/
{
- unsigned char *ascii_data, *bin_data;
+ const unsigned char *ascii_data;
+ unsigned char *bin_data;
int leftbits = 0;
unsigned char this_ch;
unsigned int leftchar = 0;
- PyObject *rv;
Py_ssize_t ascii_len, bin_len;
int quad_pos = 0;
+ _PyBytesWriter writer;
ascii_data = data->buf;
ascii_len = data->len;
@@ -447,11 +447,12 @@ binascii_a2b_base64_impl(PyObject *module, Py_buffer *data)
bin_len = ((ascii_len+3)/4)*3; /* Upper bound, corrected later */
+ _PyBytesWriter_Init(&writer);
+
/* Allocate the buffer */
- if ( (rv=PyBytes_FromStringAndSize(NULL, bin_len)) == NULL )
+ bin_data = _PyBytesWriter_Alloc(&writer, bin_len);
+ if (bin_data == NULL)
return NULL;
- bin_data = (unsigned char *)PyBytes_AS_STRING(rv);
- bin_len = 0;
for( ; ascii_len > 0; ascii_len--, ascii_data++) {
this_ch = *ascii_data;
@@ -496,31 +497,17 @@ binascii_a2b_base64_impl(PyObject *module, Py_buffer *data)
if ( leftbits >= 8 ) {
leftbits -= 8;
*bin_data++ = (leftchar >> leftbits) & 0xff;
- bin_len++;
leftchar &= ((1 << leftbits) - 1);
}
}
if (leftbits != 0) {
PyErr_SetString(Error, "Incorrect padding");
- Py_DECREF(rv);
+ _PyBytesWriter_Dealloc(&writer);
return NULL;
}
- /* And set string size correctly. If the result string is empty
- ** (because the input was all invalid) return the shared empty
- ** string instead; _PyBytes_Resize() won't do this for us.
- */
- if (bin_len > 0) {
- if (_PyBytes_Resize(&rv, bin_len) < 0) {
- Py_CLEAR(rv);
- }
- }
- else {
- Py_DECREF(rv);
- rv = PyBytes_FromStringAndSize("", 0);
- }
- return rv;
+ return _PyBytesWriter_Finish(&writer, bin_data);
}
@@ -528,24 +515,27 @@ binascii_a2b_base64_impl(PyObject *module, Py_buffer *data)
binascii.b2a_base64
data: Py_buffer
- /
+ *
+ newline: int(c_default="1") = True
Base64-code line of data.
[clinic start generated code]*/
static PyObject *
-binascii_b2a_base64_impl(PyObject *module, Py_buffer *data)
-/*[clinic end generated code: output=4d96663170778dc3 input=14ec4e47371174a9]*/
+binascii_b2a_base64_impl(PyObject *module, Py_buffer *data, int newline)
+/*[clinic end generated code: output=4ad62c8e8485d3b3 input=7b2ea6fa38d8924c]*/
{
- unsigned char *ascii_data, *bin_data;
+ unsigned char *ascii_data;
+ const unsigned char *bin_data;
int leftbits = 0;
unsigned char this_ch;
unsigned int leftchar = 0;
- PyObject *rv;
- Py_ssize_t bin_len;
+ Py_ssize_t bin_len, out_len;
+ _PyBytesWriter writer;
bin_data = data->buf;
bin_len = data->len;
+ _PyBytesWriter_Init(&writer);
assert(bin_len >= 0);
@@ -555,11 +545,14 @@ binascii_b2a_base64_impl(PyObject *module, Py_buffer *data)
}
/* We're lazy and allocate too much (fixed up later).
- "+3" leaves room for up to two pad characters and a trailing
- newline. Note that 'b' gets encoded as 'Yg==\n' (1 in, 5 out). */
- if ( (rv=PyBytes_FromStringAndSize(NULL, bin_len*2 + 3)) == NULL )
+ "+2" leaves room for up to two pad characters.
+ Note that 'b' gets encoded as 'Yg==\n' (1 in, 5 out). */
+ out_len = bin_len*2 + 2;
+ if (newline)
+ out_len++;
+ ascii_data = _PyBytesWriter_Alloc(&writer, out_len);
+ if (ascii_data == NULL)
return NULL;
- ascii_data = (unsigned char *)PyBytes_AS_STRING(rv);
for( ; bin_len > 0 ; bin_len--, bin_data++ ) {
/* Shift the data into our buffer */
@@ -581,14 +574,10 @@ binascii_b2a_base64_impl(PyObject *module, Py_buffer *data)
*ascii_data++ = table_b2a_base64[(leftchar&0xf) << 2];
*ascii_data++ = BASE64_PAD;
}
- *ascii_data++ = '\n'; /* Append a courtesy newline */
+ if (newline)
+ *ascii_data++ = '\n'; /* Append a courtesy newline */
- if (_PyBytes_Resize(&rv,
- (ascii_data -
- (unsigned char *)PyBytes_AS_STRING(rv))) < 0) {
- Py_CLEAR(rv);
- }
- return rv;
+ return _PyBytesWriter_Finish(&writer, ascii_data);
}
/*[clinic input]
@@ -604,16 +593,19 @@ static PyObject *
binascii_a2b_hqx_impl(PyObject *module, Py_buffer *data)
/*[clinic end generated code: output=4d6d8c54d54ea1c1 input=0d914c680e0eed55]*/
{
- unsigned char *ascii_data, *bin_data;
+ const unsigned char *ascii_data;
+ unsigned char *bin_data;
int leftbits = 0;
unsigned char this_ch;
unsigned int leftchar = 0;
- PyObject *rv;
+ PyObject *res;
Py_ssize_t len;
int done = 0;
+ _PyBytesWriter writer;
ascii_data = data->buf;
len = data->len;
+ _PyBytesWriter_Init(&writer);
assert(len >= 0);
@@ -623,9 +615,9 @@ binascii_a2b_hqx_impl(PyObject *module, Py_buffer *data)
/* Allocate a string that is too big (fixed later)
Add two to the initial length to prevent interning which
would preclude subsequent resizing. */
- if ( (rv=PyBytes_FromStringAndSize(NULL, len+2)) == NULL )
+ bin_data = _PyBytesWriter_Alloc(&writer, len + 2);
+ if (bin_data == NULL)
return NULL;
- bin_data = (unsigned char *)PyBytes_AS_STRING(rv);
for( ; len > 0 ; len--, ascii_data++ ) {
/* Get the byte and look it up */
@@ -634,7 +626,7 @@ binascii_a2b_hqx_impl(PyObject *module, Py_buffer *data)
continue;
if ( this_ch == FAIL ) {
PyErr_SetString(Error, "Illegal char");
- Py_DECREF(rv);
+ _PyBytesWriter_Dealloc(&writer);
return NULL;
}
if ( this_ch == DONE ) {
@@ -656,21 +648,14 @@ binascii_a2b_hqx_impl(PyObject *module, Py_buffer *data)
if ( leftbits && !done ) {
PyErr_SetString(Incomplete,
"String has incomplete number of bytes");
- Py_DECREF(rv);
+ _PyBytesWriter_Dealloc(&writer);
return NULL;
}
- if (_PyBytes_Resize(&rv,
- (bin_data -
- (unsigned char *)PyBytes_AS_STRING(rv))) < 0) {
- Py_CLEAR(rv);
- }
- if (rv) {
- PyObject *rrv = Py_BuildValue("Oi", rv, done);
- Py_DECREF(rv);
- return rrv;
- }
- return NULL;
+ res = _PyBytesWriter_Finish(&writer, bin_data);
+ if (res == NULL)
+ return NULL;
+ return Py_BuildValue("Ni", res, done);
}
@@ -687,11 +672,13 @@ static PyObject *
binascii_rlecode_hqx_impl(PyObject *module, Py_buffer *data)
/*[clinic end generated code: output=393d79338f5f5629 input=e1f1712447a82b09]*/
{
- unsigned char *in_data, *out_data;
- PyObject *rv;
+ const unsigned char *in_data;
+ unsigned char *out_data;
unsigned char ch;
Py_ssize_t in, inend, len;
+ _PyBytesWriter writer;
+ _PyBytesWriter_Init(&writer);
in_data = data->buf;
len = data->len;
@@ -701,9 +688,9 @@ binascii_rlecode_hqx_impl(PyObject *module, Py_buffer *data)
return PyErr_NoMemory();
/* Worst case: output is twice as big as input (fixed later) */
- if ( (rv=PyBytes_FromStringAndSize(NULL, len*2+2)) == NULL )
+ out_data = _PyBytesWriter_Alloc(&writer, len * 2 + 2);
+ if (out_data == NULL)
return NULL;
- out_data = (unsigned char *)PyBytes_AS_STRING(rv);
for( in=0; in<len; in++) {
ch = in_data[in];
@@ -729,12 +716,8 @@ binascii_rlecode_hqx_impl(PyObject *module, Py_buffer *data)
}
}
}
- if (_PyBytes_Resize(&rv,
- (out_data -
- (unsigned char *)PyBytes_AS_STRING(rv))) < 0) {
- Py_CLEAR(rv);
- }
- return rv;
+
+ return _PyBytesWriter_Finish(&writer, out_data);
}
@@ -751,15 +734,17 @@ static PyObject *
binascii_b2a_hqx_impl(PyObject *module, Py_buffer *data)
/*[clinic end generated code: output=d0aa5a704bc9f7de input=9596ebe019fe12ba]*/
{
- unsigned char *ascii_data, *bin_data;
+ unsigned char *ascii_data;
+ const unsigned char *bin_data;
int leftbits = 0;
unsigned char this_ch;
unsigned int leftchar = 0;
- PyObject *rv;
Py_ssize_t len;
+ _PyBytesWriter writer;
bin_data = data->buf;
len = data->len;
+ _PyBytesWriter_Init(&writer);
assert(len >= 0);
@@ -767,9 +752,9 @@ binascii_b2a_hqx_impl(PyObject *module, Py_buffer *data)
return PyErr_NoMemory();
/* Allocate a buffer that is at least large enough */
- if ( (rv=PyBytes_FromStringAndSize(NULL, len*2+2)) == NULL )
+ ascii_data = _PyBytesWriter_Alloc(&writer, len * 2 + 2);
+ if (ascii_data == NULL)
return NULL;
- ascii_data = (unsigned char *)PyBytes_AS_STRING(rv);
for( ; len > 0 ; len--, bin_data++ ) {
/* Shift into our buffer, and output any 6bits ready */
@@ -786,12 +771,8 @@ binascii_b2a_hqx_impl(PyObject *module, Py_buffer *data)
leftchar <<= (6-leftbits);
*ascii_data++ = table_b2a_hqx[leftchar & 0x3f];
}
- if (_PyBytes_Resize(&rv,
- (ascii_data -
- (unsigned char *)PyBytes_AS_STRING(rv))) < 0) {
- Py_CLEAR(rv);
- }
- return rv;
+
+ return _PyBytesWriter_Finish(&writer, ascii_data);
}
@@ -808,13 +789,15 @@ static PyObject *
binascii_rledecode_hqx_impl(PyObject *module, Py_buffer *data)
/*[clinic end generated code: output=9826619565de1c6c input=54cdd49fc014402c]*/
{
- unsigned char *in_data, *out_data;
+ const unsigned char *in_data;
+ unsigned char *out_data;
unsigned char in_byte, in_repeat;
- PyObject *rv;
- Py_ssize_t in_len, out_len, out_len_left;
+ Py_ssize_t in_len;
+ _PyBytesWriter writer;
in_data = data->buf;
in_len = data->len;
+ _PyBytesWriter_Init(&writer);
assert(in_len >= 0);
@@ -825,59 +808,48 @@ binascii_rledecode_hqx_impl(PyObject *module, Py_buffer *data)
return PyErr_NoMemory();
/* Allocate a buffer of reasonable size. Resized when needed */
- out_len = in_len*2;
- if ( (rv=PyBytes_FromStringAndSize(NULL, out_len)) == NULL )
+ out_data = _PyBytesWriter_Alloc(&writer, in_len);
+ if (out_data == NULL)
return NULL;
- out_len_left = out_len;
- out_data = (unsigned char *)PyBytes_AS_STRING(rv);
+
+ /* Use overallocation */
+ writer.overallocate = 1;
/*
** We need two macros here to get/put bytes and handle
** end-of-buffer for input and output strings.
*/
-#define INBYTE(b) \
- do { \
- if ( --in_len < 0 ) { \
- PyErr_SetString(Incomplete, ""); \
- Py_DECREF(rv); \
- return NULL; \
- } \
- b = *in_data++; \
+#define INBYTE(b) \
+ do { \
+ if ( --in_len < 0 ) { \
+ PyErr_SetString(Incomplete, ""); \
+ goto error; \
+ } \
+ b = *in_data++; \
} while(0)
-#define OUTBYTE(b) \
- do { \
- if ( --out_len_left < 0 ) { \
- if ( out_len > PY_SSIZE_T_MAX / 2) return PyErr_NoMemory(); \
- if (_PyBytes_Resize(&rv, 2*out_len) < 0) \
- { Py_XDECREF(rv); return NULL; } \
- out_data = (unsigned char *)PyBytes_AS_STRING(rv) \
- + out_len; \
- out_len_left = out_len-1; \
- out_len = out_len * 2; \
- } \
- *out_data++ = b; \
- } while(0)
-
- /*
- ** Handle first byte separately (since we have to get angry
- ** in case of an orphaned RLE code).
- */
- INBYTE(in_byte);
+ /*
+ ** Handle first byte separately (since we have to get angry
+ ** in case of an orphaned RLE code).
+ */
+ INBYTE(in_byte);
if (in_byte == RUNCHAR) {
INBYTE(in_repeat);
+ /* only 1 byte will be written, but 2 bytes were preallocated:
+ subtract 1 byte to prevent overallocation */
+ writer.min_size--;
+
if (in_repeat != 0) {
/* Note Error, not Incomplete (which is at the end
** of the string only). This is a programmer error.
*/
PyErr_SetString(Error, "Orphaned RLE code at start");
- Py_DECREF(rv);
- return NULL;
+ goto error;
}
- OUTBYTE(RUNCHAR);
+ *out_data++ = RUNCHAR;
} else {
- OUTBYTE(in_byte);
+ *out_data++ = in_byte;
}
while( in_len > 0 ) {
@@ -885,26 +857,39 @@ binascii_rledecode_hqx_impl(PyObject *module, Py_buffer *data)
if (in_byte == RUNCHAR) {
INBYTE(in_repeat);
+ /* only 1 byte will be written, but 2 bytes were preallocated:
+ subtract 1 byte to prevent overallocation */
+ writer.min_size--;
+
if ( in_repeat == 0 ) {
/* Just an escaped RUNCHAR value */
- OUTBYTE(RUNCHAR);
+ *out_data++ = RUNCHAR;
} else {
/* Pick up value and output a sequence of it */
in_byte = out_data[-1];
+
+ /* enlarge the buffer if needed */
+ if (in_repeat > 1) {
+ /* -1 because we already preallocated 1 byte */
+ out_data = _PyBytesWriter_Prepare(&writer, out_data,
+ in_repeat - 1);
+ if (out_data == NULL)
+ goto error;
+ }
+
while ( --in_repeat > 0 )
- OUTBYTE(in_byte);
+ *out_data++ = in_byte;
}
} else {
/* Normal byte */
- OUTBYTE(in_byte);
+ *out_data++ = in_byte;
}
}
- if (_PyBytes_Resize(&rv,
- (out_data -
- (unsigned char *)PyBytes_AS_STRING(rv))) < 0) {
- Py_CLEAR(rv);
- }
- return rv;
+ return _PyBytesWriter_Finish(&writer, out_data);
+
+error:
+ _PyBytesWriter_Dealloc(&writer);
+ return NULL;
}
@@ -922,7 +907,7 @@ static unsigned int
binascii_crc_hqx_impl(PyObject *module, Py_buffer *data, unsigned int crc)
/*[clinic end generated code: output=8ec2a78590d19170 input=f18240ff8c705b79]*/
{
- unsigned char *bin_data;
+ const unsigned char *bin_data;
Py_ssize_t len;
crc &= 0xffff;
@@ -1000,7 +985,7 @@ binascii_crc_hqx_impl(PyObject *module, Py_buffer *data, unsigned int crc)
using byte-swap instructions.
********************************************************************/
-static unsigned int crc_32_tab[256] = {
+static const unsigned int crc_32_tab[256] = {
0x00000000U, 0x77073096U, 0xee0e612cU, 0x990951baU, 0x076dc419U,
0x706af48fU, 0xe963a535U, 0x9e6495a3U, 0x0edb8832U, 0x79dcb8a4U,
0xe0d5e91eU, 0x97d2d988U, 0x09b64c2bU, 0x7eb17cbdU, 0xe7b82d07U,
@@ -1073,7 +1058,7 @@ binascii_crc32_impl(PyObject *module, Py_buffer *data, unsigned int crc)
#ifdef USE_ZLIB_CRC32
/* This was taken from zlibmodule.c PyZlib_crc32 (but is PY_SSIZE_T_CLEAN) */
{
- Byte *buf;
+ const Byte *buf;
Py_ssize_t len;
int signed_val;
@@ -1084,7 +1069,7 @@ binascii_crc32_impl(PyObject *module, Py_buffer *data, unsigned int crc)
}
#else /* USE_ZLIB_CRC32 */
{ /* By Jim Ahlstrom; All rights transferred to CNRI */
- unsigned char *bin_data;
+ const unsigned char *bin_data;
Py_ssize_t len;
unsigned int result;
@@ -1167,7 +1152,7 @@ static PyObject *
binascii_a2b_hex_impl(PyObject *module, Py_buffer *hexstr)
/*[clinic end generated code: output=0cc1a139af0eeecb input=9e1e7f2f94db24fd]*/
{
- char* argbuf;
+ const char* argbuf;
Py_ssize_t arglen;
PyObject *retval;
char* retbuf;
@@ -1224,7 +1209,7 @@ binascii_unhexlify_impl(PyObject *module, Py_buffer *hexstr)
return binascii_a2b_hex_impl(module, hexstr);
}
-static int table_hex[128] = {
+static const int table_hex[128] = {
-1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1,
-1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1,
-1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1,
@@ -1255,7 +1240,8 @@ binascii_a2b_qp_impl(PyObject *module, Py_buffer *data, int header)
{
Py_ssize_t in, out;
char ch;
- unsigned char *ascii_data, *odata;
+ const unsigned char *ascii_data;
+ unsigned char *odata;
Py_ssize_t datalen = 0;
PyObject *rv;
@@ -1362,13 +1348,14 @@ binascii_b2a_qp_impl(PyObject *module, Py_buffer *data, int quotetabs,
/*[clinic end generated code: output=e9884472ebb1a94c input=7f2a9aaa008e92b2]*/
{
Py_ssize_t in, out;
- unsigned char *databuf, *odata;
+ const unsigned char *databuf;
+ unsigned char *odata;
Py_ssize_t datalen = 0, odatalen = 0;
PyObject *rv;
unsigned int linelen = 0;
unsigned char ch;
int crlf = 0;
- unsigned char *p;
+ const unsigned char *p;
databuf = data->buf;
datalen = data->len;
@@ -1377,7 +1364,7 @@ binascii_b2a_qp_impl(PyObject *module, Py_buffer *data, int quotetabs,
/* XXX: this function has the side effect of converting all of
* the end of lines to be the same depending on this detection
* here */
- p = (unsigned char *) memchr(databuf, '\n', datalen);
+ p = (const unsigned char *) memchr(databuf, '\n', datalen);
if ((p != NULL) && (p > databuf) && (*(p-1) == '\r'))
crlf = 1;