[pypy-commit] pypy bootstrap-clarity: Create space._is_runtime attribute.
Author: Ronan LamyBranch: bootstrap-clarity Changeset: r83076:006b04e6249a Date: 2016-03-15 19:06 + http://bitbucket.org/pypy/pypy/changeset/006b04e6249a/ Log:Create space._is_runtime attribute. This is meant to allow cleanly separating translation-time objspace configuration from run-time interpreter initialisation. The attribute is initially False and must be set to True before running space.startup() or exectuting any annotator-visible RPython code. diff --git a/pypy/bin/pyinteractive.py b/pypy/bin/pyinteractive.py --- a/pypy/bin/pyinteractive.py +++ b/pypy/bin/pyinteractive.py @@ -42,7 +42,7 @@ StrOption("warn", "warning control (arg is action:message:category:module:lineno)", default=None, cmdline="-W"), - + ]) pypy_init = gateway.applevel(''' @@ -118,7 +118,7 @@ # set warning control options (if any) warn_arg = interactiveconfig.warn if warn_arg is not None: -space.appexec([space.wrap(warn_arg)], """(arg): +space.appexec([space.wrap(warn_arg)], """(arg): import sys sys.warnoptions.append(arg)""") @@ -167,6 +167,7 @@ try: def do_start(): +space._is_runtime = True space.startup() pypy_init(space, space.wrap(not interactiveconfig.no_site_import)) if main.run_toplevel(space, do_start, @@ -200,6 +201,6 @@ if __name__ == '__main__': if hasattr(sys, 'setrecursionlimit'): -# for running "python -i pyinteractive.py -Si -- py.py -Si" +# for running "python -i pyinteractive.py -Si -- py.py -Si" sys.setrecursionlimit(3000) sys.exit(main_(sys.argv)) diff --git a/pypy/goal/targetpypystandalone.py b/pypy/goal/targetpypystandalone.py --- a/pypy/goal/targetpypystandalone.py +++ b/pypy/goal/targetpypystandalone.py @@ -292,7 +292,7 @@ self.hack_for_cffi_modules(driver) return self.get_entry_point(config) - + def hack_for_cffi_modules(self, driver): # HACKHACKHACK # ugly hack to modify target goal from compile_* to build_cffi_imports @@ -319,7 +319,7 @@ while not basedir.join('include').exists(): _basedir = basedir.dirpath() if _basedir == basedir: -raise ValueError('interpreter %s not inside pypy repo', +raise ValueError('interpreter %s not inside pypy repo', str(exename)) basedir = _basedir modules = self.config.objspace.usemodules.getpaths() @@ -350,6 +350,7 @@ app = gateway.applevel(open(filename).read(), 'app_main.py', 'app_main') app.hidden_applevel = False w_dict = app.getwdict(space) +space._is_runtime = True entry_point, _ = create_entry_point(space, w_dict) return entry_point, None, PyPyAnnotatorPolicy() diff --git a/pypy/interpreter/baseobjspace.py b/pypy/interpreter/baseobjspace.py --- a/pypy/interpreter/baseobjspace.py +++ b/pypy/interpreter/baseobjspace.py @@ -374,6 +374,7 @@ def __init__(self, config=None): "NOT_RPYTHON: Basic initialization of objects." +self._is_runtime = False self.fromcache = InternalSpaceCache(self).getorbuild self.threadlocals = ThreadLocals() # set recursion limit @@ -391,7 +392,7 @@ self.check_signal_action = None # changed by the signal module self.user_del_action = UserDelAction(self) self._code_of_sys_exc_info = None - + # can be overridden to a subclass self.initialize() @@ -643,21 +644,14 @@ # you should not see frames while you translate # so we make sure that the threadlocals never *have* an # ExecutionContext during translation. -if not we_are_translated(): -if self.config.translating: -assert self.threadlocals.get_ec() is None, ( -"threadlocals got an ExecutionContext during translation!") -try: -return self._ec_during_translation -except AttributeError: -ec = self.createexecutioncontext() -self._ec_during_translation = ec -return ec -else: -ec = self.threadlocals.get_ec() -if ec is None: -self.threadlocals.enter_thread(self) -ec = self.threadlocals.get_ec() +if not self._is_runtime: +assert self.threadlocals.get_ec() is None, ( +"threadlocals got an ExecutionContext during translation!") +try: +return self._ec_during_translation +except AttributeError: +ec = self.createexecutioncontext() +self._ec_during_translation = ec return ec
[pypy-commit] pypy bootstrap-clarity: Make module _cleanup_ explicit
Author: Ronan LamyBranch: bootstrap-clarity Changeset: r83077:11e9cab4e26f Date: 2016-03-15 20:10 + http://bitbucket.org/pypy/pypy/changeset/11e9cab4e26f/ Log:Make module _cleanup_ explicit diff --git a/pypy/interpreter/baseobjspace.py b/pypy/interpreter/baseobjspace.py --- a/pypy/interpreter/baseobjspace.py +++ b/pypy/interpreter/baseobjspace.py @@ -633,6 +633,8 @@ self.getbuiltinmodule('__builtin__') for mod in self.builtin_modules.values(): mod.setup_after_space_initialization() +for mod in self.builtin_modules.values(): +mod.cleanup() def initialize(self): """NOT_RPYTHON: Abstract method that should put some minimal diff --git a/pypy/interpreter/mixedmodule.py b/pypy/interpreter/mixedmodule.py --- a/pypy/interpreter/mixedmodule.py +++ b/pypy/interpreter/mixedmodule.py @@ -123,7 +123,7 @@ self.save_module_content_for_future_reload() return self.w_dict -def _cleanup_(self): +def cleanup(self): self.getdict(self.space) self.w_initialdict = None self.startup_called = False diff --git a/pypy/interpreter/module.py b/pypy/interpreter/module.py --- a/pypy/interpreter/module.py +++ b/pypy/interpreter/module.py @@ -29,7 +29,7 @@ space.w_None) self.startup_called = False -def _cleanup_(self): +def cleanup(self): """Called by the annotator on prebuilt Module instances. We don't have many such modules, but for the ones that show up, remove their __file__ rather than translate it diff --git a/pypy/interpreter/test/test_appinterp.py b/pypy/interpreter/test/test_appinterp.py --- a/pypy/interpreter/test/test_appinterp.py +++ b/pypy/interpreter/test/test_appinterp.py @@ -3,30 +3,30 @@ from pypy.interpreter.gateway import appdef, ApplevelClass, applevel_temp from pypy.interpreter.error import OperationError -def test_execwith_novars(space): -val = space.appexec([], """ -(): -return 42 -""") +def test_execwith_novars(space): +val = space.appexec([], """ +(): +return 42 +""") assert space.eq_w(val, space.wrap(42)) -def test_execwith_withvars(space): +def test_execwith_withvars(space): val = space.appexec([space.wrap(7)], """ -(x): -y = 6 * x -return y -""") +(x): +y = 6 * x +return y +""") assert space.eq_w(val, space.wrap(42)) -def test_execwith_compile_error(space): +def test_execwith_compile_error(space): excinfo = py.test.raises(OperationError, space.appexec, [], """ -(): -y y +(): +y y """) -assert str(excinfo.value.errorstr(space)).find('y y') != -1 +assert str(excinfo.value.errorstr(space)).find('y y') != -1 def test_simple_applevel(space): -app = appdef("""app(x,y): +app = appdef("""app(x,y): return x + y """) assert app.func_name == 'app' @@ -34,15 +34,15 @@ assert space.eq_w(w_result, space.wrap(42)) def test_applevel_with_one_default(space): -app = appdef("""app(x,y=1): +app = appdef("""app(x,y=1): return x + y """) assert app.func_name == 'app' -w_result = app(space, space.wrap(41)) +w_result = app(space, space.wrap(41)) assert space.eq_w(w_result, space.wrap(42)) def test_applevel_with_two_defaults(space): -app = appdef("""app(x=1,y=2): +app = appdef("""app(x=1,y=2): return x + y """) w_result = app(space, space.wrap(41), space.wrap(1)) @@ -56,19 +56,19 @@ def test_applevel_noargs(space): -app = appdef("""app(): -return 42 +app = appdef("""app(): +return 42 """) assert app.func_name == 'app' -w_result = app(space) +w_result = app(space) assert space.eq_w(w_result, space.wrap(42)) -def somefunc(arg2=42): -return arg2 +def somefunc(arg2=42): +return arg2 -def test_app2interp_somefunc(space): -app = appdef(somefunc) -w_result = app(space) +def test_app2interp_somefunc(space): +app = appdef(somefunc) +w_result = app(space) assert space.eq_w(w_result, space.wrap(42)) def test_applevel_functions(space, applevel_temp = applevel_temp): @@ -85,45 +85,45 @@ def test_applevel_class(space, applevel_temp = applevel_temp): app = applevel_temp(''' class C(object): -clsattr = 42 -def __init__(self, x=13): -self.attr = x +clsattr = 42 +def __init__(self, x=13): +self.attr = x ''') C = app.interphook('C') -c = C(space, space.wrap(17)) +c = C(space, space.wrap(17)) w_attr = space.getattr(c, space.wrap('clsattr')) assert space.eq_w(w_attr, space.wrap(42)) w_clsattr = space.getattr(c, space.wrap('attr')) assert space.eq_w(w_clsattr, space.wrap(17)) -def app_test_something_at_app_level(): +def
[pypy-commit] cffi default: Document issue #247
Author: Armin RigoBranch: Changeset: r2648:9fa50c74716e Date: 2016-03-15 18:16 +0100 http://bitbucket.org/cffi/cffi/changeset/9fa50c74716e/ Log:Document issue #247 diff --git a/doc/source/cdef.rst b/doc/source/cdef.rst --- a/doc/source/cdef.rst +++ b/doc/source/cdef.rst @@ -109,6 +109,14 @@ install_requires=["cffi>=1.0.0"], ) +* Note that some bundler tools that try to find all modules used by a + project, like PyInstaller, will miss ``_cffi_backend`` in the + out-of-line mode because your program contains no explicit ``import + cffi`` or ``import _cffi_backend``. You need to add + ``_cffi_backend`` explicitly (as a "hidden import" in PyInstaller, + but it can also be done more generally by adding the line ``import + _cffi_backend`` in your main program). + Note that CFFI actually contains two different ``FFI`` classes. The page `Using the ffi/lib objects`_ describes the common functionality. It is what you get in the ``from package._foo import ffi`` lines above. ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] cffi default: Another attempt at improving the shutdown issues w.r.t. @def_extern
Author: Armin RigoBranch: Changeset: r2647:ab9941c073b3 Date: 2016-03-15 18:07 +0100 http://bitbucket.org/cffi/cffi/changeset/ab9941c073b3/ Log:Another attempt at improving the shutdown issues w.r.t. @def_extern diff --git a/c/call_python.c b/c/call_python.c --- a/c/call_python.c +++ b/c/call_python.c @@ -1,25 +1,52 @@ static PyObject *_get_interpstate_dict(void) { -/* hack around to return a dict that is subinterpreter-local */ +/* Hack around to return a dict that is subinterpreter-local. + Does not return a new reference. Returns NULL in case of + error, but without setting any exception. (If called late + during shutdown, we *can't* set an exception!) +*/ +static PyObject *attr_name = NULL; +PyThreadState *tstate; +PyObject *d, *builtins; int err; -PyObject *m, *modules = PyThreadState_GET()->interp->modules; -if (modules == NULL) { -PyErr_SetString(FFIError, "subinterpreter already gone?"); +tstate = PyThreadState_GET(); +if (tstate == NULL) { +/* no thread state! */ return NULL; } -m = PyDict_GetItemString(modules, "_cffi_backend._extern_py"); -if (m == NULL) { -m = PyModule_New("_cffi_backend._extern_py"); -if (m == NULL) -return NULL; -err = PyDict_SetItemString(modules, "_cffi_backend._extern_py", m); -Py_DECREF(m);/* sys.modules keeps one reference to m */ + +builtins = tstate->interp->builtins; +if (builtins == NULL) { +/* subinterpreter was cleared already, or is being cleared right now, + to a point that is too much for us to continue */ +return NULL; +} + +/* from there on, we know the (sub-)interpreter is still valid */ + +if (attr_name == NULL) { +attr_name = PyString_InternFromString("__cffi_backend_extern_py"); +if (attr_name == NULL) +goto error; +} + +d = PyDict_GetItem(builtins, attr_name); +if (d == NULL) { +d = PyDict_New(); +if (d == NULL) +goto error; +err = PyDict_SetItem(builtins, attr_name, d); +Py_DECREF(d);/* if successful, there is one ref left in builtins */ if (err < 0) -return NULL; +goto error; } -return PyModule_GetDict(m); +return d; + + error: +PyErr_Clear();/* typically a MemoryError */ +return NULL; } static PyObject *_ffi_def_extern_decorator(PyObject *outer_args, PyObject *fn) @@ -77,7 +104,7 @@ interpstate_dict = _get_interpstate_dict(); if (interpstate_dict == NULL) { Py_DECREF(infotuple); -return NULL; +return PyErr_NoMemory(); } externpy = (struct _cffi_externpy_s *)g->address; @@ -119,7 +146,7 @@ interpstate_dict = _get_interpstate_dict(); if (interpstate_dict == NULL) -goto error; +return 4;/* oops, shutdown issue? */ interpstate_key = PyLong_FromVoidPtr((void *)externpy); if (interpstate_key == NULL) @@ -219,8 +246,9 @@ if (err) { static const char *msg[] = { "no code was attached to it yet with @ffi.def_extern()", -"got internal exception (out of memory / shutdown issue)", +"got internal exception (out of memory?)", "@ffi.def_extern() was not called in the current subinterpreter", +"got internal exception (shutdown issue?)", }; fprintf(stderr, "extern \"Python\": function %s() called, " "but %s. Returning 0.\n", externpy->name, msg[err-1]); ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy jit-leaner-frontend: try to get rid of values too
Author: fijal Branch: jit-leaner-frontend Changeset: r83074:b62416027897 Date: 2016-03-15 15:43 +0200 http://bitbucket.org/pypy/pypy/changeset/b62416027897/ Log:try to get rid of values too diff --git a/rpython/jit/metainterp/logger.py b/rpython/jit/metainterp/logger.py --- a/rpython/jit/metainterp/logger.py +++ b/rpython/jit/metainterp/logger.py @@ -187,7 +187,10 @@ s = s.replace(',', '.') # we use comma for argument splitting s2 = '' for box in args[1:]: -s2 += ', %d' % box.getint() +if isinstance(box, ConstInt): +s2 += ', %d' % box.getint() +else: +s2 += ', box' return "jit_debug('%s'%s)" % (s, s2) if ops_offset is None: offset = -1 diff --git a/rpython/jit/metainterp/resoperation.py b/rpython/jit/metainterp/resoperation.py --- a/rpython/jit/metainterp/resoperation.py +++ b/rpython/jit/metainterp/resoperation.py @@ -329,10 +329,7 @@ descr = self.getdescr() if descr is DONT_CHANGE: descr = None -newop = ResOperation(opnum, args, descr) -if self.type != 'v': -newop.copy_value_from(self) -return newop +return ResOperation(opnum, args, descr) def repr(self, memo, graytext=False): # RPython-friendly version @@ -1720,14 +1717,6 @@ baseclass = PlainResOp mixins = [arity2mixin.get(arity, N_aryOp)] -if result_type == 'i': -mixins.append(IntOp) -elif result_type == 'f': -mixins.append(FloatOp) -elif result_type == 'r': -mixins.append(RefOp) -else: -assert result_type == 'n' if name in _cast_ops: if "INT_SIGNEXT" in name: mixins.append(SignExtOp) @@ -1736,7 +1725,11 @@ cls_name = '%s_OP' % name bases = (get_base_class(tuple(mixins), baseclass),) dic = {'opnum': opnum} -return type(cls_name, bases, dic) +res = type(cls_name, bases, dic) +if result_type == 'n': +result_type = 'v' # why? +res.type = result_type +return res setup(__name__ == '__main__') # print out the table when run directly del _oplist diff --git a/rpython/jit/tool/oparser.py b/rpython/jit/tool/oparser.py --- a/rpython/jit/tool/oparser.py +++ b/rpython/jit/tool/oparser.py @@ -252,7 +252,7 @@ return opnum, args, descr, fail_args def create_op(self, opnum, args, res, descr, fail_args): -res = ResOperation(opnum, args, -1, descr) +res = ResOperation(opnum, args, descr) if fail_args is not None: res.setfailargs(fail_args) if self._postproces: ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy jit-leaner-frontend: another micro-optimization
Author: fijal Branch: jit-leaner-frontend Changeset: r83075:5f3c4d1e2f03 Date: 2016-03-15 18:45 +0200 http://bitbucket.org/pypy/pypy/changeset/5f3c4d1e2f03/ Log:another micro-optimization diff --git a/rpython/jit/metainterp/opencoder.py b/rpython/jit/metainterp/opencoder.py --- a/rpython/jit/metainterp/opencoder.py +++ b/rpython/jit/metainterp/opencoder.py @@ -325,9 +325,12 @@ array[i] = self._encode(boxes[i]) return array -def create_top_snapshot(self, jitcode, pc, boxes, vable_boxes, vref_boxes): +def new_array(self, lgt): +return [rffi.cast(rffi.SHORT, 0)] * lgt + +def create_top_snapshot(self, jitcode, pc, frame, flag, vable_boxes, vref_boxes): self._total_snapshots += 1 -array = self._list_of_boxes(boxes) +array = frame.get_list_of_active_boxes(flag, self.new_array, self._encode) vable_array = self._list_of_boxes(vable_boxes) vref_array = self._list_of_boxes(vref_boxes) s = TopSnapshot(combine_uint(jitcode.index, pc), array, vable_array, @@ -350,9 +353,9 @@ self._ops[self._pos - 1] = rffi.cast(rffi.SHORT, len(self._snapshots) - 1) return s -def create_snapshot(self, jitcode, pc, boxes): +def create_snapshot(self, jitcode, pc, frame, flag): self._total_snapshots += 1 -array = self._list_of_boxes(boxes) +array = frame.get_list_of_active_boxes(flag, self.new_array, self._encode) return Snapshot(combine_uint(jitcode.index, pc), array) def get_iter(self, metainterp_sd=None): diff --git a/rpython/jit/metainterp/pyjitpl.py b/rpython/jit/metainterp/pyjitpl.py --- a/rpython/jit/metainterp/pyjitpl.py +++ b/rpython/jit/metainterp/pyjitpl.py @@ -127,7 +127,7 @@ def get_current_position_info(self): return self.jitcode.get_live_vars_info(self.pc) -def get_list_of_active_boxes(self, in_a_call): +def get_list_of_active_boxes(self, in_a_call, new_array, encode): if in_a_call: # If we are not the topmost frame, self._result_argcode contains # the type of the result of the call instruction in the bytecode. @@ -146,18 +146,18 @@ start_f = start_r + info.get_register_count_r() total = start_f + info.get_register_count_f() # allocate a list of the correct size -env = [None] * total +env = new_array(total) make_sure_not_resized(env) # fill it now for i in range(info.get_register_count_i()): index = info.get_register_index_i(i) -env[start_i + i] = self.registers_i[index] +env[start_i + i] = encode(self.registers_i[index]) for i in range(info.get_register_count_r()): index = info.get_register_index_r(i) -env[start_r + i] = self.registers_r[index] +env[start_r + i] = encode(self.registers_r[index]) for i in range(info.get_register_count_f()): index = info.get_register_index_f(i) -env[start_f + i] = self.registers_f[index] +env[start_f + i] = encode(self.registers_f[index]) return env def replace_active_box_in_frame(self, oldbox, newbox): diff --git a/rpython/jit/metainterp/resume.py b/rpython/jit/metainterp/resume.py --- a/rpython/jit/metainterp/resume.py +++ b/rpython/jit/metainterp/resume.py @@ -90,8 +90,7 @@ if target.parent_snapshot: snapshot.prev = target.parent_snapshot return -s = t.create_snapshot(back.jitcode, back.pc, - back.get_list_of_active_boxes(True)) +s = t.create_snapshot(back.jitcode, back.pc, back, True) snapshot.prev = s _ensure_parent_resumedata(framestack, n - 1, t, s) target.parent_snapshot = s @@ -108,7 +107,7 @@ if n >= 0: top = framestack[n] snapshot = t.create_top_snapshot(top.jitcode, top.pc, -top.get_list_of_active_boxes(False), virtualizable_boxes, +top, False, virtualizable_boxes, virtualref_boxes) _ensure_parent_resumedata(framestack, n, t,snapshot) else: ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy cpyext-ext: Undo one of the effects of hacking at PyString_Type.tp_itemsize, which
Author: Armin RigoBranch: cpyext-ext Changeset: r83073:7b7796d0cff0 Date: 2016-03-15 16:53 +0100 http://bitbucket.org/pypy/pypy/changeset/7b7796d0cff0/ Log:Undo one of the effects of hacking at PyString_Type.tp_itemsize, which is that all PyStringObjects have the extra size allocated (but don't use it) diff --git a/pypy/module/cpyext/pyobject.py b/pypy/module/cpyext/pyobject.py --- a/pypy/module/cpyext/pyobject.py +++ b/pypy/module/cpyext/pyobject.py @@ -46,7 +46,7 @@ size = pytype.c_tp_basicsize else: size = rffi.sizeof(self.basestruct) -if itemcount: +if itemcount and w_type is not space.w_str: size += itemcount * pytype.c_tp_itemsize assert size >= rffi.sizeof(PyObject.TO) buf = lltype.malloc(rffi.VOIDP.TO, size, ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy cpyext-ext: * Remove unicode_alloc.
Author: Armin RigoBranch: cpyext-ext Changeset: r83072:251f4973a108 Date: 2016-03-15 16:48 +0100 http://bitbucket.org/pypy/pypy/changeset/251f4973a108/ Log:* Remove unicode_alloc. * Ensure the order of the fields is correct (might be unnecessary, but feels safer). diff --git a/pypy/module/cpyext/bytesobject.py b/pypy/module/cpyext/bytesobject.py --- a/pypy/module/cpyext/bytesobject.py +++ b/pypy/module/cpyext/bytesobject.py @@ -53,8 +53,8 @@ PyStringObjectStruct = lltype.ForwardReference() PyStringObject = lltype.Ptr(PyStringObjectStruct) PyStringObjectFields = PyObjectFields + \ -(("ob_shash", rffi.LONG), ("ob_sstate", rffi.INT), - ("buffer", rffi.CCHARP), ("ob_size", Py_ssize_t)) +(("ob_size", Py_ssize_t), ("ob_shash", rffi.LONG), + ("ob_sstate", rffi.INT), ("buffer", rffi.CCHARP)) cpython_struct("PyStringObject", PyStringObjectFields, PyStringObjectStruct) @bootstrap_function diff --git a/pypy/module/cpyext/unicodeobject.py b/pypy/module/cpyext/unicodeobject.py --- a/pypy/module/cpyext/unicodeobject.py +++ b/pypy/module/cpyext/unicodeobject.py @@ -30,7 +30,6 @@ def init_unicodeobject(space): make_typedescr(space.w_unicode.layout.typedef, basestruct=PyUnicodeObject.TO, - alloc = unicode_alloc, attach=unicode_attach, dealloc=unicode_dealloc, realize=unicode_realize) @@ -48,6 +47,7 @@ ''' see comments with string_alloc in stringobject.py ''' +XXX from pypy.module.cpyext.typeobjectdefs import PyTypeObjectPtr pytype = as_pyobj(space, w_type) pytype = rffi.cast(PyTypeObjectPtr, pytype) ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy guard-compatible: nonsense
Author: Carl Friedrich BolzBranch: guard-compatible Changeset: r83071:24d702fa2df4 Date: 2016-03-15 15:02 +0100 http://bitbucket.org/pypy/pypy/changeset/24d702fa2df4/ Log:nonsense diff --git a/pypy/objspace/std/mapdict.py b/pypy/objspace/std/mapdict.py --- a/pypy/objspace/std/mapdict.py +++ b/pypy/objspace/std/mapdict.py @@ -129,7 +129,7 @@ def length(self): raise NotImplementedError("abstract base class") -@jit.guard_compatible() +@jit.elidable_compatible() def _length_larger_than(self, n): return self.length() > n ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy guard-compatible: avoid some operations
Author: Carl Friedrich BolzBranch: guard-compatible Changeset: r83070:cadb6f1c1225 Date: 2016-03-15 14:49 +0100 http://bitbucket.org/pypy/pypy/changeset/cadb6f1c1225/ Log:avoid some operations diff --git a/pypy/objspace/std/mapdict.py b/pypy/objspace/std/mapdict.py --- a/pypy/objspace/std/mapdict.py +++ b/pypy/objspace/std/mapdict.py @@ -129,6 +129,10 @@ def length(self): raise NotImplementedError("abstract base class") +@jit.guard_compatible() +def _length_larger_than(self, n): +return self.length() > n + def get_terminator(self): return self.terminator @@ -659,7 +663,7 @@ self.map = map def _has_storage_list(self): -return self.map.length() > n +return self.map._length_larger_than(n) def _mapdict_get_storage_list(self): erased = getattr(self, valnmin1) ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy jit-leaner-frontend: try to not have position on resop at all
Author: fijal Branch: jit-leaner-frontend Changeset: r83069:5413d954e8a2 Date: 2016-03-15 15:28 +0200 http://bitbucket.org/pypy/pypy/changeset/5413d954e8a2/ Log:try to not have position on resop at all diff --git a/rpython/jit/metainterp/history.py b/rpython/jit/metainterp/history.py --- a/rpython/jit/metainterp/history.py +++ b/rpython/jit/metainterp/history.py @@ -7,7 +7,8 @@ from rpython.conftest import option from rpython.jit.metainterp.resoperation import ResOperation, rop,\ -AbstractValue, oparity, AbstractResOp, IntOp, RefOp, FloatOp +AbstractValue, oparity, AbstractResOp, IntOp, RefOp, FloatOp,\ +opclasses from rpython.jit.codewriter import heaptracker, longlong import weakref @@ -647,15 +648,27 @@ def __init__(self, pos): self.position = pos +def get_position(self): +return self.position + class IntFrontendOp(IntOp, FrontendOp): _attrs_ = ('position', '_resint') +def copy_value_from(self, other): +self._resint = other.getint() + class FloatFrontendOp(FloatOp, FrontendOp): _attrs_ = ('position', '_resfloat') +def copy_value_from(self, other): +self._resfloat = other.getfloatstorage() + class RefFrontendOp(RefOp, FrontendOp): _attrs_ = ('position', '_resref') +def copy_value_from(self, other): +self._resref = other.getref_base() + class History(object): ends_with_jump = False trace = None @@ -673,12 +686,9 @@ self.inputargs = inpargs if self._cache: # hack to record the ops *after* we know our inputargs -for op in self._cache: -newop = self.trace.record_op(op.getopnum(), op.getarglist(), - op.getdescr()) -op.position = newop.position -if op.type != 'v': -newop.copy_value_from(op) +for (opnum, argboxes, op, descr) in self._cache: +pos = self.trace.record_op(opnum, argboxes, descr) +op.position = pos self._cache = None def length(self): @@ -710,29 +720,39 @@ @specialize.argtype(3) def record(self, opnum, argboxes, value, descr=None): if self.trace is None: -op = ResOperation(opnum, argboxes, -1, descr) -self._cache.append(op) +pos = -1 else: -pos = self.trace._record_op(opnum, argboxes, descr) -if value is None: -op = FrontendOp(pos) -elif isinstance(value, bool): -op = IntFrontendOp(pos) -elif lltype.typeOf(value) == lltype.Signed: -op = IntFrontendOp(pos) -elif lltype.typeOf(value) is longlong.FLOATSTORAGE: -op = FloatFrontendOp(pos) -else: -op = RefFrontendOp(pos) +pos = self.trace.record_op(opnum, argboxes, descr) +if value is None: +op = FrontendOp(pos) +elif isinstance(value, bool): +op = IntFrontendOp(pos) +elif lltype.typeOf(value) == lltype.Signed: +op = IntFrontendOp(pos) +elif lltype.typeOf(value) is longlong.FLOATSTORAGE: +op = FloatFrontendOp(pos) +else: +op = RefFrontendOp(pos) +if self.trace is None: +self._cache.append((opnum, argboxes, op, descr)) self.set_op_value(op, value) return op def record_nospec(self, opnum, argboxes, descr=None): -return self.trace.record_op(opnum, argboxes, descr) +tp = opclasses[opnum].type +pos = self.trace.record_op(opnum, argboxes, descr) +if tp == 'v': +return FrontendOp(pos) +elif tp == 'i': +return IntFrontendOp(pos) +elif tp == 'f': +return FloatFrontendOp(pos) +assert tp == 'r' +return RefFrontendOp(pos) def record_default_val(self, opnum, argboxes, descr=None): assert rop.is_same_as(opnum) -op = self.trace.record_op(opnum, argboxes, descr) +op = self.record_nospec(opnum, argboxes, descr) op.copy_value_from(argboxes[0]) return op diff --git a/rpython/jit/metainterp/opencoder.py b/rpython/jit/metainterp/opencoder.py --- a/rpython/jit/metainterp/opencoder.py +++ b/rpython/jit/metainterp/opencoder.py @@ -133,7 +133,7 @@ descr = self.trace._descrs[descr_index] else: descr = None -res = ResOperation(opnum, args, -1, descr=descr) +res = ResOperation(opnum, args, descr=descr) if rop.is_guard(opnum): assert isinstance(res, GuardResOp) res.rd_resume_position = descr_index @@ -288,7 +288,7 @@ else: assert False, "unreachable code" -def _record_op(self, opnum, argboxes, descr=None): +def record_op(self, opnum, argboxes, descr=None): pos = self._count
[pypy-commit] pypy guard-compatible: remove two more promotes
Author: Carl Friedrich BolzBranch: guard-compatible Changeset: r83067:1b4c7fac81be Date: 2016-03-15 10:11 +0100 http://bitbucket.org/pypy/pypy/changeset/1b4c7fac81be/ Log:remove two more promotes diff --git a/pypy/objspace/std/mapdict.py b/pypy/objspace/std/mapdict.py --- a/pypy/objspace/std/mapdict.py +++ b/pypy/objspace/std/mapdict.py @@ -41,11 +41,14 @@ # objects with different maps can have the same class return self.terminator.w_cls +@jit.elidable_compatible() +def _get_terminator(self): +return self.terminator + def read(self, obj, name, index): attr = self.find_map_attr(name, index) if attr is None: -jit.promote(self) -return self.terminator._read_terminator(obj, name, index) +return self._get_terminator()._read_terminator(obj, name, index) if ( # XXX in the guard_compatible world the following isconstant may never be true? jit.isconstant(attr.storageindex) and jit.isconstant(obj) and @@ -62,9 +65,7 @@ def write(self, obj, name, index, w_value): attr = self.find_map_attr(name, index) if attr is None: -# adding an attribute needs to know all attributes, thus promote -jit.promote(self) -return self.terminator._write_terminator(obj, name, index, w_value) +return self._get_terminator()._write_terminator(obj, name, index, w_value) if not attr.ever_mutated: attr.ever_mutated = True obj._mapdict_write_storage(attr.storageindex, w_value) ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy guard-compatible: Add more flexibility with (compilation-time) tweakable parameters
Author: Armin RigoBranch: guard-compatible Changeset: r83066:0cbabc844652 Date: 2016-03-15 10:08 +0100 http://bitbucket.org/pypy/pypy/changeset/0cbabc844652/ Log:Add more flexibility with (compilation-time) tweakable parameters diff --git a/rpython/jit/backend/test/runner_test.py b/rpython/jit/backend/test/runner_test.py --- a/rpython/jit/backend/test/runner_test.py +++ b/rpython/jit/backend/test/runner_test.py @@ -217,7 +217,7 @@ self.cpu.grow_guard_compatible_switch(looptoken.compiled_loop_token, faildescr1, t2_box._resref) -for retry in range(2): +for retry in range(5): deadframe = self.cpu.execute_token(looptoken, t2_box._resref) fail = self.cpu.get_latest_descr(deadframe) diff --git a/rpython/jit/backend/x86/guard_compat.py b/rpython/jit/backend/x86/guard_compat.py --- a/rpython/jit/backend/x86/guard_compat.py +++ b/rpython/jit/backend/x86/guard_compat.py @@ -15,6 +15,22 @@ # the guard, ending in -1. +# --tweakable parameters (you get the effect closest to before we had +# guard-compat by setting GROW_POSITION to 1 and UPDATE_ASM to 0)-- + +# where grow_switch puts the new value: +# 0 = at the beginning of the list +# 1 = at position N-1, just before the initial value which stays last +# 2 = at the end +GROW_POSITION = 2 + +# when guard_compatible's slow path is called and finds a value, when +# should we update the machine code to make this value the fast-path? +# 0 = never +# another value = after about this many calls to the slow-path +UPDATE_ASM = 1291 + + def generate_guard_compatible(assembler, guard_token, loc_reg, initial_value): # fast-path check mc = assembler.mc @@ -49,9 +65,10 @@ mc.stack_frame_size_delta(-WORD) small_ofs = rel_pos_compatible_imm - mc.get_relative_pos() -compatinfo[0] = small_ofs +assert -128 <= small_ofs < 128 +compatinfo[0] = small_ofs & 0xFF -assembler.guard_success_cc = rx86.Conditions['NZ'] +assembler.guard_success_cc = rx86.Conditions['Z'] assembler.implement_guard(guard_token) # # patch the JE above @@ -99,10 +116,22 @@ newcompatinfo = rffi.cast(rffi.SIGNEDP, newcompatinfoaddr) newcompatinfo[0] = compatinfo[0] -newcompatinfo[1] = new_value -for i in range(1, length): -newcompatinfo[i + 1] = compatinfo[i] +if GROW_POSITION == 0: +newcompatinfo[1] = new_value +for i in range(1, length): +newcompatinfo[i + 1] = compatinfo[i] +elif GROW_POSITION == 1: +for i in range(1, length - 2): +newcompatinfo[i] = compatinfo[i] +newcompatinfo[length - 2] = new_value +newcompatinfo[length - 1] = compatinfo[length - 2] +newcompatinfo[length] = -1# == compatinfo[length - 1] +else: +for i in range(1, length - 1): +newcompatinfo[i] = compatinfo[i] +newcompatinfo[length - 1] = new_value +newcompatinfo[length] = -1# == compatinfo[length - 1] # the old 'compatinfo' is not used any more, but will only be freed # when the looptoken is freed @@ -117,6 +146,36 @@ assembler._guard_compat_checkers = [0] * nb_registers +def _build_inner_loop(mc, regnum, tmp, immediate_return): +pos = mc.get_relative_pos() +mc.CMP_mr((tmp, WORD), regnum) +mc.J_il8(rx86.Conditions['E'], 0)# patched below +je_location = mc.get_relative_pos() +mc.CMP_mi((tmp, WORD), -1) +mc.LEA_rm(tmp, (tmp, WORD)) +mc.J_il8(rx86.Conditions['NE'], pos - (mc.get_relative_pos() + 2)) +# +# not found! Return the condition code 'Not Zero' to mean 'not found'. +mc.OR_rr(tmp, tmp) +# +# if 'immediate_return', patch the JE above to jump here. When we +# follow that path, we get condition code 'Zero', which means 'found'. +if immediate_return: +offset = mc.get_relative_pos() - je_location +assert 0 < offset <= 127 +mc.overwrite(je_location-1, chr(offset)) +# +if IS_X86_32: +mc.POP_r(tmp) +mc.RET16_i(WORD) +mc.force_frame_size(8) # one word on X86_64, two words on X86_32 +# +# if not 'immediate_return', patch the JE above to jump here. +if not immediate_return: +offset = mc.get_relative_pos() - je_location +assert 0 < offset <= 127 +mc.overwrite(je_location-1, chr(offset)) + def get_or_build_checker(assembler, regnum): """Returns a piece of assembler that checks if the value is in some array (there is one such piece per input register 'regnum') @@ -142,40 +201,43 @@ mc.MOV_rs(tmp, stack_arg) -pos = mc.get_relative_pos() -mc.CMP_mr((tmp, WORD), regnum) -mc.J_il8(rx86.Conditions['E'], 0)# patched below -je_location = mc.get_relative_pos() -mc.CMP_mi((tmp, WORD), -1) -mc.LEA_rm(tmp, (tmp, WORD)) -mc.J_il8(rx86.Conditions['NE'],
[pypy-commit] pypy jit-leaner-frontend: backpedal + be slightly more conscious
Author: fijal Branch: jit-leaner-frontend Changeset: r83064:345cab5f0d0b Date: 2016-03-15 10:15 +0200 http://bitbucket.org/pypy/pypy/changeset/345cab5f0d0b/ Log:backpedal + be slightly more conscious diff --git a/rpython/jit/metainterp/opencoder.py b/rpython/jit/metainterp/opencoder.py --- a/rpython/jit/metainterp/opencoder.py +++ b/rpython/jit/metainterp/opencoder.py @@ -249,36 +249,37 @@ SMALL_INT_START <= box.getint() < SMALL_INT_STOP): return tag(TAGINT, box.getint()) elif isinstance(box, ConstInt): -#self._consts_bigint += 1 -#if not isinstance(box.getint(), int): -## symbolics, for tests, don't worry about caching -#v = len(self._bigints) << 1 -#self._bigints.append(box.getint()) -#else: -#v = self._bigints_dict.get(box.getint(), -1) -#if v == -1: -v = len(self._bigints) << 1 -#self._bigints_dict[box.getint()] = v -self._bigints.append(box.getint()) +self._consts_bigint += 1 +if not isinstance(box.getint(), int): +# symbolics, for tests, don't worry about caching +v = len(self._bigints) << 1 +self._bigints.append(box.getint()) +else: +v = self._bigints_dict.get(box.getint(), -1) +if v == -1: +v = len(self._bigints) << 1 +self._bigints_dict[box.getint()] = v +self._bigints.append(box.getint()) return tag(TAGCONSTOTHER, v) elif isinstance(box, ConstFloat): self._consts_float += 1 -#v = self._floats_dict.get(box.getfloat(), -1) -#if v == -1: -v = (len(self._floats) << 1) | 1 -#self._floats_dict[box.getfloat()] = v -self._floats.append(box.getfloat()) +v = self._floats_dict.get(box.getfloat(), -1) +if v == -1: +v = (len(self._floats) << 1) | 1 +self._floats_dict[box.getfloat()] = v +self._floats.append(box.getfloat()) return tag(TAGCONSTOTHER, v) else: self._consts_ptr += 1 assert isinstance(box, ConstPtr) if not box.getref_base(): return tag(TAGCONSTPTR, 0) -#v = self._refs_dict.get(addr, -1) -#if v == -1: -v = len(self._refs) -#self._refs_dict[addr] = v -self._refs.append(box.getref_base()) +addr = box.getref_base() +v = self._refs_dict.get(addr, -1) +if v == -1: +v = len(self._refs) +self._refs_dict[addr] = v +self._refs.append(box.getref_base()) return tag(TAGCONSTPTR, v) elif isinstance(box, AbstractResOp): return tag(TAGBOX, box.get_position()) @@ -325,7 +326,10 @@ return ResOperation(opnum, argboxes, pos, descr) def _list_of_boxes(self, boxes): -return [rffi.cast(rffi.SHORT, self._encode(box)) for box in boxes] +array = [rffi.cast(rffi.SHORT, 0)] * len(boxes) +for i in range(boxes): +array[i] = self._encode(boxes[i]) +return array def create_top_snapshot(self, jitcode, pc, boxes, vable_boxes, vref_boxes): self._total_snapshots += 1 ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy jit-leaner-frontend: oops
Author: fijal Branch: jit-leaner-frontend Changeset: r83063:0779fefa5ca6 Date: 2016-03-15 09:15 +0200 http://bitbucket.org/pypy/pypy/changeset/0779fefa5ca6/ Log:oops diff --git a/rpython/jit/metainterp/opencoder.py b/rpython/jit/metainterp/opencoder.py --- a/rpython/jit/metainterp/opencoder.py +++ b/rpython/jit/metainterp/opencoder.py @@ -276,7 +276,7 @@ return tag(TAGCONSTPTR, 0) #v = self._refs_dict.get(addr, -1) #if v == -1: -#v = len(self._refs) +v = len(self._refs) #self._refs_dict[addr] = v self._refs.append(box.getref_base()) return tag(TAGCONSTPTR, v) ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy jit-leaner-frontend: a different approach - let's try not to intern constants
Author: fijal Branch: jit-leaner-frontend Changeset: r83062:106e5d6db9cb Date: 2016-03-15 08:58 +0200 http://bitbucket.org/pypy/pypy/changeset/106e5d6db9cb/ Log:a different approach - let's try not to intern constants diff --git a/rpython/jit/metainterp/opencoder.py b/rpython/jit/metainterp/opencoder.py --- a/rpython/jit/metainterp/opencoder.py +++ b/rpython/jit/metainterp/opencoder.py @@ -249,37 +249,36 @@ SMALL_INT_START <= box.getint() < SMALL_INT_STOP): return tag(TAGINT, box.getint()) elif isinstance(box, ConstInt): -self._consts_bigint += 1 -if not isinstance(box.getint(), int): -# symbolics, for tests, don't worry about caching -v = len(self._bigints) << 1 -self._bigints.append(box.getint()) -else: -v = self._bigints_dict.get(box.getint(), -1) -if v == -1: -v = len(self._bigints) << 1 -self._bigints_dict[box.getint()] = v -self._bigints.append(box.getint()) +#self._consts_bigint += 1 +#if not isinstance(box.getint(), int): +## symbolics, for tests, don't worry about caching +#v = len(self._bigints) << 1 +#self._bigints.append(box.getint()) +#else: +#v = self._bigints_dict.get(box.getint(), -1) +#if v == -1: +v = len(self._bigints) << 1 +#self._bigints_dict[box.getint()] = v +self._bigints.append(box.getint()) return tag(TAGCONSTOTHER, v) elif isinstance(box, ConstFloat): self._consts_float += 1 -v = self._floats_dict.get(box.getfloat(), -1) -if v == -1: -v = (len(self._floats) << 1) | 1 -self._floats_dict[box.getfloat()] = v -self._floats.append(box.getfloat()) +#v = self._floats_dict.get(box.getfloat(), -1) +#if v == -1: +v = (len(self._floats) << 1) | 1 +#self._floats_dict[box.getfloat()] = v +self._floats.append(box.getfloat()) return tag(TAGCONSTOTHER, v) else: self._consts_ptr += 1 assert isinstance(box, ConstPtr) if not box.getref_base(): return tag(TAGCONSTPTR, 0) -addr = box.getref_base() -v = self._refs_dict.get(addr, -1) -if v == -1: -v = len(self._refs) -self._refs_dict[addr] = v -self._refs.append(box.getref_base()) +#v = self._refs_dict.get(addr, -1) +#if v == -1: +#v = len(self._refs) +#self._refs_dict[addr] = v +self._refs.append(box.getref_base()) return tag(TAGCONSTPTR, v) elif isinstance(box, AbstractResOp): return tag(TAGBOX, box.get_position()) diff --git a/rpython/jit/metainterp/test/test_opencoder.py b/rpython/jit/metainterp/test/test_opencoder.py --- a/rpython/jit/metainterp/test/test_opencoder.py +++ b/rpython/jit/metainterp/test/test_opencoder.py @@ -13,6 +13,9 @@ def __init__(self, index): self.index = index +class metainterp_sd(object): +pass + class FakeFrame(object): parent_snapshot = None @@ -38,7 +41,7 @@ class TestOpencoder(object): def unpack(self, t): -iter = t.get_iter() +iter = t.get_iter(metainterp_sd) l = [] while not iter.done(): op = iter.next() @@ -142,7 +145,7 @@ def test_packing(self, i): t = Trace([]) t.record_snapshot_link(i) -iter = t.get_iter() +iter = t.get_iter(metainterp_sd) assert (((-iter._next() - 1) << 15) | (iter._next())) == i def test_cut_trace_from(self): ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy default: fix for 32 bit
Author: mattipBranch: Changeset: r83061:173add34cdd2 Date: 2016-03-15 08:10 +0200 http://bitbucket.org/pypy/pypy/changeset/173add34cdd2/ Log:fix for 32 bit diff --git a/pypy/module/micronumpy/test/test_ndarray.py b/pypy/module/micronumpy/test/test_ndarray.py --- a/pypy/module/micronumpy/test/test_ndarray.py +++ b/pypy/module/micronumpy/test/test_ndarray.py @@ -3439,7 +3439,7 @@ def test_index_int(self): import numpy as np -a = np.array([10, 20, 30]) +a = np.array([10, 20, 30], dtype='int64') res = a[np.int64(1)] assert isinstance(res, np.int64) assert res == 20 ___ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit