Author: Carl Friedrich Bolz <[email protected]>
Branch: dict-strategies
Changeset: r44495:49ef09de8987
Date: 2011-05-26 13:36 +0200
http://bitbucket.org/pypy/pypy/changeset/49ef09de8987/

Log:    kill CALL_LIKELY_BUILTIN, it was not really worth the hassle any
        more.

diff --git a/pypy/config/pypyoption.py b/pypy/config/pypyoption.py
--- a/pypy/config/pypyoption.py
+++ b/pypy/config/pypyoption.py
@@ -124,9 +124,6 @@
                  cmdline='--objspace -o'),
 
     OptionDescription("opcodes", "opcodes to enable in the interpreter", [
-        BoolOption("CALL_LIKELY_BUILTIN", "emit a special bytecode for likely 
calls to builtin functions",
-                   default=False,
-                   requires=[("translation.stackless", False)]),
         BoolOption("CALL_METHOD", "emit a special bytecode for expr.name()",
                    default=False),
         ]),
@@ -261,8 +258,7 @@
         BoolOption("withcelldict",
                    "use dictionaries that are optimized for being used as 
module dicts",
                    default=False,
-                   requires=[("objspace.opcodes.CALL_LIKELY_BUILTIN", False),
-                             ("objspace.honor__builtins__", False)]),
+                   requires=[("objspace.honor__builtins__", False)]),
 
         BoolOption("withmapdict",
                    "make instances really small but slow without the JIT",
@@ -345,8 +341,6 @@
     backend = config.translation.backend
 
     # all the good optimizations for PyPy should be listed here
-    if level in ['2', '3']:
-        config.objspace.opcodes.suggest(CALL_LIKELY_BUILTIN=True)
     if level in ['2', '3', 'jit']:
         config.objspace.opcodes.suggest(CALL_METHOD=True)
         config.objspace.std.suggest(withrangelist=True)
diff --git a/pypy/doc/config/objspace.opcodes.CALL_LIKELY_BUILTIN.txt 
b/pypy/doc/config/objspace.opcodes.CALL_LIKELY_BUILTIN.txt
deleted file mode 100644
--- a/pypy/doc/config/objspace.opcodes.CALL_LIKELY_BUILTIN.txt
+++ /dev/null
@@ -1,12 +0,0 @@
-Introduce a new opcode called ``CALL_LIKELY_BUILTIN``. It is used when 
something
-is called, that looks like a builtin function (but could in reality be shadowed
-by a name in the module globals). For all module globals dictionaries it is
-then tracked which builtin name is shadowed in this module. If the
-``CALL_LIKELY_BUILTIN`` opcode is executed, it is checked whether the builtin 
is
-shadowed. If not, the corresponding builtin is called. Otherwise the object 
that
-is shadowing it is called instead. If no shadowing is happening, this saves two
-dictionary lookups on calls to builtins.
-
-For more information, see the section in `Standard Interpreter Optimizations`_.
-
-.. _`Standard Interpreter Optimizations`: 
../interpreter-optimizations.html#call-likely-builtin
diff --git a/pypy/interpreter/astcompiler/assemble.py 
b/pypy/interpreter/astcompiler/assemble.py
--- a/pypy/interpreter/astcompiler/assemble.py
+++ b/pypy/interpreter/astcompiler/assemble.py
@@ -655,9 +655,6 @@
 def _compute_CALL_FUNCTION_VAR_KW(arg):
     return -_num_args(arg) - 2
 
-def _compute_CALL_LIKELY_BUILTIN(arg):
-    return -(arg & 0xFF) + 1
-
 def _compute_CALL_METHOD(arg):
     return -_num_args(arg) - 1
 
diff --git a/pypy/interpreter/astcompiler/codegen.py 
b/pypy/interpreter/astcompiler/codegen.py
--- a/pypy/interpreter/astcompiler/codegen.py
+++ b/pypy/interpreter/astcompiler/codegen.py
@@ -12,7 +12,6 @@
 from pypy.interpreter.pyparser.error import SyntaxError
 from pypy.tool import stdlib_opcode as ops
 from pypy.interpreter.error import OperationError
-from pypy.module.__builtin__.__init__ import BUILTIN_TO_INDEX
 
 
 def compile_ast(space, module, info):
@@ -942,8 +941,7 @@
 
     def visit_Call(self, call):
         self.update_position(call.lineno)
-        if self._optimize_builtin_call(call) or \
-                self._optimize_method_call(call):
+        if self._optimize_method_call(call):
             return
         call.func.walkabout(self)
         arg = 0
@@ -977,28 +975,6 @@
     def _call_has_simple_args(self, call):
         return self._call_has_no_star_args(call) and not call.keywords
 
-    def _optimize_builtin_call(self, call):
-        if not self.space.config.objspace.opcodes.CALL_LIKELY_BUILTIN or \
-                not self._call_has_simple_args(call) or \
-                not isinstance(call.func, ast.Name):
-            return False
-        func_name = call.func
-        assert isinstance(func_name, ast.Name)
-        name_scope = self.scope.lookup(func_name.id)
-        if name_scope == symtable.SCOPE_GLOBAL_IMPLICIT or \
-                name_scope == symtable.SCOPE_UNKNOWN:
-            builtin_index = BUILTIN_TO_INDEX.get(func_name.id, -1)
-            if builtin_index != -1:
-                if call.args:
-                    args_count = len(call.args)
-                    self.visit_sequence(call.args)
-                else:
-                    args_count = 0
-                arg = builtin_index << 8 | args_count
-                self.emit_op_arg(ops.CALL_LIKELY_BUILTIN, arg)
-                return True
-        return False
-
     def _optimize_method_call(self, call):
         if not self.space.config.objspace.opcodes.CALL_METHOD or \
                 not self._call_has_no_star_args(call) or \
diff --git a/pypy/interpreter/pyopcode.py b/pypy/interpreter/pyopcode.py
--- a/pypy/interpreter/pyopcode.py
+++ b/pypy/interpreter/pyopcode.py
@@ -1070,18 +1070,6 @@
     def SET_LINENO(self, lineno, next_instr):
         pass
 
-    def CALL_LIKELY_BUILTIN(self, oparg, next_instr):
-        # overridden by faster version in the standard object space.
-        from pypy.module.__builtin__ import OPTIMIZED_BUILTINS
-        varname = OPTIMIZED_BUILTINS[oparg >> 8]
-        w_function = self._load_global(varname)
-        nargs = oparg&0xFF
-        try:
-            w_result = self.space.call_valuestack(w_function, nargs, self)
-        finally:
-            self.dropvalues(nargs)
-        self.pushvalue(w_result)
-
     # overridden by faster version in the standard object space.
     LOOKUP_METHOD = LOAD_ATTR
     CALL_METHOD = CALL_FUNCTION
diff --git a/pypy/interpreter/test/test_executioncontext.py 
b/pypy/interpreter/test/test_executioncontext.py
--- a/pypy/interpreter/test/test_executioncontext.py
+++ b/pypy/interpreter/test/test_executioncontext.py
@@ -232,31 +232,6 @@
         assert [i[0] for i in events] == ['c_call', 'c_return', 'return', 
'c_call']
         assert events[0][1] == events[1][1]
 
-    def test_tracing_range_builtinshortcut(self):
-        opts = {"objspace.opcodes.CALL_LIKELY_BUILTIN": True}
-        space = gettestobjspace(**opts)
-        source = """def f(profile):
-        import sys
-        sys.setprofile(profile)
-        range(10)
-        sys.setprofile(None)
-        """
-        w_events = space.appexec([space.wrap(source)], """(source):
-        import sys
-        l = []
-        def profile(frame, event, arg):
-            l.append((event, arg))
-        d = {}
-        exec source in d
-        f = d['f']
-        f(profile)
-        import dis
-        print dis.dis(f)
-        return l
-        """)
-        events = space.unwrap(w_events)
-        assert [i[0] for i in events] == ['c_call', 'c_return', 'c_call']
-
     def test_profile_and_exception(self):
         space = self.space
         w_res = space.appexec([], """():
@@ -280,9 +255,6 @@
         """)
 
 
-class TestExecutionContextWithCallLikelyBuiltin(TestExecutionContext):
-    keywords = {'objspace.opcodes.CALL_LIKELY_BUILTIN': True}
-
 class TestExecutionContextWithCallMethod(TestExecutionContext):
     keywords = {'objspace.opcodes.CALL_METHOD': True}
 
diff --git a/pypy/module/__builtin__/__init__.py 
b/pypy/module/__builtin__/__init__.py
--- a/pypy/module/__builtin__/__init__.py
+++ b/pypy/module/__builtin__/__init__.py
@@ -5,20 +5,6 @@
 
 # put builtins here that should be optimized somehow
 
-OPTIMIZED_BUILTINS = ["len", "range", "xrange", "min", "max", "enumerate",
-        "isinstance", "type", "zip", "file", "format", "open", "abs", "chr",
-        "unichr", "ord", "pow", "repr", "hash", "oct", "hex", "round", "cmp",
-        "getattr", "setattr", "delattr", "callable", "int", "str", "float"]
-
-assert len(OPTIMIZED_BUILTINS) <= 256
-
-BUILTIN_TO_INDEX = {}
-
-for i, name in enumerate(OPTIMIZED_BUILTINS):
-    BUILTIN_TO_INDEX[name] = i
-
-assert len(OPTIMIZED_BUILTINS) == len(BUILTIN_TO_INDEX)
-
 class Module(MixedModule):
     """Built-in functions, exceptions, and other objects."""
     expose__file__attribute = False
@@ -141,9 +127,6 @@
     def setup_after_space_initialization(self):
         """NOT_RPYTHON"""
         space = self.space
-        self.builtins_by_index = [None] * len(OPTIMIZED_BUILTINS)
-        for i, name in enumerate(OPTIMIZED_BUILTINS):
-            self.builtins_by_index[i] = space.getattr(self, space.wrap(name))
         # install the more general version of isinstance() & co. in the space
         from pypy.module.__builtin__ import abstractinst as ab
         space.abstract_isinstance_w = ab.abstract_isinstance_w.__get__(space)
diff --git a/pypy/module/__builtin__/test/test_builtin.py 
b/pypy/module/__builtin__/test/test_builtin.py
--- a/pypy/module/__builtin__/test/test_builtin.py
+++ b/pypy/module/__builtin__/test/test_builtin.py
@@ -619,62 +619,6 @@
         raises(TypeError, pr, end=3)
         raises(TypeError, pr, sep=42)
 
-class AppTestBuiltinOptimized(object):
-    def setup_class(cls):
-        from pypy.conftest import gettestobjspace
-        cls.space = gettestobjspace(**{"objspace.opcodes.CALL_LIKELY_BUILTIN": 
True})
-
-    # hum, we need to invoke the compiler explicitely
-    def test_xrange_len(self):
-        s = """def test():
-        x = xrange(33)
-        assert len(x) == 33
-        x = xrange(33.2)
-        assert len(x) == 33
-        x = xrange(33,0,-1)
-        assert len(x) == 33
-        x = xrange(33,0)
-        assert len(x) == 0
-        x = xrange(33,0.2)
-        assert len(x) == 0
-        x = xrange(0,33)
-        assert len(x) == 33
-        x = xrange(0,33,-1)
-        assert len(x) == 0
-        x = xrange(0,33,2)
-        assert len(x) == 17
-        x = xrange(0,32,2)
-        assert len(x) == 16
-        """
-        ns = {}
-        exec s in ns
-        ns["test"]()
-
-    def test_delete_from_builtins(self):
-        s = """ """
-        # XXX write this test!
-
-    def test_shadow_case_bound_method(self):
-        s = """def test(l):
-        n = len(l)
-        old_len = len
-        class A(object):
-            x = 5
-            def length(self, o):
-                return self.x*old_len(o)
-        import __builtin__
-        __builtin__.len = A().length
-        try:
-            m = len(l)
-        finally:
-            __builtin__.len = old_len
-        return n+m
-        """
-        ns = {}
-        exec s in ns
-        res = ns["test"]([2,3,4])
-        assert res == 18
-
     def test_round(self):
         assert round(11.234) == 11.0
         assert round(11.234, -1) == 10.0
diff --git a/pypy/module/__builtin__/test/test_classobj.py 
b/pypy/module/__builtin__/test/test_classobj.py
--- a/pypy/module/__builtin__/test/test_classobj.py
+++ b/pypy/module/__builtin__/test/test_classobj.py
@@ -987,9 +987,9 @@
         if option.runappdirect:
             py.test.skip("can only be run on py.py")
         def is_strdict(space, w_class):
-            from pypy.objspace.std.dictmultiobject import StrDictImplementation
+            from pypy.objspace.std.dictmultiobject import StringDictStrategy
             w_d = w_class.getdict(space)
-            return space.wrap(isinstance(w_d, StrDictImplementation) and 
w_d.r_dict_content is None)
+            return space.wrap(isinstance(w_d.strategy, StringDictStrategy))
 
         cls.w_is_strdict = cls.space.wrap(gateway.interp2app(is_strdict))
 
diff --git a/pypy/module/_lsprof/test/test_cprofile.py 
b/pypy/module/_lsprof/test/test_cprofile.py
--- a/pypy/module/_lsprof/test/test_cprofile.py
+++ b/pypy/module/_lsprof/test/test_cprofile.py
@@ -181,8 +181,7 @@
 
 
 class AppTestWithDifferentBytecodes(AppTestCProfile):
-    keywords = {'objspace.opcodes.CALL_LIKELY_BUILTIN': True,
-                'objspace.opcodes.CALL_METHOD': True}
+    keywords = {'objspace.opcodes.CALL_METHOD': True}
 
 
 expected_output = {}
diff --git a/pypy/module/imp/importing.py b/pypy/module/imp/importing.py
--- a/pypy/module/imp/importing.py
+++ b/pypy/module/imp/importing.py
@@ -793,14 +793,13 @@
 
 """
 
-# XXX picking a magic number is a mess.  So far it works because we
-# have only two extra opcodes, which bump the magic number by +1 and
-# +2 respectively, and CPython leaves a gap of 10 when it increases
+# picking a magic number is a mess.  So far it works because we
+# have only one extra opcode, which bumps the magic number by +2, and CPython
+# leaves a gap of 10 when it increases
 # its own magic number.  To avoid assigning exactly the same numbers
 # as CPython we always add a +2.  We'll have to think again when we
-# get at the fourth new opcode :-(
+# get three more new opcodes
 #
-#  * CALL_LIKELY_BUILTIN    +1
 #  * CALL_METHOD            +2
 #
 # In other words:
@@ -823,8 +822,6 @@
             return struct.unpack('<i', magic)[0]
 
     result = default_magic
-    if space.config.objspace.opcodes.CALL_LIKELY_BUILTIN:
-        result += 1
     if space.config.objspace.opcodes.CALL_METHOD:
         result += 2
     return result
diff --git a/pypy/objspace/std/dictmultiobject.py 
b/pypy/objspace/std/dictmultiobject.py
--- a/pypy/objspace/std/dictmultiobject.py
+++ b/pypy/objspace/std/dictmultiobject.py
@@ -4,7 +4,6 @@
 from pypy.interpreter import gateway
 from pypy.interpreter.argument import Signature
 from pypy.interpreter.error import OperationError, operationerrfmt
-from pypy.module.__builtin__.__init__ import BUILTIN_TO_INDEX, 
OPTIMIZED_BUILTINS
 
 from pypy.rlib.objectmodel import r_dict, we_are_translated
 from pypy.objspace.std.settype import set_typedef as settypedef
@@ -40,11 +39,6 @@
             assert w_type is None
             strategy = space.fromcache(ModuleDictStrategy)
 
-        elif space.config.objspace.opcodes.CALL_LIKELY_BUILTIN and module:
-            assert w_type is None
-            # create new Strategy everytime, because each must have its own 
shadow-attribute
-            strategy = WaryDictStrategy(space)
-
         elif instance or strdict or module:
             assert w_type is None
             strategy = space.fromcache(StringDictStrategy)
@@ -94,7 +88,7 @@
                     getitem_str delitem length \
                     clear keys values \
                     items iter setdefault \
-                    popitem get_builtin_indexed".split()
+                    popitem".split()
 
     def make_method(method):
         def f(self, *args):
@@ -145,13 +139,6 @@
             else:
                 return result
 
-    # the following method only makes sense when the option to use the
-    # CALL_LIKELY_BUILTIN opcode is set. Otherwise it won't even be seen
-    # by the annotator
-    def get_builtin_indexed(self, w_dict, i):
-        key = OPTIMIZED_BUILTINS[i]
-        return self.getitem_str(w_dict, key)
-
     def clear(self, w_dict):
         strategy = self.space.fromcache(EmptyDictStrategy)
         storage = strategy.get_empty_storage()
@@ -465,36 +452,6 @@
             return None, None
 
 
-class WaryDictStrategy(StringDictStrategy):
-    def __init__(self, space):
-        StringDictStrategy.__init__(self, space)
-        self.shadowed = [None] * len(BUILTIN_TO_INDEX)
-
-    def setitem_str(self, w_dict, key, w_value):
-        i = BUILTIN_TO_INDEX.get(key, -1)
-        if i != -1:
-            self.shadowed[i] = w_value
-        self.unerase(w_dict.dstorage)[key] = w_value
-
-    def delitem(self, w_dict, w_key):
-        space = self.space
-        w_key_type = space.type(w_key)
-        if space.is_w(w_key_type, space.w_str):
-            key = space.str_w(w_key)
-            del self.unerase(w_dict.dstorage)[key]
-            i = BUILTIN_TO_INDEX.get(key, -1)
-            if i != -1:
-                self.shadowed[i] = None
-        elif _is_sane_hash(space, w_key_type):
-            raise KeyError
-        else:
-            self.switch_to_object_strategy(w_dict)
-            return w_dict.delitem(w_key)
-
-    def get_builtin_indexed(self, w_dict, i):
-        return self.shadowed[i]
-
-
 class RDictIteratorImplementation(IteratorImplementation):
     def __init__(self, space, dictimplementation):
         IteratorImplementation.__init__(self, space, dictimplementation)
diff --git a/pypy/objspace/std/frame.py b/pypy/objspace/std/frame.py
--- a/pypy/objspace/std/frame.py
+++ b/pypy/objspace/std/frame.py
@@ -6,7 +6,7 @@
 from pypy.interpreter import pyopcode, function
 from pypy.interpreter.pyframe import PyFrame
 from pypy.interpreter.error import OperationError, operationerrfmt
-from pypy.module.__builtin__ import OPTIMIZED_BUILTINS, Module
+from pypy.module.__builtin__ import Module
 from pypy.objspace.std import intobject, smallintobject
 from pypy.objspace.std.multimethod import FailedToImplement
 from pypy.objspace.std.dictmultiobject import W_DictMultiObject
@@ -66,41 +66,6 @@
         w_result = f.space.getitem(w_1, w_2)
     f.pushvalue(w_result)
 
-def CALL_LIKELY_BUILTIN(f, oparg, next_instr):
-    w_globals = f.w_globals
-    num = oparg >> 8
-    assert isinstance(w_globals, W_DictMultiObject)
-    w_value = w_globals.get_builtin_indexed(num)
-    if w_value is None:
-        builtins = f.get_builtin()
-        assert isinstance(builtins, Module)
-        w_builtin_dict = builtins.getdict(f.space)
-        assert isinstance(w_builtin_dict, W_DictMultiObject)
-        w_value = w_builtin_dict.get_builtin_indexed(num)
-    if w_value is None:
-        varname = OPTIMIZED_BUILTINS[num]
-        message = "global name '%s' is not defined"
-        raise operationerrfmt(f.space.w_NameError,
-                              message, varname)
-    nargs = oparg & 0xff
-    w_function = w_value
-    try:
-        w_result = call_likely_builtin(f, w_function, nargs)
-    finally:
-        f.dropvalues(nargs)
-    f.pushvalue(w_result)
-
-def call_likely_builtin(f, w_function, nargs):
-    if isinstance(w_function, function.Function):
-        executioncontext = f.space.getexecutioncontext()
-        executioncontext.c_call_trace(f, w_function)
-        res = w_function.funccall_valuestack(nargs, f)
-        executioncontext.c_return_trace(f, w_function)
-        return res
-    args = f.make_arguments(nargs)
-    return f.space.call_args(w_function, args)
-
-
 compare_table = [
     "lt",   # "<"
     "le",   # "<="
@@ -145,8 +110,6 @@
             StdObjSpaceFrame.BINARY_ADD = int_BINARY_ADD
     if space.config.objspace.std.optimized_list_getitem:
         StdObjSpaceFrame.BINARY_SUBSCR = list_BINARY_SUBSCR
-    if space.config.objspace.opcodes.CALL_LIKELY_BUILTIN:
-        StdObjSpaceFrame.CALL_LIKELY_BUILTIN = CALL_LIKELY_BUILTIN
     if space.config.objspace.opcodes.CALL_METHOD:
         from pypy.objspace.std.callmethod import LOOKUP_METHOD, CALL_METHOD
         StdObjSpaceFrame.LOOKUP_METHOD = LOOKUP_METHOD
diff --git a/pypy/objspace/std/test/test_dictmultiobject.py 
b/pypy/objspace/std/test/test_dictmultiobject.py
--- a/pypy/objspace/std/test/test_dictmultiobject.py
+++ b/pypy/objspace/std/test/test_dictmultiobject.py
@@ -833,8 +833,6 @@
             withsmalldicts = False
             withcelldict = False
             withmethodcache = False
-        class opcodes:
-            CALL_LIKELY_BUILTIN = False
 
 FakeSpace.config = Config()
 
_______________________________________________
pypy-commit mailing list
[email protected]
http://mail.python.org/mailman/listinfo/pypy-commit

Reply via email to