[pypy-svn] r12863 - pypy/dist/pypy/rpython

arigo at codespeak.net arigo at codespeak.net
Sun May 29 00:04:00 CEST 2005


Author: arigo
Date: Sun May 29 00:04:00 2005
New Revision: 12863

Modified:
   pypy/dist/pypy/rpython/rbool.py
   pypy/dist/pypy/rpython/rbuiltin.py
   pypy/dist/pypy/rpython/rfloat.py
   pypy/dist/pypy/rpython/rint.py
   pypy/dist/pypy/rpython/rlist.py
   pypy/dist/pypy/rpython/robject.py
   pypy/dist/pypy/rpython/rpbc.py
   pypy/dist/pypy/rpython/rptr.py
   pypy/dist/pypy/rpython/rtyper.py
Log:
Some refactoring, according to the lines of the pypy-dev post
http://codespeak.net/pipermail/pypy-dev/2005q2/002109.html

In a word, the thread-local storage is gone and we pass around a
HighLevelOp object ('hop' for short :-)



Modified: pypy/dist/pypy/rpython/rbool.py
==============================================================================
--- pypy/dist/pypy/rpython/rbool.py	(original)
+++ pypy/dist/pypy/rpython/rbool.py	Sun May 29 00:04:00 2005
@@ -1,7 +1,6 @@
 from pypy.annotation.pairtype import pairtype
 from pypy.annotation.model import SomeFloat, SomeInteger, SomeBool, SomePBC
 from pypy.rpython.lltype import Signed, Unsigned, Bool, Float
-from pypy.rpython.rtyper import receive, direct_op
 from pypy.rpython.rtyper import TyperError
 
 
@@ -9,24 +8,24 @@
 
 class __extend__(pairtype(SomeBool, SomeInteger)):
 
-    def rtype_convert_from_to((s_from, s_to), v):
+    def rtype_convert_from_to((s_from, s_to), v, llops):
         if s_to.unsigned:
             if debug: print 'explicit cast_bool_to_uint'
-            return direct_op('cast_bool_to_uint', [v], resulttype=Unsigned)
+            return llops.genop('cast_bool_to_uint', [v], resulttype=Unsigned)
         else:
             if debug: print 'explicit cast_bool_to_int'
-            return direct_op('cast_bool_to_int', [v], resulttype=Signed)
+            return llops.genop('cast_bool_to_int', [v], resulttype=Signed)
 
 
 class __extend__(pairtype(SomeBool, SomeFloat)):
 
-    def rtype_convert_from_to((s_from, s_to), v):
+    def rtype_convert_from_to((s_from, s_to), v, llops):
         if debug: print 'explicit cast_bool_to_float'
-        return direct_op('cast_bool_to_float', [v], resulttype=Float)
+        return llops.genop('cast_bool_to_float', [v], resulttype=Float)
 
 
 class __extend__(SomeBool):
 
-    def rtype_is_true(s_bool):
-        v_bool = receive(Bool, 0)
-        return v_bool
+    def rtype_is_true(_, hop):
+        vlist = hop.inputargs(Bool)
+        return vlist[0]

Modified: pypy/dist/pypy/rpython/rbuiltin.py
==============================================================================
--- pypy/dist/pypy/rpython/rbuiltin.py	(original)
+++ pypy/dist/pypy/rpython/rbuiltin.py	Sun May 29 00:04:00 2005
@@ -1,8 +1,7 @@
 from pypy.annotation.pairtype import pair, pairtype
 from pypy.annotation.model import SomeBuiltin, SomeObject
 from pypy.rpython.lltype import malloc, typeOf, Void, Signed
-from pypy.rpython.rtyper import TyperError, peek_at_result_annotation
-from pypy.rpython.rtyper import receiveconst, receive, direct_op, convertvar
+from pypy.rpython.rtyper import TyperError
 
 
 class __extend__(SomeBuiltin):
@@ -16,42 +15,41 @@
             assert s_blt.methodname is not None
             return s_blt.s_self.lowleveltype()
 
-    def rtype_simple_call(s_blt, *args_s):
+    def rtype_simple_call(s_blt, hop):
         if s_blt.s_self is None:
             if not s_blt.is_constant():
                 raise TyperError("non-constant built-in")
             bltintyper = BUILTIN_TYPER[s_blt.const]
+            hop.s_popfirstarg()
         else:
             # methods: look up the rtype_method_xxx()
             name = 'rtype_method_' + s_blt.methodname
             bltintyper = getattr(s_blt.s_self, name)
-        return bltintyper(*args_s)
+        return bltintyper(hop)
 
 
 class __extend__(pairtype(SomeBuiltin, SomeObject)):
 
-    def rtype_convert_from_to((s_blt, s_to), v):
+    def rtype_convert_from_to((s_blt, s_to), v, llops):
         if s_blt.s_self is None:
             raise TyperError("conversion requested on a built-in function")
-        return convertvar(v, s_blt.s_self, s_to)
+        return llops.convertvar(v, s_blt.s_self, s_to)
 
 # ____________________________________________________________
 
-def rtype_malloc(s_pbc_type, s_varlength=None):
-    assert s_pbc_type.is_constant()
-    v_type = receiveconst(Void, s_pbc_type.const)
-    s_result = peek_at_result_annotation()
-    if s_varlength is None:
-        return direct_op('malloc', [v_type],
-                         resulttype = s_result.lowleveltype())
+def rtype_malloc(hop):
+    assert hop.args_s[0].is_constant()
+    if hop.nb_args == 1:
+        vlist = hop.inputargs(Void)
+        return hop.genop('malloc', vlist,
+                         resulttype = hop.s_result.lowleveltype())
     else:
-        v_varlength = receive(Signed, arg=2)   # NOTE, arg=0 is the s_blt above
-        return direct_op('malloc_varsize', [v_type, v_varlength],
-                         resulttype = s_result.lowleveltype())
-
-def rtype_typeOf(s_value):
-    s_result = peek_at_result_annotation()
-    return receiveconst(Void, s_result.const)
+        vlist = hop.inputargs(Void, Signed)
+        return hop.genop('malloc_varsize', vlist,
+                         resulttype = hop.s_result.lowleveltype())
+
+def rtype_typeOf(hop):
+    return hop.inputconst(Void, hop.s_result.const)
 
 
 BUILTIN_TYPER = {

Modified: pypy/dist/pypy/rpython/rfloat.py
==============================================================================
--- pypy/dist/pypy/rpython/rfloat.py	(original)
+++ pypy/dist/pypy/rpython/rfloat.py	Sun May 29 00:04:00 2005
@@ -1,7 +1,6 @@
 from pypy.annotation.pairtype import pairtype
 from pypy.annotation.model import SomeFloat, SomeInteger, SomeBool, SomePBC
 from pypy.rpython.lltype import Signed, Unsigned, Bool, Float
-from pypy.rpython.rtyper import receive, direct_op
 from pypy.rpython.rtyper import TyperError
 
 
@@ -11,125 +10,122 @@
 
     #Arithmetic
 
-    def rtype_add(args):
-        return _rtype_template(args, 'add')
+    def rtype_add(_, hop):
+        return _rtype_template(hop, 'add')
 
     rtype_inplace_add = rtype_add
 
-    def rtype_sub(args):
-        return _rtype_template(args, 'sub')
+    def rtype_sub(_, hop):
+        return _rtype_template(hop, 'sub')
 
     rtype_inplace_sub = rtype_sub
 
-    def rtype_mul(args):
-        return _rtype_template(args, 'mul')
+    def rtype_mul(_, hop):
+        return _rtype_template(hop, 'mul')
 
     rtype_inplace_mul = rtype_mul
 
-    def rtype_div(args):
-        return _rtype_template(args, 'div')
+    def rtype_div(_, hop):
+        return _rtype_template(hop, 'div')
 
     rtype_inplace_div = rtype_div
 
-    def rtype_pow((s_float1, s_float2), s_float3=SomePBC({None: True})):
-        if isinstance(s_float3, SomeInteger):
-            v_float3_list = [receive(Float, 2)]
-        elif s_float3.is_constant() and s_float3.const is None:
-            v_float3_list = []
+    def rtype_pow(_, hop):
+        s_float3 = hop.args_s[2]
+        if s_float3.is_constant() and s_float3.const is None:
+            vlist = hop.inputargs(Float, Float, Void)[:2]
         else:
-            raise TyperError("pow() 3rd argument must be int or None")
-        v_float1 = receive(Float, 0)
-        v_float2 = receive(Float, 1)
-        return direct_op('float_pow', [v_float1, v_float2] + v_float3_list, resulttype=Float)
+            vlist = hop.inputargs(Float, Float, Float)
+        return hop.genop('float_pow', vlist, resulttype=Float)
 
-    rtype_inplace_pow = rtype_pow
+    def rtype_inplace_pow(_, hop):
+        return _rtype_template(hop, 'pow')
 
     #comparisons: eq is_ ne lt le gt ge
 
-    def rtype_eq(args):
-        return _rtype_compare_template(args, 'eq')
+    def rtype_eq(_, hop):
+        return _rtype_compare_template(hop, 'eq')
 
     rtype_is_ = rtype_eq
 
-    def rtype_ne(args):
-        return _rtype_compare_template(args, 'ne')
+    def rtype_ne(_, hop):
+        return _rtype_compare_template(hop, 'ne')
 
-    def rtype_lt(args):
-        return _rtype_compare_template(args, 'lt')
+    def rtype_lt(_, hop):
+        return _rtype_compare_template(hop, 'lt')
 
-    def rtype_le(args):
-        return _rtype_compare_template(args, 'le')
+    def rtype_le(_, hop):
+        return _rtype_compare_template(hop, 'le')
 
-    def rtype_gt(args):
-        return _rtype_compare_template(args, 'gt')
+    def rtype_gt(_, hop):
+        return _rtype_compare_template(hop, 'gt')
 
-    def rtype_ge(args):
-        return _rtype_compare_template(args, 'ge')
+    def rtype_ge(_, hop):
+        return _rtype_compare_template(hop, 'ge')
 
 
 #Helpers SomeFloat,Somefloat
 
-def _rtype_template((s_float1, s_float2), func):
-        v_float1 = receive(Float, 0)
-        v_float2 = receive(Float, 1)
-        return direct_op('float_'+func, [v_float1, v_float2], resulttype=Float)
-
-def _rtype_compare_template((s_float1, s_float2), func):
-    v_float1 = receive(Float, 0)
-    v_float2 = receive(Float, 1)
-    return direct_op('float_'+func, [v_float1, v_float2], resulttype=Bool)
+def _rtype_template(hop, func):
+    vlist = hop.inputargs(Float, Float)
+    return hop.genop('float_'+func, vlist, resulttype=Float)
+
+def _rtype_compare_template(hop, func):
+    vlist = hop.inputargs(Float, Float)
+    return hop.genop('float_'+func, vlist, resulttype=Bool)
 
 
 #
 
-class __extend__(pairtype(SomeFloat, SomeInteger)):
+## XXX we have probably no implicit casts from float to integer
+##class __extend__(pairtype(SomeFloat, SomeInteger)):
 
-    def rtype_convert_from_to((s_from, s_to), v):
-        if s_to.unsigned:
-            if debug: print 'explicit cast_float_to_uint'
-            return direct_op('cast_float_to_uint', [v], resulttype=Unsigned)
-        else:
-            if debug: print 'explicit cast_float_to_int'
-            return direct_op('cast_float_to_int', [v], resulttype=Signed)
+##    def rtype_convert_from_to((s_from, s_to), v):
+##        if s_to.unsigned:
+##            if debug: print 'explicit cast_float_to_uint'
+##            return direct_op('cast_float_to_uint', [v], resulttype=Unsigned)
+##        else:
+##            if debug: print 'explicit cast_float_to_int'
+##            return direct_op('cast_float_to_int', [v], resulttype=Signed)
 
 
 #
 
 class __extend__(pairtype(SomeInteger, SomeFloat)):
 
-    def rtype_convert_from_to((s_from, s_to), v):
+    def rtype_convert_from_to((s_from, s_to), v, llops):
         if s_from.unsigned:
             if debug: print 'explicit cast_uint_to_float'
-            return direct_op('cast_uint_to_float', [v], resulttype=Float)
+            return llops.genop('cast_uint_to_float', [v], resulttype=Float)
         else:
             if debug: print 'explicit cast_int_to_float'
-            return direct_op('cast_int_to_float', [v], resulttype=Float)
+            return llops.genop('cast_int_to_float', [v], resulttype=Float)
 
 
 #
 
-class __extend__(pairtype(SomeFloat, SomeBool)):
+## XXX we have probably no implicit casts from float to bool
+##class __extend__(pairtype(SomeFloat, SomeBool)):
 
-    def rtype_convert_from_to((s_from, s_to), v):
-        if debug: print 'explicit cast_float_to_bool'
-        return direct_op('cast_float_to_bool', [v], resulttype=Bool)  #XXX or can 'float_is_true' be reused here? 
+##    def rtype_convert_from_to((s_from, s_to), v):
+##        if debug: print 'explicit cast_float_to_bool'
+##        return direct_op('cast_float_to_bool', [v], resulttype=Bool)  #XXX or can 'float_is_true' be reused here? 
 
 
 #
 
 class __extend__(SomeFloat):
 
-    def rtype_is_true(s_float):
-        v_float = receive(Float, 0)
-        return direct_op('float_is_true', [v_float], resulttype=Bool)
-
-    def rtype_nonzero(s_float):
-        v_float = receive(Float, 0)
-        return direct_op('float_nonzero', [v_float], resulttype=Bool)
+    def rtype_is_true(_, hop):
+        vlist = hop.inputargs(Float)
+        return hop.genop('float_is_true', vlist, resulttype=Bool)
+
+    rtype_nonzero = rtype_is_true
 
     def rtype_neg(s_int):
-        v_int = receive(Float, 0)
-        return direct_op('float_neg', [v_int], resulttype=Float)
+        vlist = receive(Float)
+        return hop.genop('float_neg', vlist, resulttype=Float)
 
     def rtype_pos(s_int):
-        return receive(Float, 0)
+        v_list = receive(Float)
+        return vlist[0]

Modified: pypy/dist/pypy/rpython/rint.py
==============================================================================
--- pypy/dist/pypy/rpython/rint.py	(original)
+++ pypy/dist/pypy/rpython/rint.py	Sun May 29 00:04:00 2005
@@ -1,7 +1,6 @@
 from pypy.annotation.pairtype import pairtype
 from pypy.annotation.model import SomeFloat, SomeInteger, SomeBool, SomePBC
 from pypy.rpython.lltype import Signed, Unsigned, Bool, Float
-from pypy.rpython.rtyper import receive, direct_op
 from pypy.rpython.rtyper import TyperError
 
 
@@ -9,299 +8,189 @@
 
 class __extend__(pairtype(SomeInteger, SomeInteger)):
 
-    def rtype_convert_from_to((s_from, s_to), v):
-        if s_from.unsigned != s_to.unsigned:        #XXX Can _receive_may_cast(...) be used here?
+    def rtype_convert_from_to((s_from, s_to), v, llops):
+        if s_from.unsigned != s_to.unsigned:
             if s_to.unsigned:
                 if debug: print 'explicit cast_int_to_uint'
-                return direct_op('cast_int_to_uint', [v], resulttype=Unsigned)
+                return llops.genop('cast_int_to_uint', [v], resulttype=Unsigned)
             else:
                 if debug: print 'explicit cast_uint_to_int'
-                return direct_op('cast_uint_to_int', [v], resulttype=Signed)
+                return llops.genop('cast_uint_to_int', [v], resulttype=Signed)
         return v
 
     #arithmetic
-    
-    def rtype_add((s_int1, s_int2)):
-        if s_int1.unsigned or s_int2.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_add', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_add', [v_int1, v_int2], resulttype=Signed)
 
