[pypy-svn] r65029 - pypy/branch/pyjitpl5/pypy/jit/backend/cli
antocuni at codespeak.net
antocuni at codespeak.net
Mon May 4 18:40:50 CEST 2009
Author: antocuni
Date: Mon May 4 18:40:49 2009
New Revision: 65029
Modified:
pypy/branch/pyjitpl5/pypy/jit/backend/cli/method.py
Log:
add the possibility to catch more than one exception for raising ops. This is
needed by int_mod_ovf, which can raises both ArithmeticException and
OverflowException. The corresponding bit of test_raising_ops passes (but the
last bit still fails)
Modified: pypy/branch/pyjitpl5/pypy/jit/backend/cli/method.py
==============================================================================
--- pypy/branch/pyjitpl5/pypy/jit/backend/cli/method.py (original)
+++ pypy/branch/pyjitpl5/pypy/jit/backend/cli/method.py Mon May 4 18:40:49 2009
@@ -200,17 +200,18 @@
self.il.Emit(OpCodes.Ldnull)
self.il.Emit(OpCodes.Stfld, self.exc_value_field)
- def emit_raising_op(self, op, emit_op, exctype):
- v = self.il.DeclareLocal(exctype)
+ def emit_raising_op(self, op, emit_op, exctypes):
self.emit_clear_exception()
lbl = self.il.BeginExceptionBlock()
emit_op(self, op)
self.il.Emit(OpCodes.Leave, lbl)
- self.il.BeginCatchBlock(exctype)
- self.il.Emit(OpCodes.Stloc, v)
- self.av_inputargs.load(self)
- self.il.Emit(OpCodes.Ldloc, v)
- self.il.Emit(OpCodes.Stfld, self.exc_value_field)
+ for exctype in exctypes:
+ v = self.il.DeclareLocal(exctype)
+ self.il.BeginCatchBlock(exctype)
+ self.il.Emit(OpCodes.Stloc, v)
+ self.av_inputargs.load(self)
+ self.il.Emit(OpCodes.Ldloc, v)
+ self.il.Emit(OpCodes.Stfld, self.exc_value_field)
self.il.EndExceptionBlock()
# --------------------------------
@@ -290,12 +291,15 @@
func = getattr(Method, methname).im_func
else:
instrlist = opcodes.opcodes[key]
- func = render_op(methname, instrlist)
+ func = render_op(methname, instrlist, False)
operations[value] = func
return operations
+def is_raising_op(instrlist):
+ return len(instrlist) == 1 and isinstance(instrlist[0], opcodes.MapException)
+
def render_op(methname, instrlist):
- if len(instrlist) == 1 and isinstance(instrlist[0], opcodes.MapException):
+ if is_raising_op(instrlist):
return render_raising_op(methname, instrlist)
lines = []
for instr in instrlist:
@@ -322,21 +326,23 @@
exec src.compile() in dic
return dic[methname]
+def parse_exctype(exctype):
+ assert exctype.startswith('[mscorlib]')
+ return exctype[len('[mscorlib]'):]
+
+
def render_raising_op(methname, instrlist):
value = instrlist[0]
- mapping = value.mapping
- assert len(mapping) == 1, 'Catching more than one exception is not supported'
- exctype = mapping[0][0]
- assert exctype.startswith('[mscorlib]')
- exctype = exctype[len('[mscorlib]'):]
+ exctypes = [parse_exctype(exctype) for exctype, _ in value.mapping]
+ exctypes = ['dotnet.typeof(%s)' % exctype for exctype in exctypes]
impl_func = render_op(methname + '_impl', value.instr)
if not impl_func:
return
src = py.code.Source("""
def %s(self, op):
- exctype = dotnet.typeof(%s)
- self.emit_raising_op(op, impl_func, exctype)
- """ % (methname, exctype))
+ exctypes = [%s]
+ self.emit_raising_op(op, impl_func, exctypes)
+ """ % (methname, ', '.join(exctypes)))
dic = {'System': System,
'dotnet': dotnet,
'impl_func': impl_func}
More information about the Pypy-commit
mailing list