[pypy-svn] r51355 - in pypy/dist/pypy: jit/codegen/cli jit/codegen/cli/test translator/cli translator/cli/src
antocuni at codespeak.net
antocuni at codespeak.net
Sat Feb 9 15:15:19 CET 2008
Author: antocuni
Date: Sat Feb 9 15:15:17 2008
New Revision: 51355
Modified:
pypy/dist/pypy/jit/codegen/cli/operation.py
pypy/dist/pypy/jit/codegen/cli/rgenop.py
pypy/dist/pypy/jit/codegen/cli/test/test_rgenop.py
pypy/dist/pypy/translator/cli/dotnet.py
pypy/dist/pypy/translator/cli/src/pypylib.cs
Log:
- first tentative to add support for GenConsts that contain objects;
each of those is stored in a static field, but for now only a fixed
number of those is available;
- improve the automatic generation of Operations from the descriptions in cli/opcodes.py
- as a result, some more tests pass :-)
Modified: pypy/dist/pypy/jit/codegen/cli/operation.py
==============================================================================
--- pypy/dist/pypy/jit/codegen/cli/operation.py (original)
+++ pypy/dist/pypy/jit/codegen/cli/operation.py Sat Feb 9 15:15:17 2008
@@ -65,7 +65,37 @@
self.gv_res().store(self.il)
+class Call(Operation):
+
+ def __init__(self, il, sigtoken, gv_fnptr, args_gv):
+ from pypy.jit.codegen.cli.rgenop import token2clitype
+ self.il = il
+ self.sigtoken = sigtoken
+ self.gv_fnptr = gv_fnptr
+ self.args_gv = args_gv
+ self._restype = token2clitype(sigtoken[1])
+
+ def restype(self):
+ return self._restype
+
+ def emit(self):
+ from pypy.jit.codegen.cli.rgenop import sigtoken2clitype
+ delegate_type = sigtoken2clitype(self.sigtoken)
+ meth_invoke = delegate_type.GetMethod('Invoke')
+ self.gv_fnptr.load(self.il)
+ self.il.Emit(OpCodes.Castclass, delegate_type)
+ for gv_arg in self.args_gv:
+ gv_arg.load(self.il)
+ self.il.EmitCall(OpCodes.Callvirt, meth_invoke, None)
+ self.storeResult()
+
+
+
def opcode2attrname(opcode):
+ if opcode == 'ldc.r8 0':
+ return 'Ldc_R8, 0' # XXX this is a hack
+ if opcode == 'ldc.i8 0':
+ return 'Ldc_I8, 0' # XXX this is a hack
parts = map(str.capitalize, opcode.split('.'))
return '_'.join(parts)
@@ -97,9 +127,37 @@
elif value is cli_opcodes.DoNothing:
out[opname] = SameAs
else:
- pass # XXX: handle remaining ops
+ renderCustomOp(opname, baseclass, value, out)
return out
+def renderCustomOp(opname, baseclass, steps, out):
+ assert steps
+ body = []
+ for step in steps:
+ if step is cli_opcodes.PushAllArgs:
+ body.append('self.pushAllArgs()')
+ elif step is cli_opcodes.StoreResult:
+ body.append('self.storeResult()')
+ elif isinstance(step, str):
+ if 'call' in step:
+ return # XXX, fix this
+ attrname = opcode2attrname(step)
+ body.append('self.il.Emit(OpCodes.%s)' % attrname)
+ elif isinstance(step, cli_opcodes.MapException):
+ return # XXX, TODO
+ else:
+ return # ignore it for now
+
+ if cli_opcodes.StoreResult not in steps:
+ body.append('self.storeResult()')
+
+ emit = py.code.Source('\n'.join(body))
+ emit = emit.putaround('def emit(self):')
+ source = emit.putaround('class %(opname)s (%(baseclass)s):' % locals())
+ code = source.compile()
+ exec code in globals(), out
+
+
UNARYOPS = fillops(cli_opcodes.unary_ops, "UnaryOp")
BINARYOPS = fillops(cli_opcodes.binary_ops, "BinaryOp")
Modified: pypy/dist/pypy/jit/codegen/cli/rgenop.py
==============================================================================
--- pypy/dist/pypy/jit/codegen/cli/rgenop.py (original)
+++ pypy/dist/pypy/jit/codegen/cli/rgenop.py Sat Feb 9 15:15:17 2008
@@ -7,6 +7,7 @@
from pypy.translator.cli.dotnet import CLR, typeof, new_array, clidowncast
System = CLR.System
Utils = CLR.pypy.runtime.Utils
+Constants = CLR.pypy.runtime.Constants
OpCodes = System.Reflection.Emit.OpCodes
def token2clitype(tok):
@@ -96,30 +97,51 @@
def __repr__(self):
return "const=%s" % self.value
-SM_INT__INT = ootype.StaticMethod([ootype.Signed], ootype.Signed)
-SM_INT__INT_INT = ootype.StaticMethod([ootype.Signed, ootype.Signed], ootype.Signed)
-SM_INT__INT_100 = ootype.StaticMethod([ootype.Signed] * 100, ootype.Signed)
+class BaseConst(GenConst):
+ def __init__(self, num):
+ self.num = num
+ self.fieldname = "const" + str(num)
+
+ def getobj(self):
+ t = typeof(Constants)
+ return t.GetField(self.fieldname).GetValue(None)
+
+ def setobj(self, obj):
+ t = typeof(Constants)
+ t.GetField(self.fieldname).SetValue(None, obj)
-class ObjectConst(GenConst):
+ def load(self, il):
+ t = typeof(Constants)
+ field = t.GetField(self.fieldname)
+ il.Emit(OpCodes.Ldsfld, field)
- def __init__(self, obj):
- self.obj = obj
+SM_INT__INT = ootype.StaticMethod([ootype.Signed], ootype.Signed)
+SM_INT__INT_INT = ootype.StaticMethod([ootype.Signed, ootype.Signed], ootype.Signed)
+SM_INT__INT_100 = ootype.StaticMethod([ootype.Signed] * 100, ootype.Signed)
+class FunctionConst(BaseConst):
+
@specialize.arg(1)
def revealconst(self, T):
- # XXX: probably you can't mix StaticMethod and others OOTypes
if T == SM_INT__INT:
DelegateType = CLR.pypy.runtime.DelegateType_int__int
- return clidowncast(DelegateType, self.obj)
+ return clidowncast(DelegateType, self.getobj())
elif T == SM_INT__INT_INT:
DelegateType = CLR.pypy.runtime.DelegateType_int__int_int
- return clidowncast(DelegateType, self.obj)
+ return clidowncast(DelegateType, self.getobj())
elif T == SM_INT__INT_100:
DelegateType = CLR.pypy.runtime.DelegateType_int__int_100
- return clidowncast(DelegateType, self.obj)
+ return clidowncast(DelegateType, self.getobj())
else:
- assert isinstance(T, ootype.OOType)
- return ootype.oodowncast(T, self.obj)
+ assert False
+
+class ObjectConst(BaseConst):
+
+ @specialize.arg(1)
+ def revealconst(self, T):
+ assert isinstance(T, ootype.OOType)
+ return ootype.oodowncast(T, self.obj)
+
class Label(GenLabel):
def __init__(self, label, inputargs_gv):
@@ -132,6 +154,13 @@
def __init__(self):
self.meth = None
self.il = None
+ self.constcount = 0
+
+ def newconst(self, cls):
+ assert self.constcount < 3 # the number of static fields declared in Constants
+ res = cls(self.constcount)
+ self.constcount += 1
+ return res
@specialize.genconst(1)
def genconst(self, llvalue):
@@ -139,7 +168,9 @@
if T is ootype.Signed:
return IntConst(llvalue)
elif isinstance(T, ootype.OOType):
- return ObjectConst(llvalue)
+ const = self.newconst(ObjectConst)
+ const.setobj(llvalue)
+ return const
else:
assert False, "XXX not implemented"
@@ -178,10 +209,17 @@
self.inputargs_gv = []
for i in range(len(args)):
self.inputargs_gv.append(GenArgVar(i, args[i]))
- self.gv_entrypoint = ObjectConst(None) # XXX?
+ self.gv_entrypoint = self.rgenop.newconst(FunctionConst)
self.sigtoken = sigtoken
self.isOpen = False
-
+
+ @specialize.arg(1)
+ def genop1(self, opname, gv_arg):
+ opcls = ops.getopclass1(opname)
+ op = opcls(self.il, gv_arg)
+ self.emit(op)
+ return op.gv_res()
+
@specialize.arg(1)
def genop2(self, opname, gv_arg1, gv_arg2):
opcls = ops.getopclass2(opname)
@@ -189,6 +227,11 @@
self.emit(op)
return op.gv_res()
+ def genop_call(self, sigtoken, gv_fnptr, args_gv):
+ op = ops.Call(self.il, sigtoken, gv_fnptr, args_gv)
+ self.emit(op)
+ return op.gv_res()
+
def emit(self, op):
op.emit()
@@ -212,7 +255,7 @@
def end(self):
delegate_type = sigtoken2clitype(self.sigtoken)
myfunc = self.meth.CreateDelegate(delegate_type)
- self.gv_entrypoint.obj = myfunc
+ self.gv_entrypoint.setobj(myfunc)
def enter_next_block(self, kinds, args_gv):
for i in range(len(args_gv)):
Modified: pypy/dist/pypy/jit/codegen/cli/test/test_rgenop.py
==============================================================================
--- pypy/dist/pypy/jit/codegen/cli/test/test_rgenop.py (original)
+++ pypy/dist/pypy/jit/codegen/cli/test/test_rgenop.py Sat Feb 9 15:15:17 2008
@@ -10,10 +10,13 @@
'test_adder',
'test_dummy',
'test_hide_and_reveal',
- 'test_hide_and_reveal_p',
+ # 'test_hide_and_reveal_p', # think about this
'test_largedummy_direct', # _compile works if we set a higher maxstack
'test_branching',
'test_goto',
+ 'test_if',
+ # 'test_switch', # no promotion/flexswitch for now please :-)
+ 'test_fact',
]
for p in prefixes:
@@ -38,7 +41,7 @@
def cast(self, gv, nb_args):
"NOT_RPYTHON"
def fn(*args):
- return gv.obj.Invoke(*args)
+ return gv.getobj().Invoke(*args)
return fn
def directtesthelper(self, FUNCTYPE, func):
Modified: pypy/dist/pypy/translator/cli/dotnet.py
==============================================================================
--- pypy/dist/pypy/translator/cli/dotnet.py (original)
+++ pypy/dist/pypy/translator/cli/dotnet.py Sat Feb 9 15:15:17 2008
@@ -306,7 +306,7 @@
self._load_class()
return getattr(self._PythonNet_class, attr)
else:
- raise AttributeError
+ raise AttributeError, attr
def __call__(self, *args):
self._load_class()
Modified: pypy/dist/pypy/translator/cli/src/pypylib.cs
==============================================================================
--- pypy/dist/pypy/translator/cli/src/pypylib.cs (original)
+++ pypy/dist/pypy/translator/cli/src/pypylib.cs Sat Feb 9 15:15:17 2008
@@ -59,6 +59,7 @@
public class Constants
{
+ public static object const0;
public static object const1;
public static object const2;
}
More information about the Pypy-commit
mailing list