Author: Antonio Cuni <[email protected]>
Branch: faster-rstruct-2
Changeset: r91230:bec494d81ed2
Date: 2017-05-10 18:22 +0200
http://bitbucket.org/pypy/pypy/changeset/bec494d81ed2/

Log:    fix pack_bool and pack_string

diff --git a/rpython/rlib/rstruct/standardfmttable.py 
b/rpython/rlib/rstruct/standardfmttable.py
--- a/rpython/rlib/rstruct/standardfmttable.py
+++ b/rpython/rlib/rstruct/standardfmttable.py
@@ -33,15 +33,20 @@
 
 def pack_bool(fmtiter):
     c = '\x01' if fmtiter.accept_bool_arg() else '\x00'
-    fmtiter.result.append(c)
+    fmtiter.result.setitem(fmtiter.pos, c)
+    fmtiter.advance(1)
 
 def pack_string(fmtiter, count):
+    pos = fmtiter.pos
     string = fmtiter.accept_str_arg()
     if len(string) < count:
-        fmtiter.result.append(string)
-        fmtiter.result.append_multiple_char('\x00', count - len(string))
+        fmtiter.result.setslice(pos, string)
+        if fmtiter.needs_zeros:
+            for i in range(pos + len(string), count):
+                fmtiter.result.setitem(i, '\x00')
     else:
-        fmtiter.result.append_slice(string, 0, count)
+        fmtiter.result.setslice(pos, string[:count])
+    fmtiter.advance(count)
 
 def pack_pascal(fmtiter, count):
     string = fmtiter.accept_str_arg()
diff --git a/rpython/rlib/rstruct/test/test_pack.py 
b/rpython/rlib/rstruct/test/test_pack.py
--- a/rpython/rlib/rstruct/test/test_pack.py
+++ b/rpython/rlib/rstruct/test/test_pack.py
@@ -10,7 +10,11 @@
         self.value = value
         self.bigendian = bigendian
         self.result = MutableStringBuffer(size)
+        # we set the buffer to non-zero, so ensure that we actively write 0s
+        # where it's needed
+        self.result.setslice(0, '\xff'*size)
         self.pos = 0
+        self.needs_zeros = True
 
     def advance(self, count):
         self.pos += count
@@ -48,6 +52,12 @@
         pack(fake_fmtiter)
         return fake_fmtiter.finish()
 
+    def mypack_fn(self, func, size, arg, value):
+        bigendian = self.endianess == '>'
+        fmtiter = FakeFormatIter(bigendian, size, value)
+        func(fmtiter, arg)
+        return fmtiter.finish()
+
     def check(self, fmt, value):
         expected = struct.pack(self.endianess+fmt, value)
         got = self.mypack(fmt, value)
@@ -73,6 +83,10 @@
     def test_pack_char(self):
         self.check('c', 'a')
 
+    def test_pack_bool(self):
+        self.check('?', True)
+        self.check('?', False)
+
     def test_pack_pad(self):
         bigendian = self.endianess == '>'
         fmtiter = FakeFormatIter(bigendian, None)
@@ -81,11 +95,13 @@
         assert s == '\x00'*4
 
     def test_pack_string(self):
-        bigendian = self.endianess == '>'
-        fmtiter = FakeFormatIter(bigendian, 'hello')
-        standardfmttable.pack_string(fmtiter, 8)
-        s = fmtiter.result.build()
+        s = self.mypack_fn(standardfmttable.pack_string,
+                           arg=8, value='hello', size=8)
         assert s == 'hello\x00\x00\x00'
+        #
+        s = self.mypack_fn(standardfmttable.pack_string,
+                           arg=8, value='hello world', size=8)
+        assert s == 'hello wo'
 
     def test_pack_pascal(self):
         bigendian = self.endianess == '>'
_______________________________________________
pypy-commit mailing list
[email protected]
https://mail.python.org/mailman/listinfo/pypy-commit

Reply via email to