+    def rtype_add(_, hop):
+        return _rtype_template(hop, 'add')
     rtype_inplace_add = rtype_add
 
-    def rtype_add_ovf((s_int1, s_int2)):
-        if s_int1.unsigned or s_int2.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_add_ovf', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_add_ovf', [v_int1, v_int2], resulttype=Signed)
-
+    def rtype_add_ovf(_, hop):
+        return _rtype_template(hop, 'add_ovf')
     rtype_inplace_add_ovf = rtype_add_ovf
 
-    def rtype_sub((s_int1, s_int2)):
-        if s_int1.unsigned or s_int2.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_sub', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_sub', [v_int1, v_int2], resulttype=Signed)
-
+    def rtype_sub(_, hop):
+        return _rtype_template(hop, 'sub')
     rtype_inplace_sub = rtype_sub
 
-    def rtype_sub_ovf((s_int1, s_int2)):
-        if s_int1.unsigned or s_int2.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_sub_ovf', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_sub_ovf', [v_int1, v_int2], resulttype=Signed)
-
+    def rtype_sub_ovf(_, hop):
+        return _rtype_template(hop, 'sub_ovf')
     rtype_inplace_sub_ovf = rtype_sub_ovf
 
-    def rtype_mul((s_int1, s_int2)):
-        if s_int1.unsigned or s_int2.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_mul', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_mul', [v_int1, v_int2], resulttype=Signed)
-
+    def rtype_mul(_, hop):
+        return _rtype_template(hop, 'mul')
     rtype_inplace_mul = rtype_mul
 
-    def rtype_div((s_int1, s_int2)):
-        if s_int1.unsigned or s_int2.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_div', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_div', [v_int1, v_int2], resulttype=Signed)
-
+    def rtype_div(_, hop):
+        return _rtype_template(hop, 'div')
     rtype_inplace_div = rtype_div
 
-    def rtype_mod((s_int1, s_int2)):
-        if s_int1.unsigned or s_int2.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_mod', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_mod', [v_int1, v_int2], resulttype=Signed)
-
+    def rtype_mod(_, hop):
+        return _rtype_template(hop, 'mod')
     rtype_inplace_mod = rtype_mod
 
-    def rtype_xor((s_int1, s_int2)):
-        if s_int1.unsigned or s_int2.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_xor', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_xor', [v_int1, v_int2], resulttype=Signed)
-
+    def rtype_xor(_, hop):
+        return _rtype_template(hop, 'xor')
     rtype_inplace_xor = rtype_xor
 
-    def rtype_and_((s_int1, s_int2)):
-        if s_int1.unsigned or s_int2.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_and', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_and', [v_int1, v_int2], resulttype=Signed)
-
+    def rtype_and_(_, hop):
+        return _rtype_template(hop, 'and')
     rtype_inplace_and = rtype_and_
 
-    def rtype_or_((s_int1, s_int2)):
-        if s_int1.unsigned or s_int2.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_or', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_or', [v_int1, v_int2], resulttype=Signed)
-
+    def rtype_or_(_, hop):
+        return _rtype_template(hop, 'or')
     rtype_inplace_or = rtype_or_
 
-    def rtype_lshift((s_int1, s_int2)):
-        if s_int1.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_lshift', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_lshift', [v_int1, v_int2], resulttype=Signed)
-
+    def rtype_lshift(_, hop):
+        return _rtype_template(hop, 'lshift')
     rtype_inplace_lshift = rtype_lshift
 
-    def rtype_rshift((s_int1, s_int2)):
-        if s_int1.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_rshift', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_rshift', [v_int1, v_int2], resulttype=Signed)
-
-    rtype_inplace_rshift = rtype_rshift
-
-    def rtype_lshift_ovf((s_int1, s_int2)):
-        if s_int1.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_lshift_ovf', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_lshift_ovf', [v_int1, v_int2], resulttype=Signed)
-
+    def rtype_lshift_ovf(_, hop):
+        return _rtype_template(hop, 'lshift_ovf')
     rtype_inplace_lshift_ovf = rtype_lshift_ovf
 
-    def rtype_rshift_ovf((s_int1, s_int2)):
-        if s_int1.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_rshift_ovf', [v_int1, v_int2], resulttype=Unsigned)
-        else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_rshift_ovf', [v_int1, v_int2], resulttype=Signed)
+    def rtype_rshift(_, hop):
+        return _rtype_template(hop, 'rshift')
+    rtype_inplace_rshift = rtype_rshift
 
+    def rtype_rshift_ovf(_, hop):
+        return _rtype_template(hop, 'rshift_ovf')
     rtype_inplace_rshift_ovf = rtype_rshift_ovf
 
