[pypy-svn] r15110 - in pypy/dist/pypy: interpreter objspace/std rpython translator/goal
hpk at codespeak.net
hpk at codespeak.net
Tue Jul 26 14:29:44 CEST 2005
Author: hpk
Date: Tue Jul 26 14:29:42 2005
New Revision: 15110
Added:
pypy/dist/pypy/rpython/error.py (contents, props changed)
Modified:
pypy/dist/pypy/interpreter/baseobjspace.py
pypy/dist/pypy/objspace/std/longobject.py
pypy/dist/pypy/rpython/rclass.py
pypy/dist/pypy/rpython/rconstantdict.py
pypy/dist/pypy/rpython/rdict.py
pypy/dist/pypy/rpython/rlist.py
pypy/dist/pypy/rpython/rmodel.py
pypy/dist/pypy/rpython/rpbc.py
pypy/dist/pypy/rpython/rtyper.py
pypy/dist/pypy/translator/goal/translate_pypy.py
Log:
(hpk,pedronis)
- making rtyping more robust by
- Repr's now have a more controled way of
initialization/setup phases
- more strictly tracking and flagging RTyper problems.
- factoring out the typer error printing to
dump_typererrors()
- "-fork" now checks that there are no random rpython
modules imported. Some related changes like
factoring out a 'pypy/rpython/error.py' module
so that 'rmodel.py' doesn't need to imported
at pre-fork time.
- longobject.py now doesn't have debugging on by default
because the annotator doesn't like that and we are
running translation from the trunk currently.
Modified: pypy/dist/pypy/interpreter/baseobjspace.py
==============================================================================
--- pypy/dist/pypy/interpreter/baseobjspace.py (original)
+++ pypy/dist/pypy/interpreter/baseobjspace.py Tue Jul 26 14:29:42 2005
@@ -197,8 +197,8 @@
return PythonCompiler(self)
elif self.options.compiler == 'cpython':
return CPythonCompiler(self)
- elif self.options.compiler == 'pyparseapp':
- return PythonCompilerApp(self)
+ #elif self.options.compiler == 'pyparseapp':
+ # return PythonCompilerApp(self)
else:
raise ValueError('unknown --compiler option value: %r' % (
self.options.compiler,))
Modified: pypy/dist/pypy/objspace/std/longobject.py
==============================================================================
--- pypy/dist/pypy/objspace/std/longobject.py (original)
+++ pypy/dist/pypy/objspace/std/longobject.py Tue Jul 26 14:29:42 2005
@@ -63,7 +63,7 @@
# False == no checking at all
# True == check 0 <= value <= MASK
-CHECK_DIGITS = True
+CHECK_DIGITS = False # True
if CHECK_DIGITS:
class DigitArray(list):
Added: pypy/dist/pypy/rpython/error.py
==============================================================================
--- (empty file)
+++ pypy/dist/pypy/rpython/error.py Tue Jul 26 14:29:42 2005
@@ -0,0 +1,10 @@
+
+class TyperError(Exception):
+ def __str__(self):
+ result = Exception.__str__(self)
+ if hasattr(self, 'where'):
+ result += '\n.. %r\n.. %r' % self.where
+ return result
+
+class MissingRTypeOperation(TyperError):
+ pass
Modified: pypy/dist/pypy/rpython/rclass.py
==============================================================================
--- pypy/dist/pypy/rpython/rclass.py (original)
+++ pypy/dist/pypy/rpython/rclass.py Tue Jul 26 14:29:42 2005
@@ -66,7 +66,7 @@
else:
result = ClassRepr(rtyper, classdef)
rtyper.class_reprs[classdef] = result
- rtyper.reprs_must_call_setup.append(result)
+ rtyper.add_pendingsetup(result)
return result
def getinstancerepr(rtyper, classdef):
@@ -79,7 +79,7 @@
else:
result = InstanceRepr(rtyper,classdef)
rtyper.instance_reprs[classdef] = result
- rtyper.reprs_must_call_setup.append(result)
+ rtyper.add_pendingsetup(result)
return result
class MissingRTypeAttribute(TyperError):
@@ -93,8 +93,6 @@
class ClassRepr(Repr):
- initialized = False
-
def __init__(self, rtyper, classdef):
self.rtyper = rtyper
self.classdef = classdef
@@ -112,11 +110,7 @@
cls = self.classdef.cls
return '<ClassRepr for %s.%s>' % (cls.__module__, cls.__name__)
- def setup(self):
- if self.initialized:
- assert self.initialized == True
- return
- self.initialized = "in progress"
+ def _setup_repr(self):
# NOTE: don't store mutable objects like the dicts below on 'self'
# before they are fully built, to avoid strange bugs in case
# of recursion where other code would uses these
@@ -158,7 +152,6 @@
self.pbcfields = pbcfields
self.allmethods = allmethods
self.vtable = None
- self.initialized = True
def prepare_method(self, name, s_value, allmethods):
# special-casing for methods:
@@ -345,8 +338,6 @@
class InstanceRepr(Repr):
- initialized = False
-
def __init__(self, rtyper, classdef):
self.rtyper = rtyper
self.classdef = classdef
@@ -364,11 +355,7 @@
cls = self.classdef.cls
return '<InstanceRepr for %s.%s>' % (cls.__module__, cls.__name__)
- def setup(self):
- if self.initialized:
- assert self.initialized == True
- return
- self.initialized = "in progress"
+ def _setup_repr(self):
# NOTE: don't store mutable objects like the dicts below on 'self'
# before they are fully built, to avoid strange bugs in case
# of recursion where other code would uses these
@@ -401,9 +388,8 @@
self.fields = fields
self.allinstancefields = allinstancefields
attachRuntimeTypeInfo(self.object_type)
- self.initialized = True
- def setup_final_touch(self):
+ def _setup_repr_final(self):
self.rtyper.attachRuntimeTypeInfoFunc(self.object_type,
ll_runtime_type_info,
OBJECT)
Modified: pypy/dist/pypy/rpython/rconstantdict.py
==============================================================================
--- pypy/dist/pypy/rpython/rconstantdict.py (original)
+++ pypy/dist/pypy/rpython/rconstantdict.py Tue Jul 26 14:29:42 2005
@@ -30,7 +30,7 @@
self.value_repr = value_repr
self.dict_cache = {}
- def setup(self):
+ def _setup_repr(self):
if isinstance(self.CONSTANTDICT, lltype.ForwardReference):
self.DICTKEY = self.key_repr.lowleveltype
self.DICTVALUE = self.value_repr.lowleveltype
Modified: pypy/dist/pypy/rpython/rdict.py
==============================================================================
--- pypy/dist/pypy/rpython/rdict.py (original)
+++ pypy/dist/pypy/rpython/rdict.py Tue Jul 26 14:29:42 2005
@@ -67,7 +67,7 @@
self.dict_cache = {}
# setup() needs to be called to finish this initialization
- def setup(self):
+ def _setup_repr(self):
if 'value_repr' not in self.__dict__:
self.value_repr = self._value_repr_computer()
if isinstance(self.STRDICT, lltype.GcForwardReference):
Modified: pypy/dist/pypy/rpython/rlist.py
==============================================================================
--- pypy/dist/pypy/rpython/rlist.py (original)
+++ pypy/dist/pypy/rpython/rlist.py Tue Jul 26 14:29:42 2005
@@ -57,7 +57,7 @@
self.list_cache = {}
# setup() needs to be called to finish this initialization
- def setup(self):
+ def _setup_repr(self):
if 'item_repr' not in self.__dict__:
self.item_repr = self._item_repr_computer()
if isinstance(self.LIST, GcForwardReference):
Modified: pypy/dist/pypy/rpython/rmodel.py
==============================================================================
--- pypy/dist/pypy/rpython/rmodel.py (original)
+++ pypy/dist/pypy/rpython/rmodel.py Tue Jul 26 14:29:42 2005
@@ -5,7 +5,15 @@
from pypy.rpython.lltype import typeOf, LowLevelType, Ptr, PyObject
from pypy.rpython.lltype import FuncType, functionptr
from pypy.tool.ansi_print import ansi_print
+from pypy.rpython.error import TyperError, MissingRTypeOperation
+# initialization states for Repr instances
+
+class setupstate:
+ NOTINITIALIZED = 0
+ INPROGRESS = 1
+ BROKEN = 2
+ FINISHED = 3
class Repr:
""" An instance of Repr is associated with each instance of SomeXxx.
@@ -16,27 +24,66 @@
iterating over.
"""
__metaclass__ = extendabletype
+ _initialized = setupstate.NOTINITIALIZED
def __repr__(self):
return '<%s %s>' % (self.__class__.__name__, self.lowleveltype)
- def setup(self):
+ def setup(self):
+ """ call _setup_repr() and keep track of the initializiation
+ status to e.g. detect recursive _setup_repr invocations.
+ the '_initialized' attr has four states:
+ """
+ if self._initialized == setupstate.FINISHED:
+ return
+ elif self._initialized == setupstate.BROKEN:
+ raise BrokenReprTyperError(
+ "cannot setup already failed Repr: %r" %(self,))
+ elif self._initialized == setupstate.INPROGRESS:
+ raise AssertionError(
+ "recursive invocation of Repr setup(): %r" %(self,))
+ assert self._initialized == setupstate.NOTINITIALIZED
+ self._initialized = setupstate.INPROGRESS
+ try:
+ self._setup_repr()
+ except TyperError, e:
+ self._initialized = setupstate.BROKEN
+ raise
+ else:
+ self._initialized = setupstate.FINISHED
+
+ def _setup_repr(self):
"For recursive data structure, which must be initialized in two steps."
- def setup_final_touch(self):
+ def setup_final(self):
"""Same as setup(), called a bit later, for effects that are only
needed after the typer finished (as opposed to needed for other parts
of the typer itself)."""
+ if self._initialized == setupstate.BROKEN:
+ raise BrokenReprTyperError("cannot perform setup_final_touch "
+ "on failed Repr: %r" %(self,))
+ assert self._initialized == setupstate.FINISHED, (
+ "setup_final() on repr with state %s: %r" %
+ (self._initialized, self))
+ self._setup_repr_final()
+
+ def _setup_repr_final(self):
+ pass
def __getattr__(self, name):
# Assume that when an attribute is missing, it's because setup() needs
# to be called
- self.setup()
- try:
- return self.__dict__[name]
- except KeyError:
- raise AttributeError("%s instance has no attribute %s" % (
- self.__class__.__name__, name))
+ if name[:2] != '__' or name[-2:] != '__':
+ if self._initialized != setupstate.NOTINITIALIZED:
+ warning("__getattr__ %r in strange state %r" %(name, self,))
+ else:
+ self.setup()
+ try:
+ return self.__dict__[name]
+ except KeyError:
+ pass
+ raise AttributeError("%s instance has no attribute %s" % (
+ self.__class__.__name__, name))
def _freeze_(self):
return True
@@ -148,15 +195,6 @@
# ____________________________________________________________
-class TyperError(Exception):
- def __str__(self):
- result = Exception.__str__(self)
- if hasattr(self, 'where'):
- result += '\n.. %r\n.. %r' % self.where
- return result
-
-class MissingRTypeOperation(TyperError):
- pass
def missing_rtype_operation(self, hop):
raise MissingRTypeOperation("unimplemented operation: '%s' on %r" % (
@@ -240,6 +278,11 @@
c.concretetype = lltype
return c
+class BrokenReprTyperError(TyperError):
+ """ raised when trying to setup a Repr whose setup
+ has failed already.
+ """
+
# __________ utilities __________
PyObjPtr = Ptr(PyObject)
Modified: pypy/dist/pypy/rpython/rpbc.py
==============================================================================
--- pypy/dist/pypy/rpython/rpbc.py (original)
+++ pypy/dist/pypy/rpython/rpbc.py Tue Jul 26 14:29:42 2005
@@ -127,7 +127,7 @@
except KeyError:
result = MultipleFrozenPBCRepr(rtyper, access)
rtyper.pbc_reprs[access] = result
- rtyper.reprs_must_call_setup.append(result)
+ rtyper.add_pendingsetup(result)
return result
@@ -183,8 +183,6 @@
class MultipleFrozenPBCRepr(Repr):
"""Representation selected for multiple non-callable pre-built constants."""
- initialized = False
-
def __init__(self, rtyper, access_set):
self.rtyper = rtyper
self.access_set = access_set
@@ -192,11 +190,7 @@
self.lowleveltype = Ptr(self.pbc_type)
self.pbc_cache = {}
- def setup(self):
- if self.initialized:
- assert self.initialized == True
- return
- self.initialized = "in progress"
+ def _setup_repr(self):
llfields = []
llfieldmap = {}
if self.access_set is not None:
@@ -210,7 +204,6 @@
llfieldmap[attr] = mangled_name, r_value
self.pbc_type.become(Struct('pbc', *llfields))
self.llfieldmap = llfieldmap
- self.initialized = True
def convert_const(self, pbc):
if pbc is None:
Modified: pypy/dist/pypy/rpython/rtyper.py
==============================================================================
--- pypy/dist/pypy/rpython/rtyper.py (original)
+++ pypy/dist/pypy/rpython/rtyper.py Tue Jul 26 14:29:42 2005
@@ -24,7 +24,9 @@
from pypy.rpython.lltype import attachRuntimeTypeInfo, Primitive
from pypy.tool.sourcetools import func_with_new_name, valid_identifier
from pypy.translator.unsimplify import insert_empty_block
-from pypy.rpython.rmodel import Repr, inputconst, TyperError, getfunctionptr
+from pypy.rpython.rmodel import Repr, inputconst
+from pypy.rpython.rmodel import TyperError, BrokenReprTyperError
+from pypy.rpython.rmodel import getfunctionptr, warning
from pypy.rpython.normalizecalls import perform_normalizations
from pypy.rpython.annlowlevel import annotate_lowlevel_helper
from pypy.rpython.exceptiondata import ExceptionData
@@ -38,7 +40,8 @@
def __init__(self, annotator):
self.annotator = annotator
self.reprs = {}
- self.reprs_must_call_setup = []
+ self._reprs_must_call_setup = []
+ self._seen_reprs_must_call_setup = {}
self.specialized_ll_functions = {}
self.class_reprs = {}
self.instance_reprs = {}
@@ -71,8 +74,14 @@
print '*' * len(s)
self.crash_on_first_typeerror = True
-
-
+ def add_pendingsetup(self, repr):
+ assert isinstance(repr, Repr)
+ if repr in self._seen_reprs_must_call_setup:
+ warning("ignoring already seen repr for setup: %r" %(repr,))
+ return
+ self._reprs_must_call_setup.append(repr)
+ self._seen_reprs_must_call_setup[repr] = True
+
def getexceptiondata(self):
return self.exceptiondata # built at the end of specialize()
@@ -88,7 +97,7 @@
"missing a Ptr in the type specification "
"of %s:\n%r" % (s_obj, result.lowleveltype))
self.reprs[key] = result
- self.reprs_must_call_setup.append(result)
+ self.add_pendingsetup(result)
return result
def binding(self, var):
@@ -153,35 +162,43 @@
# make sure all reprs so far have had their setup() called
self.call_all_setups()
- if self.typererrors:
- c = 1
- for err in self.typererrors:
- block, position = err.where
- func = self.annotator.annotated.get(block, None)
- if func:
- func = "(%s:%s)" %(func.__module__ or '?', func.__name__)
- else:
- func = "(?:?)"
- print "TyperError-%d: %s" % (c, func)
- print str(err)
- print ""
- c += 1
+ if self.typererrors:
+ self.dump_typererrors()
raise TyperError("there were %d error" % len(self.typererrors))
-
# make sure that the return variables of all graphs are concretetype'd
for graph in self.annotator.translator.flowgraphs.values():
v = graph.getreturnvar()
self.setconcretetype(v)
+ def dump_typererrors(self, num=None, minimize=True):
+ c = 0
+ bc = 0
+ for err in self.typererrors[:num]:
+ c += 1
+ if minimize and isinstance(err, BrokenReprTyperError):
+ bc += 1
+ continue
+ block, position = err.where
+ func = self.annotator.annotated.get(block, None)
+ if func:
+ func = "(%s:%s)" %(func.__module__ or '?', func.__name__)
+ else:
+ func = "(?:?)"
+ print "TyperError-%d: %s" % (c, func)
+ print str(err)
+ print ""
+ if bc:
+ print "(minimized %d errors away for this dump)" % (bc,)
+
def call_all_setups(self):
# make sure all reprs so far have had their setup() called
must_setup_more = []
- while self.reprs_must_call_setup:
- r = self.reprs_must_call_setup.pop()
+ while self._reprs_must_call_setup:
+ r = self._reprs_must_call_setup.pop()
r.setup()
must_setup_more.append(r)
for r in must_setup_more:
- r.setup_final_touch()
+ r.setup_final()
def setconcretetype(self, v):
assert isinstance(v, Variable)
Modified: pypy/dist/pypy/translator/goal/translate_pypy.py
==============================================================================
--- pypy/dist/pypy/translator/goal/translate_pypy.py (original)
+++ pypy/dist/pypy/translator/goal/translate_pypy.py Tue Jul 26 14:29:42 2005
@@ -76,7 +76,7 @@
from pypy.tool.ansi_print import ansi_print
from pypy.translator.pickle.main import load, save
# catch TyperError to allow for post-mortem dump
-from pypy.rpython.rmodel import TyperError
+from pypy.rpython.error import TyperError
# XXX this tries to make compiling faster
from pypy.translator.tool import buildpyxmodule
@@ -112,6 +112,7 @@
a.simplify()
if a and options['-fork']:
from pypy.translator.goal import unixcheckpoint
+ assert_rpython_mostly_not_imported()
unixcheckpoint.restartable_point(auto='run')
if a and not options['-no-t']:
print 'Specializing...'
@@ -123,6 +124,19 @@
if a:
t.frozen = True # cannot freeze if we don't have annotations
+def assert_rpython_mostly_not_imported():
+ prefix = 'pypy.rpython.'
+ oknames = 'rarithmetic extfunctable lltype objectmodel error'.split()
+ wrongimports = []
+ for name, module in sys.modules.items():
+ if module is not None and name.startswith(prefix):
+ sname = name[len(prefix):]
+ if sname not in oknames:
+ wrongimports.append(name)
+ if wrongimports:
+ raise RuntimeError("cannot fork because improper rtyper code"
+ " has already been imported: %r" %(wrongimports,))
+
def sanity_check_exceptblocks(translator):
annotator = translator.annotator
irreg = 0
More information about the Pypy-commit
mailing list