File: bytearray_coercion.pyx

package info (click to toggle)
cython 3.0.11%2Bdfsg-2
  • links: PTS, VCS
  • area: main
  • in suites: sid, trixie
  • size: 19,092 kB
  • sloc: python: 83,539; ansic: 18,831; cpp: 1,402; xml: 1,031; javascript: 511; makefile: 403; sh: 204; sed: 11
file content (182 lines) | stat: -rw-r--r-- 4,450 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
# mode: run

# NOTE: Py2.6+ only


cimport cython

cpdef bytearray coerce_to_charptr(char* b):
    """
    >>> b = bytearray(b'abc')
    >>> coerced = coerce_to_charptr(b)
    >>> coerced == b or (coerced, b)
    True
    >>> isinstance(coerced, bytearray) or type(coerced)
    True
    """
    return b

def coerce_to_charptrs(bytearray b):
    """
    >>> b = bytearray(b'abc')
    >>> coerce_to_charptrs(b)
    True
    """
    cdef char* cs = b
    cdef unsigned char* ucs = b
    cdef signed char* scs = b
    return b == <bytearray>cs == <bytearray> ucs == <bytearray>scs

cpdef bytearray coerce_charptr_slice(char* b):
    """
    >>> b = bytearray(b'abc')
    >>> coerced = coerce_charptr_slice(b)
    >>> coerced == b[:2] or (coerced, b)
    True
    >>> isinstance(coerced, bytearray) or type(coerced)
    True
    """
    return b[:2]


def infer_concatenation_types(bytearray b):
    """
    >>> b = bytearray(b'a\\xFEc')
    >>> b2, c, d, e, tb, tc, td, te = infer_concatenation_types(b)
    >>> tb, tc, td, te
    ('bytearray object', 'bytearray object', 'bytearray object', 'bytearray object')
    >>> b2, c, d, e
    (bytearray(b'a\\xfec'), bytearray(b'a\\xfeca\\xfec'), bytearray(b'a\\xfeca\\xfec'), bytearray(b'a\\xfeca\\xfec'))
    """
    c = b[:]
    c += b[:]

    d = b[:]
    d *= 2

    e = b + b

    return b, c, d, e, cython.typeof(b), cython.typeof(c), cython.typeof(d), cython.typeof(e)


def infer_index_types(bytearray b):
    """
    >>> b = bytearray(b'a\\xFEc')
    >>> print(infer_index_types(b))
    (254, 254, 254, 'unsigned char', 'unsigned char', 'unsigned char', 'int')
    """
    c = b[1]
    with cython.wraparound(False):
        d = b[1]
    with cython.boundscheck(False):
        e = b[1]
    return c, d, e, cython.typeof(c), cython.typeof(d), cython.typeof(e), cython.typeof(b[1])


def infer_slice_types(bytearray b):
    """
    >>> b = bytearray(b'abc')
    >>> print(infer_slice_types(b))
    (bytearray(b'bc'), bytearray(b'bc'), bytearray(b'bc'), 'bytearray object', 'bytearray object', 'bytearray object', 'bytearray object')
    """
    c = b[1:]
    with cython.boundscheck(False):
        d = b[1:]
    with cython.boundscheck(False), cython.wraparound(False):
        e = b[1:]
    return c, d, e, cython.typeof(c), cython.typeof(d), cython.typeof(e), cython.typeof(b[1:])


def assign_to_index(bytearray b, value):
    """
    >>> b = bytearray(b'0abcdefg')
    >>> assign_to_index(b, 1)
    bytearray(b'xyzee\\x01h')
    >>> b
    bytearray(b'xyzee\\x01h')

    >>> assign_to_index(bytearray(b'0ABCDEFG'), 40)
    bytearray(b'xyzEE(o')

    >>> assign_to_index(bytearray(b'0abcdefg'), -1)
    Traceback (most recent call last):
    OverflowError: can't convert negative value to unsigned char

    >>> assign_to_index(bytearray(b'0abcdef\\x00'), 255)
    bytearray(b'xyzee\\xff\\xff')
    >>> assign_to_index(bytearray(b'0abcdef\\x01'), 255)
    Traceback (most recent call last):
    OverflowError: value too large to convert to unsigned char
    >>> assign_to_index(bytearray(b'0abcdef\\x00'), 256)
    Traceback (most recent call last):
    OverflowError: value too large to convert to unsigned char
    """
    b[1] = 'x'
    b[2] = b'y'
    b[3] = c'z'
    b[4] += 1
    b[5] |= 1
    b[6] = value
    b[7] += value
    del b[0]

    try:
        b[7] = 1
    except IndexError:
        pass
    else:
        assert False, "IndexError not raised"

    try:
        b[int(str(len(b)))] = 1   # test non-int-index assignment
    except IndexError:
        pass
    else:
        assert False, "IndexError not raised"

    return b


def check_bounds(int cvalue):
    """
    >>> check_bounds(0)
    0
    >>> check_bounds(255)
    255
    >>> check_bounds(256)
    Traceback (most recent call last):
    ValueError: byte must be in range(0, 256)
    >>> check_bounds(-1)
    Traceback (most recent call last):
    ValueError: byte must be in range(0, 256)
    """
    b = bytearray(b'x')

    try:
        b[0] = 256
    except ValueError:
        pass
    else:
        assert False, "ValueError not raised"

    try:
        b[0] = -1
    except ValueError:
        pass
    else:
        assert False, "ValueError not raised"

    b[0] = cvalue
    return b[0]


def nogil_assignment(bytearray x, int value):
    """
    >>> b = bytearray(b'abc')
    >>> nogil_assignment(b, ord('y'))
    >>> b
    bytearray(b'xyc')
    """
    with nogil:
        x[0] = 'x'
        x[1] = value