[pypy-svn] r26317 - in pypy/dist/pypy/rpython: . lltypesystem ootypesystem test
nik at codespeak.net
nik at codespeak.net
Tue Apr 25 11:53:24 CEST 2006
Author: nik
Date: Tue Apr 25 11:53:05 2006
New Revision: 26317
Added:
pypy/dist/pypy/rpython/lltypesystem/rrange.py (contents, props changed)
pypy/dist/pypy/rpython/ootypesystem/rrange.py (contents, props changed)
Modified:
pypy/dist/pypy/rpython/ootypesystem/rtuple.py
pypy/dist/pypy/rpython/rlist.py
pypy/dist/pypy/rpython/rrange.py
pypy/dist/pypy/rpython/test/test_rrange.py
pypy/dist/pypy/rpython/typesystem.py
Log:
bring rrange support to ootypesystem.
Added: pypy/dist/pypy/rpython/lltypesystem/rrange.py
==============================================================================
--- (empty file)
+++ pypy/dist/pypy/rpython/lltypesystem/rrange.py Tue Apr 25 11:53:05 2006
@@ -0,0 +1,71 @@
+from pypy.rpython.lltypesystem.lltype import Ptr, GcStruct, Signed, malloc, Void
+from pypy.rpython.rrange import AbstractRangeRepr, AbstractRangeIteratorRepr
+
+# ____________________________________________________________
+#
+# Concrete implementation of RPython lists that are returned by range()
+# and never mutated afterwards:
+#
+# struct range {
+# Signed start, stop; // step is always constant
+# }
+#
+# struct rangest {
+# Signed start, stop, step; // rare case, for completeness
+# }
+
+RANGE = GcStruct("range", ("start", Signed), ("stop", Signed))
+RANGEITER = GcStruct("range", ("next", Signed), ("stop", Signed))
+
+RANGEST = GcStruct("range", ("start", Signed), ("stop", Signed),("step", Signed))
+RANGESTITER = GcStruct("range", ("next", Signed), ("stop", Signed), ("step", Signed))
+
+class RangeRepr(AbstractRangeRepr):
+
+ RANGE = Ptr(RANGE)
+ RANGEITER = Ptr(RANGEITER)
+
+ RANGEST = Ptr(RANGEST)
+ RANGESTITER = Ptr(RANGESTITER)
+
+ getfield_opname = "getfield"
+
+ def __init__(self, *args):
+ AbstractRangeRepr.__init__(self, *args)
+ self.ll_newrange = ll_newrange
+ self.ll_newrangest = ll_newrangest
+
+ def make_iterator_repr(self):
+ return RangeIteratorRepr(self)
+
+
+def ll_newrange(start, stop):
+ l = malloc(RANGE)
+ l.start = start
+ l.stop = stop
+ return l
+
+def ll_newrangest(start, stop, step):
+ if step == 0:
+ raise ValueError
+ l = malloc(RANGEST)
+ l.start = start
+ l.stop = stop
+ l.step = step
+ return l
+
+
+class RangeIteratorRepr(AbstractRangeIteratorRepr):
+
+ def __init__(self, *args):
+ AbstractRangeIteratorRepr.__init__(self, *args)
+ self.ll_rangeiter = ll_rangeiter
+
+def ll_rangeiter(ITERPTR, rng):
+ iter = malloc(ITERPTR.TO)
+ iter.next = rng.start
+ iter.stop = rng.stop
+ if ITERPTR.TO is RANGESTITER:
+ iter.step = rng.step
+ return iter
+
Added: pypy/dist/pypy/rpython/ootypesystem/rrange.py
==============================================================================
--- (empty file)
+++ pypy/dist/pypy/rpython/ootypesystem/rrange.py Tue Apr 25 11:53:05 2006
@@ -0,0 +1,57 @@
+from pypy.rpython.ootypesystem.ootype import Signed, Tuple, new
+from pypy.rpython.rrange import AbstractRangeRepr, AbstractRangeIteratorRepr
+
+RANGE = Tuple({"start": Signed, "stop": Signed})
+RANGEITER = Tuple({"next": Signed, "stop": Signed})
+
+RANGEST = Tuple({"start": Signed, "stop": Signed, "step": Signed})
+RANGESTITER = Tuple({"next": Signed, "stop": Signed, "step": Signed})
+
+class RangeRepr(AbstractRangeRepr):
+
+ RANGE = RANGE
+ RANGEITER = RANGEITER
+ RANGEST = RANGEST
+ RANGESTITER = RANGESTITER
+
+ getfield_opname = "oogetfield"
+
+ def __init__(self, *args):
+ AbstractRangeRepr.__init__(self, *args)
+ self.ll_newrange = ll_newrange
+ self.ll_newrangest = ll_newrangest
+
+ def make_iterator_repr(self):
+ return RangeIteratorRepr(self)
+
+
+def ll_newrange(start, stop):
+ l = new(RANGE)
+ l.start = start
+ l.stop = stop
+ return l
+
+def ll_newrangest(start, stop, step):
+ if step == 0:
+ raise ValueError
+ l = new(RANGEST)
+ l.start = start
+ l.stop = stop
+ l.step = step
+ return l
+
+
+class RangeIteratorRepr(AbstractRangeIteratorRepr):
+
+ def __init__(self, *args):
+ AbstractRangeIteratorRepr.__init__(self, *args)
+ self.ll_rangeiter = ll_rangeiter
+
+def ll_rangeiter(ITER, rng):
+ iter = new(ITER)
+ iter.next = rng.start
+ iter.stop = rng.stop
+ if ITER is RANGESTITER:
+ iter.step = rng.step
+ return iter
+
Modified: pypy/dist/pypy/rpython/ootypesystem/rtuple.py
==============================================================================
--- pypy/dist/pypy/rpython/ootypesystem/rtuple.py (original)
+++ pypy/dist/pypy/rpython/ootypesystem/rtuple.py Tue Apr 25 11:53:05 2006
@@ -8,8 +8,8 @@
def __init__(self, rtyper, items_r):
AbstractTupleRepr.__init__(self, rtyper, items_r)
- #self.lowleveltype = ootype.Tuple(dict(zip(self.fieldnames, self.lltypes)))
- self.lowleveltype = tuple_type(self.fieldnames, self.lltypes)
+ self.lowleveltype = ootype.Tuple(dict(zip(self.fieldnames, self.lltypes)))
+ #self.lowleveltype = tuple_type(self.fieldnames, self.lltypes)
def newtuple(cls, llops, r_tuple, items_v):
# items_v should have the lowleveltype of the internal reprs
Modified: pypy/dist/pypy/rpython/rlist.py
==============================================================================
--- pypy/dist/pypy/rpython/rlist.py (original)
+++ pypy/dist/pypy/rpython/rlist.py Tue Apr 25 11:53:05 2006
@@ -12,11 +12,10 @@
class __extend__(annmodel.SomeList):
def rtyper_makerepr(self, rtyper):
- from pypy.rpython import rrange
listitem = self.listdef.listitem
s_value = listitem.s_value
if listitem.range_step is not None and not listitem.mutated:
- return rrange.RangeRepr(listitem.range_step)
+ return rtyper.type_system.rrange.RangeRepr(listitem.range_step)
elif (s_value.__class__ is annmodel.SomeObject and s_value.knowntype == object):
return robject.pyobj_repr
else:
Modified: pypy/dist/pypy/rpython/rrange.py
==============================================================================
--- pypy/dist/pypy/rpython/rrange.py (original)
+++ pypy/dist/pypy/rpython/rrange.py Tue Apr 25 11:53:05 2006
@@ -1,40 +1,22 @@
from pypy.annotation.pairtype import pairtype
from pypy.rpython.error import TyperError
+from pypy.rpython.lltypesystem.lltype import Signed, Void, Ptr
from pypy.rpython.rmodel import Repr, IntegerRepr, IteratorRepr
-from pypy.rpython.lltypesystem.lltype import Ptr, GcStruct, Signed, malloc, Void
from pypy.objspace.flow.model import Constant
from pypy.rpython.rlist import dum_nocheck, dum_checkidx
-# ____________________________________________________________
-#
-# Concrete implementation of RPython lists that are returned by range()
-# and never mutated afterwards:
-#
-# struct range {
-# Signed start, stop; // step is always constant
-# }
-#
-# struct rangest {
-# Signed start, stop, step; // rare case, for completeness
-# }
-RANGE = GcStruct("range", ("start", Signed), ("stop", Signed))
-RANGEITER = GcStruct("range", ("next", Signed), ("stop", Signed))
-
-RANGEST = GcStruct("range", ("start", Signed), ("stop", Signed),("step", Signed))
-RANGESTITER = GcStruct("range", ("next", Signed), ("stop", Signed), ("step", Signed))
-
-class RangeRepr(Repr):
+class AbstractRangeRepr(Repr):
def __init__(self, step):
self.step = step
if step != 0:
- self.lowleveltype = Ptr(RANGE)
+ self.lowleveltype = self.RANGE
else:
- self.lowleveltype = Ptr(RANGEST)
+ self.lowleveltype = self.RANGEST
def _getstep(self, v_rng, hop):
- return hop.genop('getfield', [v_rng, hop.inputconst(Void, 'step')],
- resulttype=Signed)
+ return hop.genop(self.getfield_opname,
+ [v_rng, hop.inputconst(Void, 'step')], resulttype=Signed)
def rtype_len(self, hop):
v_rng, = hop.inputargs(self)
@@ -44,10 +26,7 @@
cstep = self._getstep(v_rng, hop)
return hop.gendirectcall(ll_rangelen, v_rng, cstep)
- def make_iterator_repr(self):
- return RangeIteratorRepr(self)
-
-class __extend__(pairtype(RangeRepr, IntegerRepr)):
+class __extend__(pairtype(AbstractRangeRepr, IntegerRepr)):
def rtype_getitem((r_rng, r_int), hop):
if hop.has_implicit_exception(IndexError):
@@ -105,21 +84,6 @@
#
# Irregular operations.
-def ll_newrange(start, stop):
- l = malloc(RANGE)
- l.start = start
- l.stop = stop
- return l
-
-def ll_newrangest(start, stop, step):
- if step == 0:
- raise ValueError
- l = malloc(RANGEST)
- l.start = start
- l.stop = stop
- l.step = step
- return l
-
def rtype_builtin_range(hop):
vstep = hop.inputconst(Signed, 1)
if hop.nb_args == 1:
@@ -132,15 +96,18 @@
if isinstance(vstep, Constant) and vstep.value == 0:
# not really needed, annotator catches it. Just in case...
raise TyperError("range cannot have a const step of zero")
- if isinstance(hop.r_result, RangeRepr):
+ if isinstance(hop.r_result, AbstractRangeRepr):
if hop.r_result.step != 0:
- return hop.gendirectcall(ll_newrange, vstart, vstop)
+ return hop.gendirectcall(hop.r_result.ll_newrange, vstart, vstop)
else:
- return hop.gendirectcall(ll_newrangest, vstart, vstop, vstep)
+ return hop.gendirectcall(hop.r_result.ll_newrangest, vstart, vstop, vstep)
else:
# cannot build a RANGE object, needs a real list
r_list = hop.r_result
- cLIST = hop.inputconst(Void, r_list.lowleveltype.TO)
+ ITEMTYPE = r_list.lowleveltype
+ if isinstance(ITEMTYPE, Ptr):
+ ITEMTYPE = ITEMTYPE.TO
+ cLIST = hop.inputconst(Void, ITEMTYPE)
return hop.gendirectcall(ll_range2list, cLIST, vstart, vstop, vstep)
rtype_builtin_xrange = rtype_builtin_range
@@ -151,9 +118,8 @@
length = _ll_rangelen(start, stop, step)
l = LIST.ll_newlist(length)
idx = 0
- items = l.ll_items()
while idx < length:
- items[idx] = start
+ l.ll_setitem_fast(idx, start)
start += step
idx += 1
return l
@@ -162,18 +128,18 @@
#
# Iteration.
-class RangeIteratorRepr(IteratorRepr):
+class AbstractRangeIteratorRepr(IteratorRepr):
def __init__(self, r_rng):
self.r_rng = r_rng
if r_rng.step != 0:
- self.lowleveltype = Ptr(RANGEITER)
+ self.lowleveltype = r_rng.RANGEITER
else:
- self.lowleveltype = Ptr(RANGESTITER)
+ self.lowleveltype = r_rng.RANGESTITER
def newiter(self, hop):
v_rng, = hop.inputargs(self.r_rng)
citerptr = hop.inputconst(Void, self.lowleveltype)
- return hop.gendirectcall(ll_rangeiter, citerptr, v_rng)
+ return hop.gendirectcall(self.ll_rangeiter, citerptr, v_rng)
def rtype_next(self, hop):
v_iter, = hop.inputargs(self)
@@ -189,14 +155,6 @@
hop.exception_is_here()
return hop.gendirectcall(llfn, v_iter, *args)
-def ll_rangeiter(ITERPTR, rng):
- iter = malloc(ITERPTR.TO)
- iter.next = rng.start
- iter.stop = rng.stop
- if ITERPTR.TO is RANGESTITER:
- iter.step = rng.step
- return iter
-
def ll_rangenext_up(iter, step):
next = iter.next
if next >= iter.stop:
Modified: pypy/dist/pypy/rpython/test/test_rrange.py
==============================================================================
--- pypy/dist/pypy/rpython/test/test_rrange.py (original)
+++ pypy/dist/pypy/rpython/test/test_rrange.py Tue Apr 25 11:53:05 2006
@@ -2,122 +2,136 @@
from pypy.rpython.test.test_llinterp import interpret
from pypy.rpython.rarithmetic import intmask
-def test_rlist_range():
- def test1(start, stop, step, varstep):
- expected = range(start, stop, step)
- length = len(expected)
- if varstep:
- l = ll_newrangest(start, stop, step)
- step = l.step
- else:
- l = ll_newrange(start,stop)
- assert ll_rangelen(l, step) == length
- lst = [ll_rangeitem(dum_nocheck, l, i, step) for i in range(length)]
- assert lst == expected
- lst = [ll_rangeitem_nonneg(dum_nocheck, l, i, step) for i in range(length)]
- assert lst == expected
- lst = [ll_rangeitem(dum_nocheck, l, i-length, step) for i in range(length)]
- assert lst == expected
-
- for start in (-10, 0, 1, 10):
- for stop in (-8, 0, 4, 8, 25):
- for step in (1, 2, 3, -1, -2):
- for varstep in False, True:
- test1(start, stop, step, varstep)
-
-# ____________________________________________________________
-
-def test_range():
- def dummyfn(N):
- total = 0
- for i in range(N):
- total += i
- return total
- res = interpret(dummyfn, [10])
- assert res == 45
-
-def test_range_is_lazy():
- def dummyfn(N, M):
- total = 0
- for i in range(M):
- if i == N:
- break
- total += i
- return total
- res = interpret(dummyfn, [10, 2147418112])
- assert res == 45
-
-def test_range_item():
- def dummyfn(start, stop, i):
- r = range(start, stop)
- return r[i]
- res = interpret(dummyfn, [10, 17, 4])
- assert res == 14
- res = interpret(dummyfn, [10, 17, -2])
- assert res == 15
-
-def test_xrange():
- def dummyfn(N):
- total = 0
- for i in xrange(N):
- total += i
- return total
- res = interpret(dummyfn, [10])
- assert res == 45
-
-def test_range_len():
- def dummyfn(start, stop):
- r = range(start, stop)
- return len(r)
- start, stop = 10, 17
- res = interpret(dummyfn, [start, stop])
- assert res == dummyfn(start, stop)
-
-def test_range2list():
- def dummyfn(start, stop):
- r = range(start, stop)
- r.reverse()
- return r[0]
- start, stop = 10, 17
- res = interpret(dummyfn, [start, stop])
- assert res == dummyfn(start, stop)
-
-def check_failed(func, *args):
- try:
- interpret(func, *args)
- except:
- return True
- else:
- return False
-
-def test_range_extra():
- def failingfn_const():
- r = range(10, 17, 0)
- return r[-1]
- assert check_failed(failingfn_const, [])
-
- def failingfn_var(step):
- r = range(10, 17, step)
- return r[-1]
- step = 3
- res = interpret(failingfn_var, [step])
- assert res == failingfn_var(step)
- step = 0
- assert check_failed(failingfn_var, [step])
-
-def test_range_iter():
- def fn(start, stop, step):
- res = 0
- if step == 0:
- if stop >= start:
- r = range(start, stop, 1)
+
+class AbstractTestRange:
+
+ def test_rlist_range(self):
+ def test1(start, stop, step, varstep):
+ expected = range(start, stop, step)
+ length = len(expected)
+ if varstep:
+ l = self.rrange.ll_newrangest(start, stop, step)
+ step = l.step
else:
- r = range(start, stop, -1)
+ l = self.rrange.ll_newrange(start,stop)
+ assert ll_rangelen(l, step) == length
+ lst = [ll_rangeitem(dum_nocheck, l, i, step) for i in range(length)]
+ assert lst == expected
+ lst = [ll_rangeitem_nonneg(dum_nocheck, l, i, step) for i in range(length)]
+ assert lst == expected
+ lst = [ll_rangeitem(dum_nocheck, l, i-length, step) for i in range(length)]
+ assert lst == expected
+
+ for start in (-10, 0, 1, 10):
+ for stop in (-8, 0, 4, 8, 25):
+ for step in (1, 2, 3, -1, -2):
+ for varstep in False, True:
+ test1(start, stop, step, varstep)
+
+ def test_range(self):
+ def dummyfn(N):
+ total = 0
+ for i in range(N):
+ total += i
+ return total
+ res = interpret(dummyfn, [10], type_system=self.ts)
+ assert res == 45
+
+ def test_range_is_lazy(self):
+ def dummyfn(N, M):
+ total = 0
+ for i in range(M):
+ if i == N:
+ break
+ total += i
+ return total
+ res = interpret(dummyfn, [10, 2147418112], type_system=self.ts)
+ assert res == 45
+
+ def test_range_item(self):
+ def dummyfn(start, stop, i):
+ r = range(start, stop)
+ return r[i]
+ res = interpret(dummyfn, [10, 17, 4], type_system=self.ts)
+ assert res == 14
+ res = interpret(dummyfn, [10, 17, -2], type_system=self.ts)
+ assert res == 15
+
+ def test_xrange(self):
+ def dummyfn(N):
+ total = 0
+ for i in xrange(N):
+ total += i
+ return total
+ res = interpret(dummyfn, [10], type_system=self.ts)
+ assert res == 45
+
+ def test_range_len(self):
+ def dummyfn(start, stop):
+ r = range(start, stop)
+ return len(r)
+ start, stop = 10, 17
+ res = interpret(dummyfn, [start, stop], type_system=self.ts)
+ assert res == dummyfn(start, stop)
+
+ def test_range2list(self):
+ def dummyfn(start, stop):
+ r = range(start, stop)
+ r.reverse()
+ return r[0]
+ start, stop = 10, 17
+ res = interpret(dummyfn, [start, stop], type_system=self.ts)
+ assert res == dummyfn(start, stop)
+
+ def check_failed(self, func, *args):
+ try:
+ kwargs = {"type_system": self.ts}
+ interpret(func, *args, **kwargs)
+ except:
+ return True
else:
- r = range(start, stop, step)
- for i in r:
- res = res * 51 + i
- return res
- for args in [2, 7, 0], [7, 2, 0], [10, 50, 7], [50, -10, -3]:
- res = interpret(fn, args)#, view=True)
- assert res == intmask(fn(*args))
+ return False
+
+ def test_range_extra(self):
+ def failingfn_const():
+ r = range(10, 17, 0)
+ return r[-1]
+ assert self.check_failed(failingfn_const, [])
+
+ def failingfn_var(step):
+ r = range(10, 17, step)
+ return r[-1]
+ step = 3
+ res = interpret(failingfn_var, [step], type_system=self.ts)
+ assert res == failingfn_var(step)
+ step = 0
+ assert self.check_failed(failingfn_var, [step])
+
+ def test_range_iter(self):
+ def fn(start, stop, step):
+ res = 0
+ if step == 0:
+ if stop >= start:
+ r = range(start, stop, 1)
+ else:
+ r = range(start, stop, -1)
+ else:
+ r = range(start, stop, step)
+ for i in r:
+ res = res * 51 + i
+ return res
+ for args in [2, 7, 0], [7, 2, 0], [10, 50, 7], [50, -10, -3]:
+ res = interpret(fn, args, type_system=self.ts)
+ assert res == intmask(fn(*args))
+
+
+class TestRangeLltype(AbstractTestRange):
+
+ ts = "lltype"
+ from pypy.rpython.lltypesystem import rrange
+
+
+class TestRangeOotype(AbstractTestRange):
+
+ ts = "ootype"
+ from pypy.rpython.ootypesystem import rrange
Modified: pypy/dist/pypy/rpython/typesystem.py
==============================================================================
--- pypy/dist/pypy/rpython/typesystem.py (original)
+++ pypy/dist/pypy/rpython/typesystem.py Tue Apr 25 11:53:05 2006
@@ -20,8 +20,8 @@
None, None, ['__doc__'])
except ImportError:
return None
- if name in ('rclass', 'rpbc', 'rbuiltin', 'rtuple', 'rlist', 'rslice', 'rdict',
- 'exceptiondata'):
+ if name in ('rclass', 'rpbc', 'rbuiltin', 'rtuple', 'rlist',
+ 'rslice', 'rdict', 'rrange', 'exceptiondata'):
mod = load(name)
if mod is not None:
setattr(self, name, mod)
More information about the Pypy-commit
mailing list