Author: Antonio Cuni <[email protected]>
Branch: faster-rstruct-2
Changeset: r91234:b1e1e6b5e8bd
Date: 2017-05-11 00:46 +0200
http://bitbucket.org/pypy/pypy/changeset/b1e1e6b5e8bd/
Log: adapt pypy/module/struct to the new interface for packing, which
means to use MutableStringBuffer instead of StrinbBuilder everywhere
diff --git a/pypy/module/struct/formatiterator.py
b/pypy/module/struct/formatiterator.py
--- a/pypy/module/struct/formatiterator.py
+++ b/pypy/module/struct/formatiterator.py
@@ -2,7 +2,7 @@
maxint, intmask)
from rpython.rlib import jit
from rpython.rlib.objectmodel import specialize
-from rpython.rlib.rstring import StringBuilder
+from rpython.rlib.mutbuffer import MutableStringBuffer
from rpython.rlib.rstruct.error import StructError
from rpython.rlib.rstruct.formatiterator import FormatIterator
@@ -14,7 +14,12 @@
self.space = space
self.args_w = args_w
self.args_index = 0
- self.result = StringBuilder(size)
+ self.pos = 0
+ self.result = MutableStringBuffer(size)
+ self.needs_zeros = False # MutableStringBuffer is already 0-inizialized
+
+ def advance(self, count):
+ self.pos += count
# This *should* be always unroll safe, the only way to get here is by
# unroll the interpret function, which means the fmt is const, and thus
@@ -31,8 +36,8 @@
@jit.unroll_safe
def align(self, mask):
- pad = (-self.result.getlength()) & mask
- self.result.append_multiple_char('\x00', pad)
+ pad = (-self.pos) & mask
+ self.advance(pad)
def finished(self):
if self.args_index != len(self.args_w):
diff --git a/pypy/module/struct/interp_struct.py
b/pypy/module/struct/interp_struct.py
--- a/pypy/module/struct/interp_struct.py
+++ b/pypy/module/struct/interp_struct.py
@@ -40,10 +40,7 @@
def _pack(space, format, args_w):
"""Return string containing values v1, v2, ... packed according to fmt."""
- if jit.isconstant(format):
- size = _calcsize(space, format)
- else:
- size = 8
+ size = _calcsize(space, format)
fmtiter = PackFormatIterator(space, args_w, size)
try:
fmtiter.interpret(format)
@@ -51,7 +48,8 @@
raise OperationError(space.w_OverflowError, space.newtext(e.msg))
except StructError as e:
raise OperationError(get_error(space), space.newtext(e.msg))
- return fmtiter.result.build()
+ assert fmtiter.pos == fmtiter.result.getlength(), 'missing .advance() or
wrong calcsize()'
+ return fmtiter.result.finish()
@unwrap_spec(format='text')
diff --git a/pypy/objspace/std/unicodeobject.py
b/pypy/objspace/std/unicodeobject.py
--- a/pypy/objspace/std/unicodeobject.py
+++ b/pypy/objspace/std/unicodeobject.py
@@ -4,6 +4,7 @@
compute_hash, compute_unique_id, import_from_mixin,
enforceargs)
from rpython.rlib.buffer import StringBuffer
+from rpython.rlib.mutbuffer import MutableStringBuffer
from rpython.rlib.rstring import StringBuilder, UnicodeBuilder
from rpython.rlib.runicode import (
make_unicode_escape_function, str_decode_ascii, str_decode_utf_8,
@@ -84,10 +85,12 @@
def readbuf_w(self, space):
from rpython.rlib.rstruct.unichar import pack_unichar, UNICODE_SIZE
- builder = StringBuilder(len(self._value) * UNICODE_SIZE)
+ buf = MutableStringBuffer(len(self._value) * UNICODE_SIZE)
+ pos = 0
for unich in self._value:
- pack_unichar(unich, builder)
- return StringBuffer(builder.build())
+ pack_unichar(unich, buf, pos)
+ pos += UNICODE_SIZE
+ return StringBuffer(buf.finish())
def writebuf_w(self, space):
raise oefmt(space.w_TypeError,
diff --git a/rpython/rlib/rstruct/nativefmttable.py
b/rpython/rlib/rstruct/nativefmttable.py
--- a/rpython/rlib/rstruct/nativefmttable.py
+++ b/rpython/rlib/rstruct/nativefmttable.py
@@ -136,7 +136,8 @@
if len(unistr) != 1:
raise StructError("expected a unicode string of length 1")
c = unistr[0] # string->char conversion for the annotator
- unichar.pack_unichar(c, fmtiter.result)
+ unichar.pack_unichar(c, fmtiter.result, fmtiter.pos)
+ fmtiter.advance(unichar.UNICODE_SIZE)
@specialize.argtype(0)
def unpack_unichar(fmtiter):
diff --git a/rpython/rlib/rstruct/unichar.py b/rpython/rlib/rstruct/unichar.py
--- a/rpython/rlib/rstruct/unichar.py
+++ b/rpython/rlib/rstruct/unichar.py
@@ -11,25 +11,25 @@
UNICODE_SIZE = 4
BIGENDIAN = sys.byteorder == "big"
-def pack_unichar(unich, charlist):
+def pack_unichar(unich, buf, pos):
if UNICODE_SIZE == 2:
if BIGENDIAN:
- charlist.append(chr(ord(unich) >> 8))
- charlist.append(chr(ord(unich) & 0xFF))
+ buf.setitem(pos, chr(ord(unich) >> 8))
+ buf.setitem(pos+1, chr(ord(unich) & 0xFF))
else:
- charlist.append(chr(ord(unich) & 0xFF))
- charlist.append(chr(ord(unich) >> 8))
+ buf.setitem(pos, chr(ord(unich) & 0xFF))
+ buf.setitem(pos+1, chr(ord(unich) >> 8))
else:
if BIGENDIAN:
- charlist.append(chr(ord(unich) >> 24))
- charlist.append(chr((ord(unich) >> 16) & 0xFF))
- charlist.append(chr((ord(unich) >> 8) & 0xFF))
- charlist.append(chr(ord(unich) & 0xFF))
+ buf.setitem(pos, chr(ord(unich) >> 24))
+ buf.setitem(pos+1, chr((ord(unich) >> 16) & 0xFF))
+ buf.setitem(pos+2, chr((ord(unich) >> 8) & 0xFF))
+ buf.setitem(pos+3, chr(ord(unich) & 0xFF))
else:
- charlist.append(chr(ord(unich) & 0xFF))
- charlist.append(chr((ord(unich) >> 8) & 0xFF))
- charlist.append(chr((ord(unich) >> 16) & 0xFF))
- charlist.append(chr(ord(unich) >> 24))
+ buf.setitem(pos, chr(ord(unich) & 0xFF))
+ buf.setitem(pos+1, chr((ord(unich) >> 8) & 0xFF))
+ buf.setitem(pos+2, chr((ord(unich) >> 16) & 0xFF))
+ buf.setitem(pos+3, chr(ord(unich) >> 24))
def unpack_unichar(rawstring):
assert len(rawstring) == UNICODE_SIZE
_______________________________________________
pypy-commit mailing list
[email protected]
https://mail.python.org/mailman/listinfo/pypy-commit