-    def rtype_pow((s_int1, s_int2), s_int3=SomePBC({None: True})):
-        if isinstance(s_int3, SomeInteger):
-            if s_int3.unsigned:
-                v_int3_list = [_receive_may_cast(s_int1, Unsigned, 2)]
+    def rtype_pow(_, hop):
+        s_int3 = hop.args_s[2]
+        if hop.s_result.unsigned:
+            if s_int3.is_constant() and s_int3.const is None:
+                vlist = hop.inputargs(Unsigned, Unsigned, Void)[:2]
             else:
-                v_int3_list = [_receive_may_cast(s_int1, Signed, 2)]
-        elif s_int3.is_constant() and s_int3.const is None:
-            v_int3_list = []
-        else:
-            raise TyperError("pow() 3rd argument must be int or None")
-        if s_int1.unsigned or s_int2.unsigned:
-            v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-            v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-            return direct_op('uint_pow', [v_int1, v_int2] + v_int3_list, resulttype=Unsigned)
+                vlist = hop.inputargs(Unsigned, Unsigned, Unsigned)
+            return hop.genop('uint_pow', vlist, resulttype=Unsigned)
         else:
-            v_int1 = _receive_may_cast(s_int1, Signed, 0)
-            v_int2 = _receive_may_cast(s_int2, Signed, 1)
-            return direct_op('int_pow', [v_int1, v_int2] + v_int3_list, resulttype=Signed)
+            if s_int3.is_constant() and s_int3.const is None:
+                vlist = hop.inputargs(Signed, Signed, Void)[:2]
+            else:
+                vlist = hop.inputargs(Signed, Signed, Signed)
+            return hop.genop('int_pow', vlist, resulttype=Signed)
 
-    rtype_inplace_pow = rtype_pow
+    def rtype_inplace_pow(_, hop):
+        return _rtype_template(hop, 'pow')
 
     #comparisons: eq is_ ne lt le gt ge
 
-    def rtype_eq(args): 
-        return _rtype_compare_template(args, 'eq')
+    def rtype_eq(_, hop): 
+        return _rtype_compare_template(hop, 'eq')
 
     rtype_is_ = rtype_eq
 
-    def rtype_ne(args):
-        return _rtype_compare_template(args, 'ne')
+    def rtype_ne(_, hop):
+        return _rtype_compare_template(hop, 'ne')
 
-    def rtype_lt(args):
-        return _rtype_compare_template(args, 'lt')
+    def rtype_lt(_, hop):
+        return _rtype_compare_template(hop, 'lt')
 
-    def rtype_le(args):
-        return _rtype_compare_template(args, 'le')
+    def rtype_le(_, hop):
+        return _rtype_compare_template(hop, 'le')
 
-    def rtype_gt(args):
-        return _rtype_compare_template(args, 'gt')
+    def rtype_gt(_, hop):
+        return _rtype_compare_template(hop, 'gt')
 
-    def rtype_ge(args):
-        return _rtype_compare_template(args, 'ge')
+    def rtype_ge(_, hop):
+        return _rtype_compare_template(hop, 'ge')
 
 #Helper functions
 
-def _receive_may_cast(s_var, s_requested, arg):
-    v = receive(s_requested, arg)
-    s = (Signed,Unsigned)[s_var.unsigned]
-    if s != s_requested:
-        if s_requested is Unsigned:
-            if debug: print 'cast_int_to_uint'
-            return direct_op('cast_int_to_uint', [v], resulttype=Unsigned)
-        else:
-            if debug: print 'cast_uint_to_int'
-            return direct_op('cast_uint_to_int', [v], resulttype=Signed)
-    #elif debug:
-    #    if s_requested is Unsigned:
-    #        if debug: print 'fake cast_uint_to_uint'
-    #        return direct_op('cast_uint_to_uint', [v], resulttype=Unsigned)
-    #    else:
-    #        if debug: print 'fake cast_int_to_int'
-    #        return direct_op('cast_int_to_int', [v], resulttype=Signed)
-    return v
-    
+def _rtype_template(hop, func):
+    if hop.s_result.unsigned:
+        vlist = hop.inputargs(Unsigned, Unsigned)
+        return hop.genop('uint_'+func, vlist, resulttype=Unsigned)
+    else:
+        vlist = hop.inputargs(Signed, Signed)
+        return hop.genop('int_'+func, vlist, resulttype=Signed)
+
 #Helper functions for comparisons
 
-def _rtype_compare_template((s_int1, s_int2), func):
+def _rtype_compare_template(hop, func):
+    s_int1, s_int2 = hop.args_s
     if s_int1.unsigned or s_int2.unsigned:
         if not s_int1.nonneg or not s_int2.nonneg:
             raise TyperError("comparing a signed and an unsigned number")
-        v_int1 = _receive_may_cast(s_int1, Unsigned, 0)
-        v_int2 = _receive_may_cast(s_int2, Unsigned, 1)
-        return direct_op('uint_'+func, [v_int1, v_int2], resulttype=Bool)
+        vlist = hop.inputargs(Unsigned, Unsigned)
+        return hop.genop('uint_'+func, vlist, resulttype=Bool)
     else:
-        v_int1 = _receive_may_cast(s_int1, Signed, 0)
-        v_int2 = _receive_may_cast(s_int2, Signed, 1)
-        return direct_op('int_'+func, [v_int1, v_int2], resulttype=Bool)
+        vlist = hop.inputargs(Signed, Signed)
+        return hop.genop('int_'+func, vlist, resulttype=Bool)
 
 
 #
 
 class __extend__(SomeInteger):
 
-    def rtype_is_true(s_int):
-        v_int = _receive_may_cast(s_int, Signed, 0)
-        return direct_op('int_is_true', [v_int], resulttype=Bool)
-
-    #Unary arithmetic operations    
-    
-    def rtype_abs(s_int):
+    def rtype_is_true(s_int, hop):
         if s_int.unsigned:
-            return _receive_may_cast(s_int, Unsigned, 0)
+            vlist = hop.inputargs(Unsigned)
+            return hop.genop('uint_is_true', vlist, resulttype=Bool)
         else:
-            v_int = _receive_may_cast(s_int, Signed, 0)
-            return direct_op('int_abs', [v_int], resulttype=Signed) #XXX I would like to make this Unsigned, but the annotator insists it is Signed!
+            vlist = hop.inputargs(Signed)
+            return hop.genop('int_is_true', vlist, resulttype=Bool)
 
-    def rtype_abs_ovf(s_int):
-        if s_int.unsigned:
-            return _receive_may_cast(s_int, Unsigned, 0)
-        else:
-            v_int = _receive_may_cast(s_int, Signed, 0)
-            direct_op('int_abs_ovf', [v_int], resulttype=Signed) #XXX I would like to make this Unsigned, but the annotator insists it is Signed!
+    rtype_nonzero = rtype_is_true
 
