~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/_bencode_pyx.pyx

  • Committer: John Arbash Meinel
  • Date: 2009-06-04 17:12:29 UTC
  • mto: This revision was merged to the branch mainline in revision 4410.
  • Revision ID: john@arbash-meinel.com-20090604171229-kbgfatt63y3u3uh1
Some small tweaks to decoding strings (avoid passing over the length 2x)

Down to 1.1s (from 1.4s) for decoding all of bzr.dev.
Also, favor decoding strings and then lists in _decode_object, since that is the
frequency we have those types inside Revisions.

Show diffs side-by-side

added added

removed removed

Lines of Context:
98
98
            raise RuntimeError("too deeply nested")
99
99
        try:
100
100
            ch = self.tail[0]
101
 
            if ch == c'i':
102
 
                D_UPDATE_TAIL(self, 1)
103
 
                return self._decode_int()
104
 
            elif c'0' <= ch <= c'9':
 
101
            if c'0' <= ch <= c'9':
105
102
                return self._decode_string()
106
103
            elif ch == c'l':
107
104
                D_UPDATE_TAIL(self, 1)
108
105
                return self._decode_list()
 
106
            elif ch == c'i':
 
107
                D_UPDATE_TAIL(self, 1)
 
108
                return self._decode_int()
109
109
            elif ch == c'd':
110
110
                D_UPDATE_TAIL(self, 1)
111
111
                return self._decode_dict()
144
144
        return ret
145
145
 
146
146
    cdef object _decode_string(self):
147
 
        cdef int n, i
148
 
        i = self._read_digits(c':')
149
 
        n = strtol(self.tail, NULL, 10)
150
 
        D_UPDATE_TAIL(self, i+1)
 
147
        cdef int n
 
148
        cdef char *next_tail
 
149
        # strtol allows leading whitespace, negatives, and leading zeros
 
150
        # however, all callers have already checked that '0' <= tail[0] <= '9'
 
151
        # or they wouldn't have called _decode_string
 
152
        # strtol will stop at trailing whitespace, etc
 
153
        n = strtol(self.tail, &next_tail, 10)
 
154
        if next_tail == NULL or next_tail[0] != c':':
 
155
            raise ValueError('string len not terminated by ":"')
 
156
        # strtol allows leading zeros, so validate that we don't have that
 
157
        if (self.tail[0] == c'0'
 
158
            and (n != 0 or (next_tail - self.tail != 1))):
 
159
            raise ValueError('leading zeros are not allowed')
 
160
        D_UPDATE_TAIL(self, next_tail - self.tail + 1)
151
161
        if n == 0:
152
162
            return ''
153
163
        if n > self.size:
170
180
                else:
171
181
                    return result
172
182
            else:
 
183
                # As a quick shortcut, check to see if the next object is a
 
184
                # string, since we know that won't be creating recursion
 
185
                # if self.tail[0] >= c'0' and self.tail[0] <= c'9':
173
186
                PyList_Append(result, self._decode_object())
174
187
 
175
188
        raise ValueError('malformed list')
187
200
                return result
188
201
            else:
189
202
                # keys should be strings only
 
203
                if self.tail[0] < c'0' or self.tail[0] > c'9':
 
204
                    raise ValueError('key was not a simple string.')
190
205
                key = self._decode_string()
191
206
                if lastkey >= key:
192
207
                    raise ValueError('dict keys disordered')