[pypy-commit] pypy rpython-bytearray: basic bytearray creation

fijal noreply at buildbot.pypy.org
Mon Dec 24 17:22:11 CET 2012


Author: Maciej Fijalkowski <fijall at gmail.com>
Branch: rpython-bytearray
Changeset: r59548:33301a219af0
Date: 2012-12-24 18:21 +0200
http://bitbucket.org/pypy/pypy/changeset/33301a219af0/

Log:	basic bytearray creation

diff --git a/pypy/rpython/lltypesystem/rbytearray.py b/pypy/rpython/lltypesystem/rbytearray.py
new file mode 100644
--- /dev/null
+++ b/pypy/rpython/lltypesystem/rbytearray.py
@@ -0,0 +1,24 @@
+
+from pypy.rpython.rbytearray import AbstractByteArrayRepr
+from pypy.rpython.lltypesystem import lltype
+
+BYTEARRAY = lltype.GcArray(lltype.Char)
+
+class ByteArrayRepr(AbstractByteArrayRepr):
+    lowleveltype = lltype.Ptr(BYTEARRAY)
+
+    def convert_const(self, value):
+        if value is None:
+            return lltype.nullptr(BYTEARRAY)
+        p = lltype.malloc(BYTEARRAY, len(value))
+        for i, c in enumerate(value):
+            p[i] = chr(c)
+        return p
+
+bytearray_repr = ByteArrayRepr()
+
+def hlbytearray(ll_b):
+    b = bytearray()
+    for i in range(len(ll_b)):
+        b.append(ll_b[i])
+    return b
diff --git a/pypy/rpython/lltypesystem/rstr.py b/pypy/rpython/lltypesystem/rstr.py
--- a/pypy/rpython/lltypesystem/rstr.py
+++ b/pypy/rpython/lltypesystem/rstr.py
@@ -15,7 +15,7 @@
 from pypy.rpython.lltypesystem.lltype import \
      GcStruct, Signed, Array, Char, UniChar, Ptr, malloc, \
      Bool, Void, GcArray, nullptr, cast_primitive, typeOf,\
-     staticAdtMethod, GcForwardReference
+     staticAdtMethod, GcForwardReference, malloc
 from pypy.rpython.rmodel import Repr
 from pypy.rpython.lltypesystem import llmemory
 from pypy.tool.sourcetools import func_with_new_name
@@ -285,6 +285,15 @@
             s.chars[i] = cast_primitive(UniChar, str.chars[i])
         return s
 
+    def ll_str2bytearray(str):
+        from pypy.rpython.lltypesystem.rbytearray import BYTEARRAY
+        
+        lgt = len(str.chars)
+        b = malloc(BYTEARRAY, lgt)
+        for i in range(lgt):
+            b[i] = str.chars[i]
+        return b
+
     @jit.elidable
     def ll_strhash(s):
         # unlike CPython, there is no reason to avoid to return -1
diff --git a/pypy/rpython/rbuiltin.py b/pypy/rpython/rbuiltin.py
--- a/pypy/rpython/rbuiltin.py
+++ b/pypy/rpython/rbuiltin.py
@@ -222,6 +222,9 @@
 def rtype_builtin_unicode(hop):
     return hop.args_r[0].rtype_unicode(hop)
 
+def rtype_builtin_bytearray(hop):
+    return hop.args_r[0].rtype_bytearray(hop)
+
 def rtype_builtin_list(hop):
     return hop.args_r[0].rtype_bltn_list(hop)
 
diff --git a/pypy/rpython/rbytearray.py b/pypy/rpython/rbytearray.py
new file mode 100644
--- /dev/null
+++ b/pypy/rpython/rbytearray.py
@@ -0,0 +1,13 @@
+
+from pypy.rpython.rmodel import Repr
+from pypy.annotation import model as annmodel
+
+class AbstractByteArrayRepr(Repr):
+    pass
+
+class __extend__(annmodel.SomeByteArray):
+    def rtyper_makekey(self):
+        return self.__class__,
+
+    def rtyper_makerepr(self, rtyper):
+        return rtyper.type_system.rbytearray.bytearray_repr
diff --git a/pypy/rpython/rstr.py b/pypy/rpython/rstr.py
--- a/pypy/rpython/rstr.py
+++ b/pypy/rpython/rstr.py
@@ -374,6 +374,15 @@
         hop.exception_is_here()
         return hop.gendirectcall(self.ll.ll_str2unicode, v_str)
 
+    def rtype_bytearray(self, hop):
+        if hop.args_s[0].is_constant():
+            # convertion errors occur during annotation, so cannot any more:
+            hop.exception_cannot_occur()
+            return hop.inputconst(hop.r_result, hop.s_result.const)
+        hop.exception_is_here()
+        return hop.gendirectcall(self.ll.ll_str2bytearray,
+                                 hop.inputarg(hop.args_r[0].repr, 0))
+
     def rtype_method_decode(self, hop):
         if not hop.args_s[1].is_constant():
             raise TyperError("encoding must be a constant")
diff --git a/pypy/rpython/rtyper.py b/pypy/rpython/rtyper.py
--- a/pypy/rpython/rtyper.py
+++ b/pypy/rpython/rtyper.py
@@ -1013,7 +1013,7 @@
 # and the rtyper_chooserepr() methods
 from pypy.rpython import rint, rbool, rfloat
 from pypy.rpython import rrange
-from pypy.rpython import rstr, rdict, rlist
+from pypy.rpython import rstr, rdict, rlist, rbytearray
 from pypy.rpython import rclass, rbuiltin, rpbc
 from pypy.rpython import rexternalobj
 from pypy.rpython import rptr
diff --git a/pypy/rpython/test/test_rbytearray.py b/pypy/rpython/test/test_rbytearray.py
new file mode 100644
--- /dev/null
+++ b/pypy/rpython/test/test_rbytearray.py
@@ -0,0 +1,16 @@
+
+from pypy.rpython.test.tool import BaseRtypingTest, LLRtypeMixin
+from pypy.rpython.lltypesystem.rbytearray import hlbytearray
+
+class TestByteArray(BaseRtypingTest, LLRtypeMixin):
+    def test_bytearray_creation(self):
+        def f(x):
+            if x:
+                b = bytearray(str(x))
+            else:
+                b = bytearray("def")
+            return b
+        ll_res = self.interpret(f, [0])
+        assert hlbytearray(ll_res) == "def"
+        ll_res = self.interpret(f, [1])
+        assert hlbytearray(ll_res) == "1"
diff --git a/pypy/rpython/typesystem.py b/pypy/rpython/typesystem.py
--- a/pypy/rpython/typesystem.py
+++ b/pypy/rpython/typesystem.py
@@ -22,7 +22,7 @@
                 return None
         if name in ('rclass', 'rpbc', 'rbuiltin', 'rtuple', 'rlist',
                     'rslice', 'rdict', 'rrange', 'rstr', 'rgeneric',
-                    'll_str', 'rbuilder', 'rvirtualizable2',
+                    'll_str', 'rbuilder', 'rvirtualizable2', 'rbytearray',
                     'exceptiondata'):
             mod = load(name)
             if mod is not None:


More information about the pypy-commit mailing list