-    def rtype_invert(s_int):
-        v_int = _receive_may_cast(s_int, Signed, 0)
-        return direct_op('int_invert', [v_int], resulttype=Signed)
-
-    def rtype_neg(s_int):
-        v_int = _receive_may_cast(s_int, Signed, 0)
-        return direct_op('int_neg', [v_int], resulttype=Signed)
+    #Unary arithmetic operations    
+    
+    def rtype_abs(_, hop):
+        if hop.s_result.unsigned:
+            vlist = hop.inputargs(Unsigned)
+            return vlist[0]
+        else:
+            vlist = hop.inputargs(Signed)
+            return hop.genop('int_abs', vlist, resulttype=Signed)
+
+    def rtype_abs_ovf(_, hop):
+        if hop.s_result.unsigned:
+            vlist = hop.inputargs(Unsigned)
+            return vlist[0]
+        else:
+            vlist = hop.inputargs(Signed)
+            return hop.genop('int_abs_ovf', vlist, resulttype=Signed)
+
+    def rtype_invert(_, hop):
+        if hop.s_result.unsigned:
+            vlist = hop.inputargs(Unsigned)
+            return hop.genop('uint_invert', vlist, resulttype=Unsigned)
+        else:
+            vlist = hop.inputargs(Signed)
+            return hop.genop('int_invert', vlist, resulttype=Signed)
+
+    def rtype_neg(_, hop):
+        if hop.s_result.unsigned:
+            vlist = hop.inputargs(Unsigned)
+            return hop.genop('uint_neg', vlist, resulttype=Unsigned)
+        else:
+            vlist = hop.inputargs(Signed)
+            return hop.genop('int_neg', vlist, resulttype=Signed)
 
-    def rtype_pos(s_int):
+    def rtype_pos(_, hop):
         if s_int.unsigned:
-            return _receive_may_cast(s_int, Unsigned, 0)
+            vlist = hop.inputargs(Unsigned)
         else:
-            return _receive_may_cast(s_int, Signed, 0)
+            vlist = hop.inputargs(Signed)
+        return vlist[0]

Modified: pypy/dist/pypy/rpython/rlist.py
==============================================================================
--- pypy/dist/pypy/rpython/rlist.py	(original)
+++ pypy/dist/pypy/rpython/rlist.py	Sun May 29 00:04:00 2005
@@ -1,8 +1,6 @@
 from pypy.annotation.pairtype import pair, pairtype
 from pypy.annotation.model import SomeList, SomeInteger
 from pypy.rpython.lltype import *
-from pypy.rpython.rtyper import receive, receiveconst
-from pypy.rpython.rtyper import peek_at_result_annotation, direct_call
 
 # ____________________________________________________________
 #
@@ -26,25 +24,24 @@
     def get_s_items(s_list):
         return s_list.listdef.listitem.s_value
 
-    def rtype_len(s_lst):
-        v_lst = receive(s_lst, arg=0)
-        return direct_call(ll_len, v_lst)
-
-    def rtype_method_append(s_lst, s_value):
-        v_lst = receive(s_lst, arg=0)
-        v_value = receive(s_lst.get_s_items(), arg=1)
-        direct_call(ll_append, v_lst, v_value)
+    def rtype_len(s_lst, hop):
+        v_lst = hop.inputargs(s_lst)
+        return hop.gendirectcall(ll_len, v_lst)
+
+    def rtype_method_append(s_lst, hop):
+        v_lst, v_value = hop.inputargs(s_lst, s_lst.get_s_items())
+        hop.gendirectcall(ll_append, v_lst, v_value)
 
 
 class __extend__(pairtype(SomeList, SomeInteger)):
 
-    def rtype_getitem((s_lst1, s_int2)):
-        v_lst = receive(s_lst1, arg=0)
-        v_index = receive(Signed, arg=1)
+    def rtype_getitem((s_lst1, s_int2), hop):
+        v_lst, v_index = hop.inputargs(s_lst1, Signed)
         if s_int2.nonneg:
-            return direct_call(ll_getitem_nonneg, v_lst, v_index)
+            llfn = ll_getitem_nonneg
         else:
-            return direct_call(ll_getitem, v_lst, v_index)
+            llfn = ll_getitem
+        return hop.gendirectcall(llfn, v_lst, v_index)
 
 
 # ____________________________________________________________
@@ -86,15 +83,15 @@
     l.items = malloc(LISTPTR.TO.items.TO, length)
     return l
 
-def rtype_newlist(*items_s):
-    nb_args = len(items_s)
-    s_list = peek_at_result_annotation()
+def rtype_newlist(hop):
+    nb_args = hop.nb_args
+    s_list = hop.s_result
     s_listitem = s_list.get_s_items()
-    items_v = [receive(s_listitem, arg=i) for i in range(nb_args)]
-    c1 = receiveconst(Void, s_list.lowleveltype())
-    v_result = direct_call(ll_newlist, c1, receiveconst(Signed, nb_args))
+    c1 = hop.inputconst(Void, s_list.lowleveltype())
+    c2 = hop.inputconst(Signed, nb_args)
+    v_result = hop.gendirectcall(ll_newlist, c1, c2)
     for i in range(nb_args):
-        direct_call(ll_setitem_nonneg, v_result,
-                                       receiveconst(Signed, i),
-                                       items_v[i])
+        ci = hop.inputconst(Signed, i)
+        v_item = hop.inputarg(s_listitem, arg=i)
+        hop.gendirectcall(ll_setitem_nonneg, v_result, ci, v_item)
     return v_result

Modified: pypy/dist/pypy/rpython/robject.py
==============================================================================
--- pypy/dist/pypy/rpython/robject.py	(original)
+++ pypy/dist/pypy/rpython/robject.py	Sun May 29 00:04:00 2005
@@ -2,7 +2,6 @@
 from pypy.annotation.model import SomeObject, annotation_to_lltype
 from pypy.rpython.lltype import PyObject, GcPtr, Void
 from pypy.rpython.rtyper import TyperError
-from pypy.rpython.rtyper import receiveconst, receive
 
 
 PyObjPtr = GcPtr(PyObject)
@@ -19,7 +18,8 @@
             else:
                 return PyObjPtr
 
-    def rtype_getattr(s_obj, s_attr):
+    def rtype_getattr(s_obj, hop):
+        s_attr = hop.args_s[1]
         if s_attr.is_constant() and isinstance(s_attr.const, str):
             attr = s_attr.const
             try:
@@ -28,14 +28,14 @@
                 raise TyperError("no method %s on %r" % (attr, s_obj))
             else:
                 # implement methods (of a known name) as just their 'self'
-                return receive(s_obj, arg=0)
+                return hop.inputarg(s_obj, arg=0)
         else:
             raise TyperError("getattr() with a non-constant attribute name")
 
 
 class __extend__(pairtype(SomeObject, SomeObject)):
 
-    def rtype_convert_from_to((s_from, s_to), v):
+    def rtype_convert_from_to((s_from, s_to), v, llops):
         FROM = s_from.lowleveltype()
         TO   = s_to.lowleveltype()
         if PyObjPtr == FROM == TO:

