[pypy-commit] pypy stm-thread-2: Kill these two files too.
arigo
noreply at buildbot.pypy.org
Mon Sep 3 19:45:07 CEST 2012
Author: Armin Rigo <arigo at tunes.org>
Branch: stm-thread-2
Changeset: r57099:e089fbd249d8
Date: 2012-09-03 16:16 +0200
http://bitbucket.org/pypy/pypy/changeset/e089fbd249d8/
Log: Kill these two files too.
diff --git a/pypy/translator/stm/gcsource.py b/pypy/translator/stm/gcsource.py
deleted file mode 100644
--- a/pypy/translator/stm/gcsource.py
+++ /dev/null
@@ -1,153 +0,0 @@
-from pypy.objspace.flow.model import Variable, Constant
-from pypy.rpython.lltypesystem import lltype, rclass
-from pypy.translator.simplify import get_graph
-
-
-COPIES_POINTER = set([
- 'force_cast', 'cast_pointer', 'same_as', 'cast_opaque_ptr',
- 'jit_force_virtual',
- # as well as most 'hint' operations, but not all --- see below
- ])
-
-
-def is_gc(var_or_const):
- TYPE = var_or_const.concretetype
- return isinstance(TYPE, lltype.Ptr) and TYPE.TO._gckind == 'gc'
-
-def enum_gc_dependencies(translator):
- """Enumerate pairs (var-or-const-or-op, var) that together describe
- the whole control flow of GC pointers in the program. If the source
- is a SpaceOperation, it means 'produced by this operation but we can't
- follow what this operation does'. The source is a string to describe
- special cases.
- """
- # Tracking dependencies of only GC pointers simplifies the logic here.
- # We don't have to worry about external calls and callbacks.
- # This works by assuming that each graph's calls are fully tracked
- # by the last argument to 'indirect_call'. Graphs for which we don't
- # find any call like this are assumed to be not called at all, e.g.
- # as a result of having been inlined everywhere.
- resultlist = []
- #
- def call(graph, args, result):
- inputargs = graph.getargs()
- assert len(args) == len(inputargs)
- for v1, v2 in zip(args, inputargs):
- ig = is_gc(v1)
- assert ig is is_gc(v2)
- if ig:
- resultlist.append((v1, v2))
- v = graph.getreturnvar()
- ig = is_gc(result)
- assert ig is is_gc(v)
- if ig:
- resultlist.append((v, result))
- #
- for graph in translator.graphs:
- for block in graph.iterblocks():
- for op in block.operations:
- #
- if (op.opname in COPIES_POINTER or
- (op.opname == 'hint' and
- 'stm_write' not in op.args[1].value)):
- if is_gc(op.result) and is_gc(op.args[0]):
- resultlist.append((op.args[0], op.result))
- continue
- #
- if op.opname == 'direct_call':
- tograph = get_graph(op.args[0], translator)
- if tograph is not None:
- call(tograph, op.args[1:], op.result)
- continue
- #
- if op.opname == 'indirect_call':
- # any GC argument or result?
- for v in op.args[:-1]:
- if is_gc(v):
- break
- else:
- if not is_gc(op.result):
- continue # no: ignore the indirect_call
- #
- tographs = op.args[-1].value
- if tographs is not None:
- for tograph in tographs:
- call(tograph, op.args[1:-1], op.result)
- continue
- # special-case to detect 'instantiate'
- is_instantiate = False
- v_func = op.args[0]
- for op1 in block.operations:
- if (v_func is op1.result and
- op1.opname == 'getfield' and
- op1.args[0].concretetype == rclass.CLASSTYPE and
- op1.args[1].value == 'instantiate'):
- is_instantiate = True
- break
- if is_instantiate:
- resultlist.append(('instantiate', op.result))
- continue
- #
- # unknwon targets, passing GC arguments or result:
- # check that there is already a stm_writebarrier
- # protecting all GC arguments. The stm_writebarrier
- # must be inserted manually. Only for jit.backend's
- # bh_call_x().
- writebarriers = set()
- for op1 in block.operations:
- if op1.opname == 'stm_writebarrier':
- writebarriers.add(op1.result)
- for v in op.args[1:-1]:
- if is_gc(v) and v not in writebarriers:
- raise Exception("%r: unknown targets, passing "
- "unprotected GC arguments" % (op,))
- # the result is listed in a normal dependency.
- #
- if is_gc(op.result):
- resultlist.append((op, op.result))
- #
- for link in block.exits:
- for v1, v2 in zip(link.args, link.target.inputargs):
- ig = is_gc(v2)
- assert ig is is_gc(v1)
- if ig:
- if v1 is link.last_exc_value:
- v1 = 'last_exc_value'
- resultlist.append((v1, v2))
- return resultlist
-
-
-class GcSource(object):
- """Works like a dict {gcptr-var: set-of-sources}. A source is a
- Constant, or a SpaceOperation that creates the value, or a string
- which describes a special case."""
-
- def __init__(self, translator):
- self.translator = translator
- self._backmapping = {}
- for v1, v2 in enum_gc_dependencies(translator):
- self._backmapping.setdefault(v2, []).append(v1)
-
- def __getitem__(self, variable):
- set_of_origins, set_of_variables = self._backpropagate(variable)
- return set_of_origins
-
- def backpropagate(self, variable):
- set_of_origins, set_of_variables = self._backpropagate(variable)
- return set_of_variables
-
- def _backpropagate(self, variable):
- if isinstance(variable, Constant):
- return set([variable]), set()
- result = set()
- pending = [variable]
- seen = set(pending)
- for v2 in pending:
- for v1 in self._backmapping.get(v2, ()):
- if isinstance(v1, Variable):
- if v1 not in seen:
- seen.add(v1)
- pending.append(v1)
- else:
- result.add(v1)
- return result, seen
diff --git a/pypy/translator/stm/localtracker.py b/pypy/translator/stm/localtracker.py
deleted file mode 100644
--- a/pypy/translator/stm/localtracker.py
+++ /dev/null
@@ -1,76 +0,0 @@
-from pypy.translator.stm.gcsource import GcSource
-from pypy.objspace.flow.model import Variable, Constant, SpaceOperation
-
-
-RETURNS_LOCAL_POINTER = set([
- 'malloc', 'malloc_varsize', 'malloc_nonmovable',
- 'malloc_nonmovable_varsize',
- 'stm_writebarrier',
- ])
-
-ENSURED_LOCAL_VARS = False # not needed for now
-
-
-class StmLocalTracker(object):
- """Tracker to determine which pointers are statically known to point
- to local objects. Here, 'local' versus 'global' is meant in the sense
- of the stmgc: a pointer is 'local' if it goes to the thread-local memory,
- and 'global' if it points to the shared read-only memory area."""
-
- def __init__(self, translator):
- self.translator = translator
- self.gsrc = GcSource(translator)
- # Set of variables on which we have called try_ensure_local()
- # and it returned True, or recursively the variables that
- # these variables depend on. It is the set of variables
- # holding a value that we really want to be local. It does
- # not contain the variables that happen to be local but whose
- # locality is not useful any more.
- if ENSURED_LOCAL_VARS:
- self.ensured_local_vars = set()
-
- def try_ensure_local(self, *variables):
- for variable in variables:
- if not self._could_be_local(variable):
- return False # one of the passed-in variables cannot be local
- #
- # they could all be locals, so flag them and their dependencies
- # and return True
- if ENSURED_LOCAL_VARS:
- for variable in variables:
- if (isinstance(variable, Variable) and
- variable not in self.ensured_local_vars):
- depends_on = self.gsrc.backpropagate(variable)
- self.ensured_local_vars.update(depends_on)
- return True
-
- def _could_be_local(self, variable):
- srcs = self.gsrc[variable]
- for src in srcs:
- if isinstance(src, SpaceOperation):
- if src.opname in RETURNS_LOCAL_POINTER:
- continue
- if src.opname == 'hint' and 'stm_write' in src.args[1].value:
- continue
- self.reason = src
- return False
- elif isinstance(src, Constant):
- if src.value: # a NULL pointer is still valid as local
- self.reason = src
- return False
- elif src == 'instantiate':
- pass
- elif isinstance(src, str):
- self.reason = src
- return False
- else:
- raise AssertionError(repr(src))
- return True
-
- def assert_local(self, variable, graph='?'):
- if self.try_ensure_local(variable):
- return # fine
- else:
- raise AssertionError(
- "assert_local() failed (%s, %s):\n%r" % (variable, graph,
- self.reason))
More information about the pypy-commit
mailing list