Modified: pypy/dist/pypy/rpython/rpbc.py
==============================================================================
--- pypy/dist/pypy/rpython/rpbc.py	(original)
+++ pypy/dist/pypy/rpython/rpbc.py	Sun May 29 00:04:00 2005
@@ -2,31 +2,28 @@
 from pypy.annotation.pairtype import pair, pairtype
 from pypy.annotation.model import SomePBC
 from pypy.rpython.lltype import typeOf
-from pypy.rpython.rtyper import TLS, receive, receiveconst, direct_op
-from pypy.rpython.rtyper import peek_at_result_annotation
 
 
 class __extend__(SomePBC):
 
-    def rtype_getattr(s_pbc, s_attr):
-        attr = s_attr.const
-        s_result = peek_at_result_annotation()
-        if s_result.is_constant():
-            return receiveconst(s_result, s_result.const)
+    def rtype_getattr(_, hop):
+        attr = hop.args_s[1].const
+        if hop.s_result.is_constant():
+            return hop.inputconst(hop.s_result, hop.s_result.const)
         else:
             NotImplementedYet
 
-    def rtype_simple_call(s_pbc, *args_s):
-        if not s_pbc.is_constant():
+    def rtype_simple_call(_, hop):
+        s_func = hop.s_popfirstarg()
+        if not s_func.is_constant():
             NotImplementedYet
-        func = s_pbc.const
+        func = s_func.const
         if not isinstance(func, types.FunctionType):
             NotImplementedYet
         # XXX hackish
-        f = TLS.rtyper.getfunctionptr(func)
+        f = hop.rtyper.getfunctionptr(func)
         FUNCPTR = typeOf(f)
-        args_v = [receive(FUNCPTR.TO.ARGS[i], arg=i+1)
-                  for i in range(len(args_s))]
-        c = receiveconst(FUNCPTR, f)
-        return direct_op('direct_call', [c] + args_v,
+        args_v = hop.inputargs(*FUNCPTR.TO.ARGS)
+        c = hop.inputconst(FUNCPTR, f)
+        return hop.genop('direct_call', [c] + args_v,
                          resulttype = FUNCPTR.TO.RESULT)

Modified: pypy/dist/pypy/rpython/rptr.py
==============================================================================
--- pypy/dist/pypy/rpython/rptr.py	(original)
+++ pypy/dist/pypy/rpython/rptr.py	Sun May 29 00:04:00 2005
@@ -1,8 +1,6 @@
 from pypy.annotation.pairtype import pair, pairtype
 from pypy.annotation.model import SomePtr, SomeInteger
 from pypy.rpython.lltype import ContainerType, Void, Signed
-from pypy.rpython.rtyper import receive, receiveconst
-from pypy.rpython.rtyper import peek_at_result_annotation, direct_op
 
 
 class __extend__(SomePtr):
@@ -10,40 +8,33 @@
     def lowleveltype(s_ptr):
         return s_ptr.ll_ptrtype
 
-    def rtype_getattr(s_ptr, s_attr):
-        attr = s_attr.const
+    def rtype_getattr(s_ptr, hop):
+        attr = hop.args_s[1].const
         FIELD_TYPE = getattr(s_ptr.ll_ptrtype.TO, attr)
         if isinstance(FIELD_TYPE, ContainerType):
             newopname = 'getsubstruct'
         else:
             newopname = 'getfield'
-        v_ptr = receive(s_ptr, arg=0)
-        v_attr = receiveconst(Void, attr)
-        s_result = peek_at_result_annotation()
-        return direct_op(newopname, [v_ptr, v_attr],
-                         resulttype = s_result.lowleveltype())
+        vlist = hop.inputargs(s_ptr, Void)
+        return hop.genop(newopname, vlist,
+                         resulttype = hop.s_result.lowleveltype())
 
-    def rtype_setattr(s_ptr, s_attr, s_value):
-        attr = s_attr.const
+    def rtype_setattr(s_ptr, hop):
+        attr = hop.args_s[1].const
         FIELD_TYPE = getattr(s_ptr.ll_ptrtype.TO, attr)
         assert not isinstance(FIELD_TYPE, ContainerType)
-        v_ptr = receive(s_ptr, arg=0)
-        v_attr = receiveconst(Void, attr)
-        v_value = receive(FIELD_TYPE, arg=2)
-        direct_op('setfield', [v_ptr, v_attr, v_value])
-
-    def rtype_len(s_ptr):
-        v_ptr = receive(s_ptr, arg=0)
-        s_result = peek_at_result_annotation()
-        return direct_op('getarraysize', [v_ptr],
-                         resulttype = s_result.lowleveltype())
+        vlist = hop.inputargs(s_ptr, Void, FIELD_TYPE)
+        hop.genop('setfield', vlist)
+
+    def rtype_len(s_ptr, hop):
+        vlist = hop.inputargs(s_ptr)
+        return hop.genop('getarraysize', vlist,
+                         resulttype = hop.s_result.lowleveltype())
 
 
 class __extend__(pairtype(SomePtr, SomeInteger)):
 
-    def rtype_getitem((s_ptr, s_int)):
-        v_ptr = receive(s_ptr, arg=0)
-        v_index = receive(Signed, arg=1)
-        s_result = peek_at_result_annotation()
-        return direct_op('getarrayitem', [v_ptr, v_index],
-                         resulttype = s_result.lowleveltype())
+    def rtype_getitem((s_ptr, s_int), hop):
+        vlist = hop.inputargs(s_ptr, Signed)
+        return hop.genop('getarrayitem', vlist,
+                         resulttype = hop.s_result.lowleveltype())

Modified: pypy/dist/pypy/rpython/rtyper.py
==============================================================================
--- pypy/dist/pypy/rpython/rtyper.py	(original)
+++ pypy/dist/pypy/rpython/rtyper.py	Sun May 29 00:04:00 2005
@@ -4,12 +4,9 @@
 from pypy.objspace.flow.model import SpaceOperation
 from pypy.rpython.lltype import Void, LowLevelType, NonGcPtr, ContainerType
 from pypy.rpython.lltype import FuncType, functionptr, typeOf
-from pypy.tool.tls import tlsobject
 from pypy.tool.sourcetools import func_with_new_name, valid_identifier
 from pypy.translator.unsimplify import insert_empty_block
 
-TLS = tlsobject()
-
 
 # XXX copied from pypy.translator.typer and modified.
 #     We'll remove pypy.translator.typer at some point.
@@ -48,16 +45,6 @@
         if s_value is not None:
             v.concretetype = s_value.lowleveltype()
 
-    def enter_operation(self, op, newops):
-        TLS.rtyper = self
-        TLS.currentoperation = op
-        TLS.newops = newops
-
-    def leave_operation(self):
-        del TLS.rtyper
-        del TLS.currentoperation
-        del TLS.newops
-
     def specialize_block(self, block):
         # give the best possible types to the input args
         for a in block.inputargs:
@@ -66,19 +53,12 @@
         # specialize all the operations, as far as possible
         if block.operations == ():   # return or except block
             return
-        newops = []
+        newops = LowLevelOpList(self)
         varmapping = {}
         for op in block.operations:
             try:
-                args = list(op.args)
-                bindings = [self.annotator.binding(a, True) for a in args]
-
-                self.enter_operation(op, newops)
-                try:
-                    self.consider_op(op, varmapping)
-                finally:
-                    self.leave_operation()
-
+                hop = HighLevelOp(self, op, newops)
+                self.translate_hl_to_ll(hop, varmapping)
             except TyperError, e:
                 e.where = (block, op)
                 raise
@@ -110,12 +90,8 @@
                     s_a2 = self.annotator.binding(a2)
                     if s_a1 == s_a2:
                         continue   # no conversion needed
-                    newops = []
-                    self.enter_operation(None, newops)
-                    try:
-                        a1 = convertvar(a1, s_a1, s_a2)
-                    finally:
-                        self.leave_operation()
+                    newops = LowLevelOpList(self)
+                    a1 = newops.convertvar(a1, s_a1, s_a2)
                     if newops and not can_insert_here:
                         # cannot insert conversion operations around a single
                         # link, unless it is the only exit of this block.
@@ -132,23 +108,22 @@
                 e.where = (block, link)
                 raise
 
-    def consider_op(self, op, varmapping):
-        argcells = [self.annotator.binding(a) for a in op.args]
-        consider_meth = getattr(self, 'consider_op_'+op.opname)
-        resultvar = consider_meth(*argcells)
-        s_expected = self.annotator.binding(op.result)
+    def translate_hl_to_ll(self, hop, varmapping):
+        op = hop.spaceop
+        translate_meth = getattr(self, 'translate_op_'+op.opname)
+        resultvar = translate_meth(hop)
         if resultvar is None:
             # no return value
-            if s_expected != annmodel.SomeImpossibleValue():
+            if hop.s_result != annmodel.SomeImpossibleValue():
                 raise TyperError("the annotator doesn't agree that '%s' "
                                  "has no return value" % op.opname)
             op.result.concretetype = Void
         elif isinstance(resultvar, Variable):
-            # for simplicity of the consider_meth, resultvar is usually not
+            # for simplicity of the translate_meth, resultvar is usually not
             # op.result here.  We have to replace resultvar with op.result
             # in all generated operations.
             resulttype = resultvar.concretetype
-            op.result.concretetype = s_expected.lowleveltype()
+            op.result.concretetype = hop.s_result.lowleveltype()
             if op.result.concretetype != resulttype:
                 raise TyperError("inconsistent type for the result of '%s':\n"
                                  "annotator says %r\n"
@@ -159,15 +134,14 @@
                 resultvar = varmapping[resultvar]
             varmapping[resultvar] = op.result
         else:
-            # consider_meth() can actually generate no operation and return
-            # a Constant.
-            if not s_expected.is_constant():
+            # translate_meth() returned a Constant
+            if not hop.s_result.is_constant():
                 raise TyperError("the annotator doesn't agree that '%s' "
                                  "returns a constant" % op.opname)
-            if resultvar.value != s_expected.const:
+            if resultvar.value != hop.s_result.const:
                 raise TyperError("constant mismatch: %r vs %r" % (
-                    resultvar.value, s_expected.const))
-            op.result.concretetype = s_expected.lowleveltype()
+                    resultvar.value, hop.s_result.const))
+            op.result.concretetype = hop.s_result.lowleveltype()
 
     # __________ regular operations __________
 
@@ -175,14 +149,17 @@
         # All unary operations
         for opname in annmodel.UNARY_OPERATIONS:
             exec """
-def consider_op_%s(self, arg, *args):
-    return arg.rtype_%s(*args)
+def translate_op_%s(self, hop):
+    s_arg1 = hop.args_s[0]
+    return s_arg1.rtype_%s(hop)
 """ % (opname, opname) in globals(), loc
         # All binary operations
         for opname in annmodel.BINARY_OPERATIONS:
             exec """
-def consider_op_%s(self, arg1, arg2, *args):
-    return pair(arg1,arg2).rtype_%s(*args)
+def translate_op_%s(self, hop):
+    s_arg1 = hop.args_s[0]
+    s_arg2 = hop.args_s[1]
+    return pair(s_arg1, s_arg2).rtype_%s(hop)
 """ % (opname, opname) in globals(), loc
 
     _registeroperations(locals())
@@ -190,8 +167,8 @@
 
     # __________ irregular operations __________
 
-    def consider_op_newlist(self, *items_s):
-        return rlist.rtype_newlist(*items_s)
+    def translate_op_newlist(self, hop):
+        return rlist.rtype_newlist(hop)
 
     # __________ utilities __________
 
@@ -208,29 +185,17 @@
         FT = FuncType(llinputs, lloutput)
         return functionptr(FT, func.func_name, graph = graph, _callable = func)
 
-# ____________________________________________________________
-#
-#  Global helpers, working on the current operation (as stored in TLS)
 
-def _requestedtype(s_requested):
-    if isinstance(s_requested, LowLevelType):
-        lowleveltype = s_requested
-        s_requested = annmodel.lltype_to_annotation(lowleveltype)
-    elif isinstance(s_requested, annmodel.SomeObject):
-        lowleveltype = s_requested.lowleveltype()
-    else:
-        raise TypeError("SomeObject or LowLevelType expected, got %r" % (
-            s_requested,))
-    return s_requested, lowleveltype
+# ____________________________________________________________
 
-def receiveconst(s_requested, value):
+def inputconst(type, value):
     """Return a Constant with the given value, of the requested type.
-    s_requested can be a SomeXxx annotation or a primitive low-level type.
+    'type' can be a SomeXxx annotation or a low-level type.
     """
-    if isinstance(s_requested, LowLevelType):
-        lowleveltype = s_requested
+    if isinstance(type, LowLevelType):
+        lowleveltype = type
     else:
-        lowleveltype = s_requested.lowleveltype()
+        lowleveltype = type.lowleveltype()
     assert not isinstance(lowleveltype, ContainerType), (
         "missing a GcPtr or NonGcPtr in the type specification of %r" %
         (lowleveltype,))
@@ -238,84 +203,126 @@
     c.concretetype = lowleveltype
     return c
 
-def receive(s_requested, arg):
-    """Returns the arg'th input argument of the current operation,
-    as a Variable or Constant converted to the requested type.
-    s_requested can be a SomeXxx annotation or a primitive low-level type.
+# ____________________________________________________________
+
+class HighLevelOp:
+    nb_popped = 0
+
+    def __init__(self, rtyper, spaceop, llops):
+        self.rtyper   = rtyper
+        self.spaceop  = spaceop
+        self.nb_args  = len(spaceop.args)
+        self.llops    = llops
+        self.args_s   = [rtyper.annotator.binding(a) for a in spaceop.args]
+        self.s_result = rtyper.annotator.binding(spaceop.result)
+
+    def inputarg(self, converted_to, arg):
+        """Returns the arg'th input argument of the current operation,
+        as a Variable or Constant converted to the requested type.
+        'converted_to' can be a SomeXxx annotation or a primitive low-level
+        type.
+        """
+        v = self.spaceop.args[self.nb_popped + arg]
+        if isinstance(v, Constant):
+            return inputconst(converted_to, v.value)
+
+        s_binding = self.args_s[arg]
+        if s_binding is None:
+            s_binding = annmodel.SomeObject()
+        if s_binding.is_constant():
+            return inputconst(converted_to, s_binding.const)
+
+        if isinstance(converted_to, LowLevelType):
+            converted_to = annmodel.lltype_to_annotation(converted_to)
+        return self.llops.convertvar(v, s_binding, converted_to)
+
+    def inputargs(self, *converted_to):
+        assert len(converted_to) == self.nb_args, (
+            "operation argument count mismatch: '%s' has %d+%d arguments" % (
+            self.spaceop.opname, self.nb_popped, self.nb_args))
+        vars = []
+        for i in range(len(converted_to)):
+            vars.append(self.inputarg(converted_to[i], i))
+        return vars
+
+    inputconst = staticmethod(inputconst)    # export via the HighLevelOp class
+
+    def genop(self, opname, args_v, resulttype=None):
+        return self.llops.genop(opname, args_v, resulttype)
+
+    def gendirectcall(self, ll_function, *args_v):
+        return self.llops.gendirectcall(ll_function, *args_v)
+
+    def s_popfirstarg(self):
+        "Return and discard the first argument."
+        self.nb_popped += 1
+        self.nb_args -= 1
+        return self.args_s.pop(0)
+
+# ____________________________________________________________
+
+class LowLevelOpList(list):
+    """A list with gen*() methods to build and append low-level
+    operations to it.
     """
-    v = TLS.currentoperation.args[arg]
-    if isinstance(v, Constant):
-        return receiveconst(s_requested, v.value)
-
-    s_binding = TLS.rtyper.annotator.binding(v, True)
-    if s_binding is None:
-        s_binding = annmodel.SomeObject()
-    if s_binding.is_constant():
-        return receiveconst(s_requested, s_binding.const)
-
-    s_requested, lowleveltype = _requestedtype(s_requested)
-    return convertvar(v, s_binding, s_requested)
-
-def convertvar(v, s_from, s_to):
-    if s_from != s_to:
-        v = pair(s_from, s_to).rtype_convert_from_to(v)
-    return v
-
-
-def peek_at_result_annotation():
-    return TLS.rtyper.annotator.binding(TLS.currentoperation.result)
-
-
-def direct_call(ll_function, *args_v):
-    annotator = TLS.rtyper.annotator
-    spec_key = [ll_function]
-    spec_name = [ll_function.func_name]
-    args_s = []
-    for v in args_v:
-        s_value = annotator.binding(v, True)
-        if s_value is None:
-            s_value = annmodel.SomeObject()
-        if v.concretetype == Void:
-            if not s_value.is_constant():
-                raise TyperError("non-constant variable of type Void")
-            key = s_value.const       # specialize by constant value
-            args_s.append(s_value)
-            suffix = 'Const'
-        else:
-            key = v.concretetype      # specialize by low-level type
-            args_s.append(annmodel.lltype_to_annotation(key))
-            suffix = ''
-        spec_key.append(key)
-        spec_name.append(valid_identifier(getattr(key, '__name__', key))+suffix)
-    spec_key = tuple(spec_key)
-    try:
-        spec_function = TLS.rtyper.specialized_ll_functions[spec_key]
-    except KeyError:
-        name = '_'.join(spec_name)
-        spec_function = func_with_new_name(ll_function, name)
-        # flow and annotate (the copy of) the low-level function
-        spec_graph = annotator.translator.getflowgraph(spec_function)
-        annotator.build_types(spec_function, args_s)
-        # cache the result
-        TLS.rtyper.specialized_ll_functions[spec_key] = spec_function
-
-    # build the 'direct_call' operation
-    f = TLS.rtyper.getfunctionptr(spec_function)
-    c = receiveconst(typeOf(f), f)
-    return direct_op('direct_call', [c]+list(args_v),
-                     resulttype = typeOf(f).TO.RESULT)
-
-
-def direct_op(opname, args, resulttype=None):
-    v = Variable()
-    TLS.newops.append(SpaceOperation(opname, args, v))
-    if resulttype is None:
-        v.concretetype = Void
-        return None
-    else:
-        v.concretetype = resulttype
+    def __init__(self, rtyper):
+        self.rtyper = rtyper
+
+    def convertvar(self, v, s_from, s_to):
+        if s_from != s_to:
+            v = pair(s_from, s_to).rtype_convert_from_to(v, self)
         return v
 
+    def genop(self, opname, args_v, resulttype=None):
+        vresult = Variable()
+        self.append(SpaceOperation(opname, args_v, vresult))
+        if resulttype is None:
+            vresult.concretetype = Void
+            return None
+        else:
+            vresult.concretetype = resulttype
+            return vresult
+
+    def gendirectcall(self, ll_function, *args_v):
+        annotator = self.rtyper.annotator
+        spec_key = [ll_function]
+        spec_name = [ll_function.func_name]
+        args_s = []
+        for v in args_v:
+            s_value = annotator.binding(v, True)
+            if s_value is None:
+                s_value = annmodel.SomeObject()
+            if v.concretetype == Void:
+                if not s_value.is_constant():
+                    raise TyperError("non-constant variable of type Void")
+                key = s_value.const       # specialize by constant value
+                args_s.append(s_value)
+                suffix = 'Const'
+            else:
+                key = v.concretetype      # specialize by low-level type
+                args_s.append(annmodel.lltype_to_annotation(key))
+                suffix = ''
+            spec_key.append(key)
+            spec_name.append(valid_identifier(getattr(key, '__name__', key))
+                             + suffix)
+        spec_key = tuple(spec_key)
+        try:
+            spec_function = self.rtyper.specialized_ll_functions[spec_key]
+        except KeyError:
+            name = '_'.join(spec_name)
+            spec_function = func_with_new_name(ll_function, name)
+            # flow and annotate (the copy of) the low-level function
+            spec_graph = annotator.translator.getflowgraph(spec_function)
+            annotator.build_types(spec_function, args_s)
+            # cache the result
+            self.rtyper.specialized_ll_functions[spec_key] = spec_function
+
+        # build the 'direct_call' operation
+        f = self.rtyper.getfunctionptr(spec_function)
+        c = inputconst(typeOf(f), f)
+        return self.genop('direct_call', [c]+list(args_v),
+                          resulttype = typeOf(f).TO.RESULT)
+
 
 # _______________________________________________________________________
 # this has the side-effect of registering the unary and binary operations



More information about the Pypy-commit mailing list