[pypy-commit] pypy default: add runner tests for cast_int_to_float and cast_float_to_int
Author: David Schneider Branch: Changeset: r64787:ca5c756f0e50 Date: 2013-06-05 03:10 -0500 http://bitbucket.org/pypy/pypy/changeset/ca5c756f0e50/ Log:add runner tests for cast_int_to_float and cast_float_to_int 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 @@ -1911,6 +1911,29 @@ [BoxPtr(x)], 'int').value assert res == -19 +def test_cast_int_to_float(self): +if not self.cpu.supports_floats: +py.test.skip("requires floats") +for x in [-10, -1, 0, 3, 42, sys.maxint-1]: +res = self.execute_operation(rop.CAST_INT_TO_FLOAT, + [BoxInt(x)], 'float').value +assert longlong.getrealfloat(res) == float(x) +res = self.execute_operation(rop.CAST_INT_TO_FLOAT, + [ConstInt(x)], 'float').value +assert longlong.getrealfloat(res) == float(x) + +def test_cast_float_to_int(self): +if not self.cpu.supports_floats: +py.test.skip("requires floats") +for x in [-24.23, -5.3, 0.0, 3.1234, 11.1, 0.1]: +v = longlong.getfloatstorage(x) +res = self.execute_operation(rop.CAST_FLOAT_TO_INT, + [BoxFloat(v)], 'int').value +assert res == int(x) +res = self.execute_operation(rop.CAST_FLOAT_TO_INT, + [ConstFloat(v)], 'int').value +assert res == int(x) + def test_convert_float_bytes(self): if not self.cpu.supports_floats: py.test.skip("requires floats") ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy default: Document merged branch
Author: Armin Rigo Branch: Changeset: r64788:5e587e197d4f Date: 2013-06-05 11:49 +0200 http://bitbucket.org/pypy/pypy/changeset/5e587e197d4f/ Log:Document merged branch diff --git a/pypy/doc/whatsnew-head.rst b/pypy/doc/whatsnew-head.rst --- a/pypy/doc/whatsnew-head.rst +++ b/pypy/doc/whatsnew-head.rst @@ -50,3 +50,5 @@ .. branch: win32-fixes3 Skip and fix some non-translated (own) tests for win32 builds +.. branch: ctypes-byref +Add the '_obj' attribute on ctypes pointer() and byref() objects ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy default: Fix various tests failing because of e953dfbc7f0a.
Author: Armin Rigo Branch: Changeset: r64789:d0ffe15789d8 Date: 2013-06-05 12:38 +0200 http://bitbucket.org/pypy/pypy/changeset/d0ffe15789d8/ Log:Fix various tests failing because of e953dfbc7f0a. diff --git a/lib-python/2.7/opcode.py b/lib-python/2.7/opcode.py --- a/lib-python/2.7/opcode.py +++ b/lib-python/2.7/opcode.py @@ -193,6 +193,6 @@ hasname.append(201) def_op('CALL_METHOD', 202)# #args not including 'self' def_op('BUILD_LIST_FROM_ARG', 203) -jrel_op('JUMP_IF_NOT_DEBUG', 204) # Distance to target address +jrel_op('JUMP_IF_NOT_DEBUG', 204) # jump over assert statements del def_op, name_op, jrel_op, jabs_op diff --git a/lib-python/2.7/test/test_code.py b/lib-python/2.7/test/test_code.py --- a/lib-python/2.7/test/test_code.py +++ b/lib-python/2.7/test/test_code.py @@ -75,7 +75,7 @@ cellvars: () freevars: () nlocals: 0 -flags: 67 +flags: 1048643 consts: ("'doc string'", 'None') """ diff --git a/lib-python/2.7/test/test_dis.py b/lib-python/2.7/test/test_dis.py --- a/lib-python/2.7/test/test_dis.py +++ b/lib-python/2.7/test/test_dis.py @@ -53,25 +53,26 @@ pass dis_bug1333982 = """\ - %-4d 0 LOAD_CONST 1 (0) - 3 POP_JUMP_IF_TRUE41 - 6 LOAD_GLOBAL 0 (AssertionError) - 9 LOAD_FAST0 (x) - 12 BUILD_LIST_FROM_ARG 0 - 15 GET_ITER ->> 16 FOR_ITER12 (to 31) - 19 STORE_FAST 1 (s) - 22 LOAD_FAST1 (s) - 25 LIST_APPEND 2 - 28 JUMP_ABSOLUTE 16 + %-4d 0 JUMP_IF_NOT_DEBUG 41 (to 44) + 3 LOAD_CONST 1 (0) + 6 POP_JUMP_IF_TRUE44 + 9 LOAD_GLOBAL 0 (AssertionError) + 12 LOAD_FAST0 (x) + 15 BUILD_LIST_FROM_ARG 0 + 18 GET_ITER +>> 19 FOR_ITER12 (to 34) + 22 STORE_FAST 1 (s) + 25 LOAD_FAST1 (s) + 28 LIST_APPEND 2 + 31 JUMP_ABSOLUTE 19 - %-4d >> 31 LOAD_CONST 2 (1) - 34 BINARY_ADD - 35 CALL_FUNCTION1 - 38 RAISE_VARARGS1 + %-4d >> 34 LOAD_CONST 2 (1) + 37 BINARY_ADD + 38 CALL_FUNCTION1 + 41 RAISE_VARARGS1 - %-4d >> 41 LOAD_CONST 0 (None) - 44 RETURN_VALUE + %-4d >> 44 LOAD_CONST 0 (None) + 47 RETURN_VALUE """%(bug1333982.func_code.co_firstlineno + 1, bug1333982.func_code.co_firstlineno + 2, bug1333982.func_code.co_firstlineno + 3) diff --git a/pypy/module/pypyjit/test_pypy_c/test_intbound.py b/pypy/module/pypyjit/test_pypy_c/test_intbound.py --- a/pypy/module/pypyjit/test_pypy_c/test_intbound.py +++ b/pypy/module/pypyjit/test_pypy_c/test_intbound.py @@ -231,6 +231,7 @@ assert loop.match(""" i8 = int_lt(i6, 300) guard_true(i8, descr=...) +guard_not_invalidated? i10 = int_lshift(i6, 1) i12 = int_add_ovf(i5, 1) guard_no_overflow(descr=...) @@ -253,6 +254,7 @@ assert loop.match(""" i8 = int_lt(i6, 300) guard_true(i8, descr=...) +guard_not_invalidated? i10 = int_add_ovf(i5, 8) guard_no_overflow(descr=...) i12 = int_add(i6, 1) ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy fastjson: add support for parsing float values
Author: Antonio Cuni Branch: fastjson Changeset: r64792:535479329816 Date: 2013-06-05 14:14 +0200 http://bitbucket.org/pypy/pypy/changeset/535479329816/ Log:add support for parsing float values diff --git a/pypy/module/_fastjson/interp_decoder.py b/pypy/module/_fastjson/interp_decoder.py --- a/pypy/module/_fastjson/interp_decoder.py +++ b/pypy/module/_fastjson/interp_decoder.py @@ -7,6 +7,15 @@ def is_whitespace(ch): return ch == ' ' or ch == '\t' or ch == '\r' or ch == '\n' +# precomputing negative powers of 10 is MUCH faster than using e.g. math.pow +# at runtime +NEG_POW_10 = [10**-i for i in range(16)] +def neg_pow_10(x, exp): +if exp >= len(NEG_POW_10): +return 0.0 +return x * NEG_POW_10[exp] + + TYPE_UNKNOWN = 0 TYPE_STRING = 1 @@ -23,6 +32,12 @@ def peek(self): return self.s[self.i] +def peek_maybe(self): +if self.eof(): +return '\0' +else: +return self.peek() + def next(self): ch = self.peek() self.i += 1 @@ -56,30 +71,69 @@ self.next() return self.decode_string() elif ch.isdigit() or ch == '-': -return self.decode_numeric(ch) +return self.decode_numeric() elif ch == '{': self.next() return self.decode_object() else: -assert False, 'Unkown char: %s' % ch +self._raise("No JSON object could be decoded: unexpected '%s' at char %d", +ch, self.i) -def decode_numeric(self, ch): -intval = 0 +def decode_numeric(self): +intval = self.parse_integer() +# +is_float = False +exp = 0 +frcval = 0.0 +frccount = 0 +# +# check for the optional fractional part +ch = self.peek_maybe() +if ch == '.': +is_float = True +self.next() +frcval, frccount = self.parse_digits() +frcval = neg_pow_10(frcval, frccount) +ch = self.peek_maybe() +# check for the optional exponent part +if ch == 'E' or ch == 'e': +is_float = True +self.next() +exp = self.parse_integer() +# +if is_float: +# build the float +floatval = intval + frcval +floatval = floatval * 10**exp +return self.space.wrap(floatval) +else: +return self.space.wrap(intval) + +def parse_integer(self): +"Parse a decimal number with an optional minus sign" sign = 1 -if ch == '-': +if self.peek_maybe() == '-': sign = -1 self.next() +intval, _ = self.parse_digits() +return sign * intval +def parse_digits(self): +"Parse a sequence of digits as a decimal number. No sign allowed" +intval = 0 +count = 0 while not self.eof(): ch = self.peek() if ch.isdigit(): intval = intval*10 + ord(ch)-ord('0') +count += 1 self.next() else: break -# -intval = intval*sign -return self.space.wrap(intval) +if count == 0: +self._raise("Expected digit at char %d", self.i) +return intval, count + def decode_object(self): start = self.i diff --git a/pypy/module/_fastjson/test/test__fastjson.py b/pypy/module/_fastjson/test/test__fastjson.py --- a/pypy/module/_fastjson/test/test__fastjson.py +++ b/pypy/module/_fastjson/test/test__fastjson.py @@ -71,9 +71,31 @@ def test_decode_numeric(self): import _fastjson -assert _fastjson.loads('42') == 42 -assert _fastjson.loads('-42') == -42 -raises(ValueError, "_fastjson.loads('42 abc')") +def check(s, val): +res = _fastjson.loads(s) +assert type(res) is type(val) +assert res == val +# +check('42', 42) +check('-42', -42) +check('42.123', 42.123) +check('42E0', 42.0) +check('42E3', 42000.0) +check('42E-1', 4.2) +check('42.123E3', 42123.0) + +def test_decode_numeric_invalid(self): +import _fastjson +def error(s): +raises(ValueError, _fastjson.loads, s) +# +error(' 42 abc') +error('.123') +error('12.') +error('12.-3') +error('12E') +error('12E-') + def test_decode_object(self): import _fastjson ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy fastjson: add parsing of integers
Author: Antonio Cuni Branch: fastjson Changeset: r64791:65996c45a142 Date: 2013-06-05 12:32 +0200 http://bitbucket.org/pypy/pypy/changeset/65996c45a142/ Log:add parsing of integers diff --git a/pypy/module/_fastjson/interp_decoder.py b/pypy/module/_fastjson/interp_decoder.py --- a/pypy/module/_fastjson/interp_decoder.py +++ b/pypy/module/_fastjson/interp_decoder.py @@ -51,14 +51,36 @@ def decode_any(self): self.skip_whitespace() -ch = self.next() +ch = self.peek() if ch == '"': +self.next() return self.decode_string() +elif ch.isdigit() or ch == '-': +return self.decode_numeric(ch) elif ch == '{': +self.next() return self.decode_object() else: assert False, 'Unkown char: %s' % ch +def decode_numeric(self, ch): +intval = 0 +sign = 1 +if ch == '-': +sign = -1 +self.next() + +while not self.eof(): +ch = self.peek() +if ch.isdigit(): +intval = intval*10 + ord(ch)-ord('0') +self.next() +else: +break +# +intval = intval*sign +return self.space.wrap(intval) + def decode_object(self): start = self.i w_dict = self.space.newdict() diff --git a/pypy/module/_fastjson/test/test__fastjson.py b/pypy/module/_fastjson/test/test__fastjson.py --- a/pypy/module/_fastjson/test/test__fastjson.py +++ b/pypy/module/_fastjson/test/test__fastjson.py @@ -69,6 +69,12 @@ s = r'"\u1234"' assert _fastjson.loads(s) == u'\u1234' +def test_decode_numeric(self): +import _fastjson +assert _fastjson.loads('42') == 42 +assert _fastjson.loads('-42') == -42 +raises(ValueError, "_fastjson.loads('42 abc')") + def test_decode_object(self): import _fastjson assert _fastjson.loads('{}') == {} ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy fastjson: add a fast path for decoding ascii-only, it gives ~10% speedup on certain benchmarks
Author: Antonio Cuni Branch: fastjson Changeset: r64790:73de5d85c1b3 Date: 2013-06-05 11:32 +0200 http://bitbucket.org/pypy/pypy/changeset/73de5d85c1b3/ Log:add a fast path for decoding ascii-only, it gives ~10% speedup on certain benchmarks diff --git a/pypy/module/_fastjson/interp_decoder.py b/pypy/module/_fastjson/interp_decoder.py --- a/pypy/module/_fastjson/interp_decoder.py +++ b/pypy/module/_fastjson/interp_decoder.py @@ -96,13 +96,20 @@ def decode_string(self): start = self.i +bits = 0 while not self.eof(): # this loop is a fast path for strings which do not contain escape # characters ch = self.next() +bits |= ord(ch) if ch == '"': content_utf8 = self.getslice(start, self.i-1) -content_unicode = unicodehelper.decode_utf8(self.space, content_utf8) +if bits & 0x80: +# the 8th bit is set, it's an utf8 strnig +content_unicode = content_utf8.decode('utf-8') +else: +# ascii only, faster to decode +content_unicode = content_utf8.decode('ascii') self.last_type = TYPE_STRING return self.space.wrap(content_unicode) elif ch == '\\': ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy default: Partial revert of 661d7f7624dc: don't let the JIT look inside rbigint.
Author: Armin Rigo Branch: Changeset: r64793:236f4d2c1567 Date: 2013-06-05 13:35 +0200 http://bitbucket.org/pypy/pypy/changeset/236f4d2c1567/ Log:Partial revert of 661d7f7624dc: don't let the JIT look inside rbigint. It causes issues. Instead, fix the test more directly by adding some @jit.elidable that were needed for consistency. diff --git a/pypy/module/pypyjit/policy.py b/pypy/module/pypyjit/policy.py --- a/pypy/module/pypyjit/policy.py +++ b/pypy/module/pypyjit/policy.py @@ -118,7 +118,7 @@ def look_inside_function(self, func): mod = func.__module__ or '?' -if mod == 'rpython.rlib.rlocale' or mod == 'rpython.rlib.rsocket': +if mod == 'rpython.rlib.rbigint' or mod == 'rpython.rlib.rlocale' or mod == 'rpython.rlib.rsocket': return False if mod.startswith('pypy.interpreter.astcompiler.'): return False diff --git a/pypy/module/pypyjit/test/test_policy.py b/pypy/module/pypyjit/test/test_policy.py --- a/pypy/module/pypyjit/test/test_policy.py +++ b/pypy/module/pypyjit/test/test_policy.py @@ -8,7 +8,12 @@ def test_bigint(): from rpython.rlib.rbigint import rbigint -assert pypypolicy.look_inside_function(rbigint.lt.im_func) +assert not pypypolicy.look_inside_function(rbigint.eq.im_func) +assert not pypypolicy.look_inside_function(rbigint.ne.im_func) +assert not pypypolicy.look_inside_function(rbigint.lt.im_func) +assert not pypypolicy.look_inside_function(rbigint.le.im_func) +assert not pypypolicy.look_inside_function(rbigint.gt.im_func) +assert not pypypolicy.look_inside_function(rbigint.ge.im_func) def test_rlocale(): from rpython.rlib.rlocale import setlocale diff --git a/rpython/rlib/rbigint.py b/rpython/rlib/rbigint.py --- a/rpython/rlib/rbigint.py +++ b/rpython/rlib/rbigint.py @@ -448,6 +448,7 @@ i += 1 return True +@jit.elidable def ne(self, other): return not self.eq(other) @@ -486,12 +487,15 @@ i -= 1 return False +@jit.elidable def le(self, other): return not other.lt(self) +@jit.elidable def gt(self, other): return other.lt(self) +@jit.elidable def ge(self, other): return not self.lt(other) ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy default: More @jit.elidable. The new test in test_misc is still not passing.
Author: Armin Rigo Branch: Changeset: r64794:e4d4c3e4eafa Date: 2013-06-05 14:57 +0200 http://bitbucket.org/pypy/pypy/changeset/e4d4c3e4eafa/ Log:More @jit.elidable. The new test in test_misc is still not passing. diff --git a/pypy/module/pypyjit/test_pypy_c/test_misc.py b/pypy/module/pypyjit/test_pypy_c/test_misc.py --- a/pypy/module/pypyjit/test_pypy_c/test_misc.py +++ b/pypy/module/pypyjit/test_pypy_c/test_misc.py @@ -407,5 +407,5 @@ log = self.run(main, [300]) loop, = log.loops_by_id("long_op") -assert log.match(""" +assert loop.match(""" """) diff --git a/rpython/rlib/jit.py b/rpython/rlib/jit.py --- a/rpython/rlib/jit.py +++ b/rpython/rlib/jit.py @@ -83,6 +83,13 @@ func._jit_look_inside_ = False return func +def look_inside(func): +""" Make sure the JIT traces inside decorated function, even +if the rest of the module is not visible to the JIT +""" +func._jit_look_inside_ = True +return func + def unroll_safe(func): """ JIT can safely unroll loops in this function and this will not lead to code explosion diff --git a/rpython/rlib/rbigint.py b/rpython/rlib/rbigint.py --- a/rpython/rlib/rbigint.py +++ b/rpython/rlib/rbigint.py @@ -190,9 +190,9 @@ @staticmethod +@jit.elidable def frombool(b): -# This function is marked as pure, so you must not call it and -# then modify the result. +# You must not call this function and then modify the result. if b: return ONERBIGINT return NULLRBIGINT @@ -251,6 +251,7 @@ return _decimalstr_to_bigint(s) @staticmethod +@jit.elidable def frombytes(s, byteorder, signed): if byteorder not in ('big', 'little'): raise InvalidEndiannessError() @@ -383,9 +384,11 @@ def tolonglong(self): return _AsLongLong(self) +@jit.look_inside def tobool(self): return self.sign != 0 +@jit.elidable def touint(self): if self.sign == -1: raise ValueError("cannot convert negative integer to unsigned int") @@ -410,13 +413,16 @@ raise ValueError("cannot convert negative integer to unsigned int") return _AsULonglong_ignore_sign(self) +@jit.elidable def uintmask(self): return _AsUInt_mask(self) +@jit.elidable def ulonglongmask(self): """Return r_ulonglong(self), truncating.""" return _AsULonglong_mask(self) +@jit.elidable def tofloat(self): return _AsDouble(self) @@ -448,7 +454,7 @@ i += 1 return True -@jit.elidable +@jit.look_inside def ne(self, other): return not self.eq(other) @@ -487,15 +493,15 @@ i -= 1 return False -@jit.elidable +@jit.look_inside def le(self, other): return not other.lt(self) -@jit.elidable +@jit.look_inside def gt(self, other): return other.lt(self) -@jit.elidable +@jit.look_inside def ge(self, other): return not self.lt(other) @@ -596,6 +602,7 @@ return div +@jit.look_inside def div(self, other): return self.floordiv(other) @@ -796,14 +803,17 @@ z = z.sub(c) return z +@jit.elidable def neg(self): return rbigint(self._digits, -self.sign, self.size) +@jit.elidable def abs(self): if self.sign != -1: return self return rbigint(self._digits, 1, self.size) +@jit.elidable def invert(self): #Implement ~x as -(x + 1) if self.sign == 0: return ONENEGATIVERBIGINT @@ -913,12 +923,14 @@ def or_(self, other): return _bitwise(self, '|', other) +@jit.elidable def oct(self): if self.sign == 0: return '0L' else: return _format(self, BASE8, '0', 'L') +@jit.elidable def hex(self): return _format(self, BASE16, '0x', 'L') ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy default: A test and fix for jit.look_inside.
Author: Armin Rigo Branch: Changeset: r64795:6ee99f717da5 Date: 2013-06-05 15:01 +0200 http://bitbucket.org/pypy/pypy/changeset/6ee99f717da5/ Log:A test and fix for jit.look_inside. diff --git a/rpython/jit/codewriter/policy.py b/rpython/jit/codewriter/policy.py --- a/rpython/jit/codewriter/policy.py +++ b/rpython/jit/codewriter/policy.py @@ -39,8 +39,6 @@ return True # look into everything by default def _reject_function(self, func): -if hasattr(func, '_jit_look_inside_'): -return not func._jit_look_inside_ # explicitly elidable functions are always opaque if getattr(func, '_elidable_function_', False): return True @@ -58,8 +56,11 @@ except AttributeError: see_function = True else: -see_function = (self.look_inside_function(func) and not -self._reject_function(func)) +if hasattr(func, '_jit_look_inside_'): +see_function = func._jit_look_inside_ # override guessing +else: +see_function = (self.look_inside_function(func) and not +self._reject_function(func)) contains_loop = contains_loop and not getattr( func, '_jit_unroll_safe_', False) diff --git a/rpython/jit/codewriter/test/test_policy.py b/rpython/jit/codewriter/test/test_policy.py --- a/rpython/jit/codewriter/test/test_policy.py +++ b/rpython/jit/codewriter/test/test_policy.py @@ -65,6 +65,20 @@ graph = support.getgraph(h, [5]) assert not JitPolicy().look_inside_graph(graph) +def test_look_inside(): +def h1(x): +return x + 1 +@jit.look_inside# force True, even if look_inside_function() thinks not +def h2(x): +return x + 2 +class MyPolicy(JitPolicy): +def look_inside_function(self, func): +return False +graph1 = support.getgraph(h1, [5]) +graph2 = support.getgraph(h2, [5]) +assert not MyPolicy().look_inside_graph(graph1) +assert MyPolicy().look_inside_graph(graph2) + def test_loops(): def g(x): i = 0 ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy fastjson: rpython fixes
Author: Antonio Cuni Branch: fastjson Changeset: r64796:6b66c9b61731 Date: 2013-06-05 15:05 +0200 http://bitbucket.org/pypy/pypy/changeset/6b66c9b61731/ Log:rpython fixes diff --git a/pypy/module/_fastjson/interp_decoder.py b/pypy/module/_fastjson/interp_decoder.py --- a/pypy/module/_fastjson/interp_decoder.py +++ b/pypy/module/_fastjson/interp_decoder.py @@ -1,3 +1,4 @@ +import math from rpython.rlib.rstring import StringBuilder from rpython.rlib.objectmodel import specialize from pypy.interpreter.error import OperationError, operationerrfmt @@ -9,13 +10,12 @@ # precomputing negative powers of 10 is MUCH faster than using e.g. math.pow # at runtime -NEG_POW_10 = [10**-i for i in range(16)] +NEG_POW_10 = [10.0**-i for i in range(16)] def neg_pow_10(x, exp): if exp >= len(NEG_POW_10): return 0.0 return x * NEG_POW_10[exp] - TYPE_UNKNOWN = 0 TYPE_STRING = 1 @@ -104,7 +104,7 @@ if is_float: # build the float floatval = intval + frcval -floatval = floatval * 10**exp +floatval = floatval * math.pow(10, exp) return self.space.wrap(floatval) else: return self.space.wrap(intval) @@ -236,6 +236,8 @@ uchr = unichr(int(hexdigits, 16)) except ValueError: self._raise("Invalid \u escape (char %d)", self.i-1) +return # help the annotator to know that we'll never go beyond + # this point # utf8_ch = unicodehelper.encode_utf8(self.space, uchr) builder.append(utf8_ch) ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] stmgc default: in-progress
Author: Armin Rigo Branch: Changeset: r64:87d10f56bb42 Date: 2013-06-05 12:53 +0200 http://bitbucket.org/pypy/stmgc/changeset/87d10f56bb42/ Log:in-progress diff --git a/.hgignore b/.hgignore new file mode 100644 --- /dev/null +++ b/.hgignore @@ -0,0 +1,3 @@ +syntax: glob +*.pyc +*~ diff --git a/c3/et.c b/c3/et.c --- a/c3/et.c +++ b/c3/et.c @@ -18,21 +18,18 @@ die if we start more than 0x7fff threads. */ static revision_t next_locked_value = (LOCKED + 1) | 1; -/* a negative odd number that uniquely identifies the currently running - transaction (but the number in aborted transactions is reused). - Because we don't know yet the value of 'global_cur_time' that we'll - be assigned when we commit, we use the (negative of) the value of - 'global_cur_time' when we committed the previous transaction. */ -__thread revision_t stm_local_revision; +/* a negative odd number that identifies the currently running + transaction within the thread. */ +__thread revision_t stm_private_rev_num; revision_t stm_global_cur_time(void) /* for tests */ { return global_cur_time; } -revision_t stm_local_rev(void)/* for tests */ +revision_t get_private_rev_num(void)/* for tests */ { - return stm_local_revision; + return stm_private_rev_num; } struct tx_descriptor *stm_thread_descriptor(void) /* for tests */ { @@ -70,6 +67,8 @@ static gcptr HeadOfRevisionChainList(struct tx_descriptor *d, gcptr G) { + abort(); +#if 0 gcptr R = G; revision_t v; @@ -135,10 +134,13 @@ goto retry; // restart searching from R } return R; +#endif } static inline gcptr AddInReadSet(struct tx_descriptor *d, gcptr R) { + abort(); +#if 0 fprintf(stderr, "AddInReadSet(%p)\n", R); d->count_reads++; if (!fxcache_add(&d->recent_reads_cache, R)) { @@ -153,10 +155,13 @@ // return Localize(d, R); // } return R; +#endif } gcptr stm_DirectReadBarrier(gcptr G) { + abort(); +#if 0 gcptr R; struct tx_descriptor *d = thread_descriptor; assert(d->active >= 1); @@ -174,19 +179,13 @@ G2L_FIND(d->public_to_private, R, entry, goto not_found); L = entry->val; assert(L->h_revision == stm_local_revision); -#if 0 - if (R_Container && !(R_Container->h_tid & GCFLAG_GLOBAL)) -{/* R_Container is a local object */ - gcptr *ref = (gcptr *)(((char *)R_Container) + offset); - *ref = L; /* fix in-place */ -} -#endif return L; not_found:; } R = AddInReadSet(d, R); return R; +#endif } static gcptr _latest_gcptr(gcptr R) @@ -312,6 +311,8 @@ static gcptr LocalizePublic(struct tx_descriptor *d, gcptr R) { + abort(); +#if 0 if (R->h_tid & GCFLAG_PUBLIC_TO_PRIVATE) { wlog_t *entry; @@ -332,6 +333,7 @@ AddInReadSet(d, R); /*mark*/ return L; +#endif } gcptr stm_WriteBarrier(gcptr P) @@ -376,6 +378,8 @@ static _Bool ValidateDuringTransaction(struct tx_descriptor *d, _Bool during_commit) { + abort(); +#if 0 long i, size = d->list_of_read_objects.size; gcptr *items = d->list_of_read_objects.items; @@ -416,6 +420,7 @@ } } return 1; +#endif } static void ValidateNow(struct tx_descriptor *d) @@ -638,8 +643,8 @@ goto retry; gcptr L = item->val; - assert(L->h_revision == stm_local_revision); - assert(v != stm_local_revision); + assert(L->h_revision == stm_private_rev_num); + assert(v != stm_private_rev_num); L->h_revision = v; /* store temporarily this value here */ } G2L_LOOP_END; @@ -647,6 +652,8 @@ static void CancelLocks(struct tx_descriptor *d) { + abort(); +#if 0 revision_t my_lock = d->my_lock; wlog_t *item; @@ -672,6 +679,7 @@ ACCESS_ONCE(R->h_revision) = v; } G2L_LOOP_END; +#endif } static pthread_mutex_t mutex_prebuilt_gcroots = PTHREAD_MUTEX_INITIALIZER; @@ -820,15 +828,15 @@ "*\n", (long)cur_time); - revision_t localrev = stm_local_revision; + revision_t localrev = stm_private_rev_num; UpdateProtectedChainHeads(d, cur_time, localrev); smp_wmb(); revision_t newrev = -(cur_time + 1); assert(newrev & 1); - ACCESS_ONCE(stm_local_revision) = newrev; + ACCESS_ONCE(stm_private_rev_num) = newrev; fprintf(stderr, "%p: stm_local_revision = %ld\n", d, (long)newrev); - assert(d->local_revision_ref = &stm_local_revision); + assert(d->private_revision_ref = &stm_private_rev_num); UpdateChainHeads(d, cur_time, localrev); @@ -1027,8 +1035,8 @@ } assert(d->my_lock & 1); assert(d->my_lock > LOCKED); - stm_local_revision = -d->my_lock; /* a unique negative odd value */ - d->local_revision_ref = &stm_local_revision; + stm_private_rev_num = -1; + d->private_revision_ref = &stm_private_rev_num; d->max_aborts = -1; thread_descriptor = d
[pypy-commit] stmgc default: in-progress
Author: Armin Rigo Branch: Changeset: r65:7526350df472 Date: 2013-06-05 15:57 +0200 http://bitbucket.org/pypy/stmgc/changeset/7526350df472/ Log:in-progress diff --git a/c3/et.c b/c3/et.c --- a/c3/et.c +++ b/c3/et.c @@ -286,27 +286,33 @@ #endif } -static gcptr LocalizeProtected(struct tx_descriptor *d, gcptr R) +static gcptr LocalizeProtected(struct tx_descriptor *d, gcptr P) { - assert(!(R->h_tid & GCFLAG_PUBLIC_TO_PRIVATE)); + gcptr B; - /* duplicate, and save the original R->h_revision into an extra - word allocated just after L */ - assert(R->h_revision & 1); - gcptr L = stmgc_duplicate(R, R->h_revision); + assert(P->h_revision != stm_private_rev_num); + assert(!(P->h_tid & GCFLAG_PUBLIC)); + assert(!(P->h_tid & GCFLAG_PUBLIC_TO_PRIVATE)); + assert(!(P->h_tid & GCFLAG_BACKUP_COPY)); + assert(!(P->h_tid & GCFLAG_STUB)); - /* cross-thread memory barrier: make sure the local object is correct - and has h_revision == stm_local_revision, and the extra word is - written as well; when it is done, and only then, then we change - R->h_revision */ - smp_wmb(); - - R->h_revision = (revision_t)L; - - gcptrlist_insert(&d->protected_with_private_copy, R); - AddInReadSet(d, R); - /*mark*/ - return L; + if (P->h_revision & 1) +{ + /* does not have a backup yet */ + B = stmgc_duplicate(P, 0); + B->h_tid |= GCFLAG_BACKUP_COPY; +} + else +{ + size_t size = stmcb_size(P); + B = (gcptr)P->h_revision; + assert(B->h_tid & GCFLAG_BACKUP_COPY); + memcpy(B + 1, P + 1, size - sizeof(*B)); +} + assert(B->h_tid & GCFLAG_BACKUP_COPY); + g2l_insert(&d->private_to_backup, P, B); + P->h_revision = stm_private_rev_num; + return P; } static gcptr LocalizePublic(struct tx_descriptor *d, gcptr R) @@ -338,35 +344,25 @@ gcptr stm_WriteBarrier(gcptr P) { - gcptr R, W; + gcptr W; struct tx_descriptor *d = thread_descriptor; assert(d->active >= 1); - /* must normalize the situation now, otherwise we risk that - LocalizePublic creates a new private version of a public - object that has got one, attached to the equivalent stolen - protected object */ - if (gcptrlist_size(&d->stolen_objects) > 0) -stmgc_normalize_stolen_objects(); - - /* XXX optimize me based on common patterns */ - R = HeadOfRevisionChainList(d, P); - - switch (stmgc_classify(R)) { - case K_PRIVATE: W = R; break; - case K_PROTECTED: W = LocalizeProtected(d, R); break; - case K_PUBLIC:W = LocalizePublic(d, R);break; - default: abort(); - } - - if (W->h_tid & GCFLAG_WRITE_BARRIER) -stmgc_write_barrier(W); + W = LocalizeProtected(d, P); fprintf(stderr, "write_barrier: %p -> %p\n", P, W); return W; } +gcptr stm_get_backup_copy(gcptr P) +{ + struct tx_descriptor *d = thread_descriptor; + wlog_t *entry; + G2L_FIND(d->private_to_backup, P, entry, return NULL); + return entry->val; +} + // static revision_t GetGlobalCurTime(struct tx_descriptor *d) @@ -527,6 +523,7 @@ } gcptrlist_clear(&d->list_of_read_objects); + g2l_clear(&d->private_to_backup); stmgc_abort_transaction(d); fprintf(stderr, @@ -590,6 +587,7 @@ d->start_real_time.tv_nsec = -1; } assert(d->list_of_read_objects.size == 0); + assert(!g2l_any_entry(&d->private_to_backup)); stmgc_start_transaction(d); d->count_reads = 1; @@ -775,6 +773,23 @@ } } +void TurnPrivateWithBackupToProtected(struct tx_descriptor *d, + revision_t cur_time) +{ + wlog_t *item; + G2L_LOOP_FORWARD(d->private_to_backup, item) +{ + gcptr P = item->addr; + gcptr B = item->val; + assert(P->h_revision == stm_private_rev_num); + assert(B->h_tid & GCFLAG_BACKUP_COPY); + B->h_revision = cur_time; + P->h_revision = (revision_t)B; + +} G2L_LOOP_END; + g2l_clear(&d->private_to_backup); +} + void CommitTransaction(void) { /* must save roots around this call */ revision_t cur_time; @@ -828,6 +843,8 @@ "*\n", (long)cur_time); + TurnPrivateWithBackupToProtected(d, cur_time); + revision_t localrev = stm_private_rev_num; UpdateProtectedChainHeads(d, cur_time, localrev); smp_wmb(); @@ -1057,6 +1074,7 @@ thread_descriptor = NULL; +g2l_delete(&d->private_to_backup); gcptrlist_delete(&d->list_of_read_objects); gcptrlist_delete(&d->abortinfo); free(d->longest_abort_info); diff --git a/c3/et.h b/c3/et.h --- a/c3/et.h +++ b/c3/et.h @@ -116,6 +116,7 @@ unsigned int num_spinloops[SPINLOOP_REASONS]; struct GcPtrList list_of_read_objects; struct GcPtrList abortinfo; + struct G2L private_to_backup; char *longest_abort_info; long long longest_abort_info_time; struct FXCache recent_reads_cache; @@ -175,6 +176,7 @@ gcptr stm_RepeatReadBarrier(gcptr); gcptr stm_WriteBarrier(gcptr
[pypy-commit] pypy default: Fix the test.
Author: Armin Rigo Branch: Changeset: r64797:cb46a58acf67 Date: 2013-06-05 16:06 +0200 http://bitbucket.org/pypy/pypy/changeset/cb46a58acf67/ Log:Fix the test. diff --git a/pypy/module/pypyjit/test_pypy_c/test_misc.py b/pypy/module/pypyjit/test_pypy_c/test_misc.py --- a/pypy/module/pypyjit/test_pypy_c/test_misc.py +++ b/pypy/module/pypyjit/test_pypy_c/test_misc.py @@ -407,5 +407,4 @@ log = self.run(main, [300]) loop, = log.loops_by_id("long_op") -assert loop.match(""" -""") +assert len(loop.ops_by_id("long_op")) == 0 ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] stmgc default: Add a passing test
Author: Armin Rigo Branch: Changeset: r66:48bc3f6660a8 Date: 2013-06-05 16:43 +0200 http://bitbucket.org/pypy/stmgc/changeset/48bc3f6660a8/ Log:Add a passing test diff --git a/c3/test/test_et.py b/c3/test/test_et.py --- a/c3/test/test_et.py +++ b/c3/test/test_et.py @@ -84,3 +84,24 @@ assert classify(p) == "protected" assert classify(pback) == "backup" assert ffi.cast("revision_t *", p.h_revision) == pback + +def test_protected_backup_reused(): +p = nalloc(HDR + WORD) +lib.setlong(p, 0, 78927812) +lib.stm_commit_transaction() +lib.stm_begin_inevitable_transaction() +lib.setlong(p, 0, 927122) +pback = lib.stm_get_backup_copy(p) +assert pback != p +lib.stm_commit_transaction() +lib.stm_begin_inevitable_transaction() +assert lib.stm_get_backup_copy(p) == ffi.NULL +assert classify(p) == "protected" +assert classify(pback) == "backup" +assert lib.rawgetlong(p, 0) == 927122 +assert lib.rawgetlong(pback, 0) == 78927812# but should not be used +lib.setlong(p, 0, 43891) +assert p.h_revision == lib.get_private_rev_num() +assert pback == lib.stm_get_backup_copy(p) +assert lib.rawgetlong(p, 0) == 43891 +assert lib.rawgetlong(pback, 0) == 927122 ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy fastjson: add two tests and the corresponding fixes
Author: Antonio Cuni Branch: fastjson Changeset: r64800:ca39af17b48f Date: 2013-06-05 15:56 +0200 http://bitbucket.org/pypy/pypy/changeset/ca39af17b48f/ Log:add two tests and the corresponding fixes diff --git a/pypy/module/_fastjson/interp_decoder.py b/pypy/module/_fastjson/interp_decoder.py --- a/pypy/module/_fastjson/interp_decoder.py +++ b/pypy/module/_fastjson/interp_decoder.py @@ -177,7 +177,9 @@ if self.last_type != TYPE_STRING: self._raise("Key name must be string for object starting at char %d", start) self.skip_whitespace() -ch = self.next() # XXX +if self.eof(): +break +ch = self.next() if ch != ':': self._raise("No ':' found at char %d", self.i) self.skip_whitespace() @@ -185,6 +187,8 @@ w_value = self.decode_any() self.space.setitem(w_dict, w_name, w_value) self.skip_whitespace() +if self.eof(): +break ch = self.next() if ch == '}': return w_dict diff --git a/pypy/module/_fastjson/test/test__fastjson.py b/pypy/module/_fastjson/test/test__fastjson.py --- a/pypy/module/_fastjson/test/test__fastjson.py +++ b/pypy/module/_fastjson/test/test__fastjson.py @@ -104,6 +104,8 @@ s = '{"hello": "world", "aaa": "bbb"}' assert _fastjson.loads(s) == {'hello': 'world', 'aaa': 'bbb'} +raises(ValueError, _fastjson.loads, '{"key"') +raises(ValueError, _fastjson.loads, '{"key": 42') def test_decode_object_nonstring_key(self): import _fastjson ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy fastjson: add a passing test:
Author: Antonio Cuni Branch: fastjson Changeset: r64798:649d62298da1 Date: 2013-06-05 15:37 +0200 http://bitbucket.org/pypy/pypy/changeset/649d62298da1/ Log:add a passing test: diff --git a/pypy/module/_fastjson/test/test__fastjson.py b/pypy/module/_fastjson/test/test__fastjson.py --- a/pypy/module/_fastjson/test/test__fastjson.py +++ b/pypy/module/_fastjson/test/test__fastjson.py @@ -106,5 +106,6 @@ 'aaa': 'bbb'} def test_decode_object_nonstring_key(self): -pass # write me when we have numbers - +import _fastjson +raises(ValueError, "_fastjson.loads('{42: 43}')") + ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy fastjson: raise the appropriate applevel exception if we get an invalid utf8
Author: Antonio Cuni Branch: fastjson Changeset: r64801:86bc837fcae3 Date: 2013-06-05 16:18 +0200 http://bitbucket.org/pypy/pypy/changeset/86bc837fcae3/ Log:raise the appropriate applevel exception if we get an invalid utf8 diff --git a/pypy/module/_fastjson/interp_decoder.py b/pypy/module/_fastjson/interp_decoder.py --- a/pypy/module/_fastjson/interp_decoder.py +++ b/pypy/module/_fastjson/interp_decoder.py @@ -213,7 +213,7 @@ content_utf8 = self.getslice(start, self.i-1) if bits & 0x80: # the 8th bit is set, it's an utf8 strnig -content_unicode = content_utf8.decode('utf-8') +content_unicode = unicodehelper.decode_utf8(self.space, content_utf8) else: # ascii only, faster to decode content_unicode = content_utf8.decode('ascii') diff --git a/pypy/module/_fastjson/test/test__fastjson.py b/pypy/module/_fastjson/test/test__fastjson.py --- a/pypy/module/_fastjson/test/test__fastjson.py +++ b/pypy/module/_fastjson/test/test__fastjson.py @@ -69,6 +69,12 @@ s = r'"\u1234"' assert _fastjson.loads(s) == u'\u1234' +def test_invalid_utf_8(self): +import _fastjson +s = '"\xe0"' # this is an invalid UTF8 sequence inside a string +raises(UnicodeDecodeError, "_fastjson.loads(s)") + + def test_decode_numeric(self): import _fastjson def check(s, val): ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy fastjson: decoding arrays
Author: Antonio Cuni Branch: fastjson Changeset: r64799:0fce473a480a Date: 2013-06-05 15:53 +0200 http://bitbucket.org/pypy/pypy/changeset/0fce473a480a/ Log:decoding arrays diff --git a/pypy/module/_fastjson/interp_decoder.py b/pypy/module/_fastjson/interp_decoder.py --- a/pypy/module/_fastjson/interp_decoder.py +++ b/pypy/module/_fastjson/interp_decoder.py @@ -72,6 +72,9 @@ return self.decode_string() elif ch.isdigit() or ch == '-': return self.decode_numeric() +elif ch == '[': +self.next() +return self.decode_array() elif ch == '{': self.next() return self.decode_object() @@ -134,6 +137,30 @@ self._raise("Expected digit at char %d", self.i) return intval, count +def decode_array(self): +start = self.i +w_list = self.space.newlist([]) +self.skip_whitespace() +while not self.eof(): +ch = self.peek() +if ch == ']': +self.next() +return w_list +w_item = self.decode_any() +self.space.call_method(w_list, 'append', w_item) +self.skip_whitespace() +if self.eof(): +break +ch = self.next() +if ch == ']': +return w_list +elif ch == ',': +pass +else: +self._raise("Unexpected '%s' when decoding array (char %d)", +ch, self.i) +self._raise("Unterminated array starting at char %d", start) + def decode_object(self): start = self.i @@ -150,7 +177,7 @@ if self.last_type != TYPE_STRING: self._raise("Key name must be string for object starting at char %d", start) self.skip_whitespace() -ch = self.next() +ch = self.next() # XXX if ch != ':': self._raise("No ':' found at char %d", self.i) self.skip_whitespace() diff --git a/pypy/module/_fastjson/test/test__fastjson.py b/pypy/module/_fastjson/test/test__fastjson.py --- a/pypy/module/_fastjson/test/test__fastjson.py +++ b/pypy/module/_fastjson/test/test__fastjson.py @@ -109,3 +109,11 @@ import _fastjson raises(ValueError, "_fastjson.loads('{42: 43}')") +def test_decode_array(self): +import _fastjson +assert _fastjson.loads('[]') == [] +assert _fastjson.loads('[ ]') == [] +assert _fastjson.loads('[1]') == [1] +assert _fastjson.loads('[1, 2]') == [1, 2] +raises(ValueError, "_fastjson.loads('[1: 2]')") +raises(ValueError, "_fastjson.loads('[1, 2')") ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy fastjson: parsing of null, true and false
Author: Antonio Cuni Branch: fastjson Changeset: r64802:5e34f815e7f7 Date: 2013-06-05 16:51 +0200 http://bitbucket.org/pypy/pypy/changeset/5e34f815e7f7/ Log:parsing of null, true and false diff --git a/pypy/module/_fastjson/interp_decoder.py b/pypy/module/_fastjson/interp_decoder.py --- a/pypy/module/_fastjson/interp_decoder.py +++ b/pypy/module/_fastjson/interp_decoder.py @@ -78,10 +78,47 @@ elif ch == '{': self.next() return self.decode_object() +elif ch == 'n': +self.next() +return self.decode_null() +elif ch == 't': +self.next() +return self.decode_true() +elif ch == 'f': +self.next() +return self.decode_false() else: self._raise("No JSON object could be decoded: unexpected '%s' at char %d", ch, self.i) +def decode_null(self): +N = len('ull') +if (self.i+N <= len(self.s) and +self.next() == 'u' and +self.next() == 'l' and +self.next() == 'l'): +return self.space.w_None +self._raise("Error when decoding null at char %d", self.i) + +def decode_true(self): +N = len('rue') +if (self.i+N <= len(self.s) and +self.next() == 'r' and +self.next() == 'u' and +self.next() == 'e'): +return self.space.w_True +self._raise("Error when decoding true at char %d", self.i) + +def decode_false(self): +N = len('alse') +if (self.i+N <= len(self.s) and +self.next() == 'a' and +self.next() == 'l' and +self.next() == 's' and +self.next() == 'e'): +return self.space.w_False +self._raise("Error when decoding false at char %d", self.i) + def decode_numeric(self): intval = self.parse_integer() # diff --git a/pypy/module/_fastjson/test/test__fastjson.py b/pypy/module/_fastjson/test/test__fastjson.py --- a/pypy/module/_fastjson/test/test__fastjson.py +++ b/pypy/module/_fastjson/test/test__fastjson.py @@ -19,6 +19,28 @@ class AppTest(object): spaceconfig = {"objspace.usemodules._fastjson": True} +def test_decode_constants(self): +import _fastjson +assert _fastjson.loads('null') is None +raises(ValueError, _fastjson.loads, 'nul') +raises(ValueError, _fastjson.loads, 'nu') +raises(ValueError, _fastjson.loads, 'n') +raises(ValueError, _fastjson.loads, 'nuXX') +# +assert _fastjson.loads('true') is True +raises(ValueError, _fastjson.loads, 'tru') +raises(ValueError, _fastjson.loads, 'tr') +raises(ValueError, _fastjson.loads, 't') +raises(ValueError, _fastjson.loads, 'trXX') +# +assert _fastjson.loads('false') is False +raises(ValueError, _fastjson.loads, 'fals') +raises(ValueError, _fastjson.loads, 'fal') +raises(ValueError, _fastjson.loads, 'fa') +raises(ValueError, _fastjson.loads, 'f') +raises(ValueError, _fastjson.loads, 'falXX') + + def test_decode_string(self): import _fastjson res = _fastjson.loads('"hello"') ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] stmgc default: public->private
Author: Armin Rigo Branch: Changeset: r68:2f624ecb97a7 Date: 2013-06-05 16:55 +0200 http://bitbucket.org/pypy/stmgc/changeset/2f624ecb97a7/ Log:public->private diff --git a/c3/et.c b/c3/et.c --- a/c3/et.c +++ b/c3/et.c @@ -317,29 +317,32 @@ static gcptr LocalizePublic(struct tx_descriptor *d, gcptr R) { - abort(); -#if 0 if (R->h_tid & GCFLAG_PUBLIC_TO_PRIVATE) { wlog_t *entry; gcptr L; G2L_FIND(d->public_to_private, R, entry, goto not_found); L = entry->val; - assert(L->h_revision == stm_local_revision); + assert(L->h_revision == stm_private_rev_num); /* private object */ return L; } - else -R->h_tid |= GCFLAG_PUBLIC_TO_PRIVATE; + R->h_tid |= GCFLAG_PUBLIC_TO_PRIVATE; not_found:; gcptr L = stmgc_duplicate(R, 0); - assert(L->h_revision == stm_local_revision); + assert(!(L->h_tid & GCFLAG_BACKUP_COPY)); + assert(!(L->h_tid & GCFLAG_STOLEN)); + assert(!(L->h_tid & GCFLAG_STUB)); + L->h_tid &= ~(GCFLAG_OLD | +GCFLAG_VISITED | +GCFLAG_PUBLIC| +GCFLAG_PREBUILT_ORIGINAL | +GCFLAG_PUBLIC_TO_PRIVATE | +GCFLAG_WRITE_BARRIER | +0); + L->h_revision = stm_private_rev_num; g2l_insert(&d->public_to_private, R, L); - gcptrlist_insert(&d->public_to_young, R); - AddInReadSet(d, R); - /*mark*/ return L; -#endif } gcptr stm_WriteBarrier(gcptr P) @@ -348,7 +351,12 @@ struct tx_descriptor *d = thread_descriptor; assert(d->active >= 1); - W = LocalizeProtected(d, P); + /*P = stm_DirectReadBarrier(P);*/ + + if (P->h_tid & GCFLAG_PUBLIC) +W = LocalizePublic(d, P); + else +W = LocalizeProtected(d, P); fprintf(stderr, "write_barrier: %p -> %p\n", P, W); diff --git a/c3/test/test_et.py b/c3/test/test_et.py --- a/c3/test/test_et.py +++ b/c3/test/test_et.py @@ -114,3 +114,15 @@ GCFLAG_PUBLIC | GCFLAG_PREBUILT_ORIGINAL) assert classify(p) == "public" + +def test_change_prebuilt_object(): +p = palloc(HDR + WORD) +lib.rawsetlong(p, 0, 28971289) +flags = p.h_tid +assert (flags & GCFLAG_PUBLIC_TO_PRIVATE) == 0 +assert classify(p) == "public" +p2 = lib.stm_write_barrier(p) +assert p2 != p +assert classify(p) == "public" +assert classify(p2) == "private" +assert p.h_tid == flags | GCFLAG_PUBLIC_TO_PRIVATE ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] stmgc default: Next test
Author: Armin Rigo Branch: Changeset: r67:baa39610ff9b Date: 2013-06-05 16:47 +0200 http://bitbucket.org/pypy/stmgc/changeset/baa39610ff9b/ Log:Next test diff --git a/c3/doc-objects.txt b/c3/doc-objects.txt --- a/c3/doc-objects.txt +++ b/c3/doc-objects.txt @@ -50,7 +50,7 @@ - original obj after GC killed the backup GT Public objects: -- prebuilt object, never modified -1 +- prebuilt object, never modified 1 - other public object, never modified GT - outdated, has a protected copy HANDLE to prot/priv copy - outdated, target stolen ptr to a more recent public copy diff --git a/c3/test/support.py b/c3/test/support.py --- a/c3/test/support.py +++ b/c3/test/support.py @@ -436,6 +436,7 @@ def palloc(size): "Get a ``prebuilt'' object." p = lib.pseudoprebuilt(size, 42 + size) +assert p.h_revision == 1 return p def palloc_refs(nrefs): diff --git a/c3/test/test_et.py b/c3/test/test_et.py --- a/c3/test/test_et.py +++ b/c3/test/test_et.py @@ -105,3 +105,12 @@ assert pback == lib.stm_get_backup_copy(p) assert lib.rawgetlong(p, 0) == 43891 assert lib.rawgetlong(pback, 0) == 927122 + +def test_prebuilt_is_public(): +p = palloc(HDR) +assert p.h_revision == 1 +assert p.h_tid == lib.gettid(p) | (GCFLAG_OLD | + GCFLAG_VISITED | + GCFLAG_PUBLIC | + GCFLAG_PREBUILT_ORIGINAL) +assert classify(p) == "public" ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] stmgc default: This test passes, but probably only because it's simple enough.
Author: Armin Rigo Branch: Changeset: r69:a31993e9805a Date: 2013-06-05 16:59 +0200 http://bitbucket.org/pypy/stmgc/changeset/a31993e9805a/ Log:This test passes, but probably only because it's simple enough. diff --git a/c3/test/test_et.py b/c3/test/test_et.py --- a/c3/test/test_et.py +++ b/c3/test/test_et.py @@ -115,9 +115,8 @@ GCFLAG_PREBUILT_ORIGINAL) assert classify(p) == "public" -def test_change_prebuilt_object(): -p = palloc(HDR + WORD) -lib.rawsetlong(p, 0, 28971289) +def test_prebuilt_object_to_private(): +p = palloc(HDR) flags = p.h_tid assert (flags & GCFLAG_PUBLIC_TO_PRIVATE) == 0 assert classify(p) == "public" @@ -126,3 +125,17 @@ assert classify(p) == "public" assert classify(p2) == "private" assert p.h_tid == flags | GCFLAG_PUBLIC_TO_PRIVATE + +def test_commit_change_to_prebuilt_object(): +p = palloc(HDR + WORD) +lib.rawsetlong(p, 0, 28971289) +p2 = lib.stm_write_barrier(p) +assert p2 != p +assert classify(p) == "public" +assert classify(p2) == "private" +lib.rawsetlong(p, 0, 1289222) +lib.stm_commit_transaction() +lib.stm_begin_inevitable_transaction() +assert classify(p) == "public" +assert classify(p2) == "protected" +assert p.h_revision == int(ffi.cast("revision_t", p2)) + 2 ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] stmgc default: Fixes
Author: Armin Rigo Branch: Changeset: r70:5c86454b6e59 Date: 2013-06-05 17:44 +0200 http://bitbucket.org/pypy/stmgc/changeset/5c86454b6e59/ Log:Fixes diff --git a/c3/et.c b/c3/et.c --- a/c3/et.c +++ b/c3/et.c @@ -716,15 +716,6 @@ #endif L->h_revision = new_revision; - if (is_young(L)) -{ - item->val = (gcptr)(((revision_t)L) | 2); -#ifdef DUMP_EXTRA - fprintf(stderr, "PUBLIC-TO-PROTECTED:\n"); - /*mark*/ -#endif -} - } G2L_LOOP_END; smp_wmb(); /* a memory barrier: make sure the new L->h_revisions are visible @@ -742,11 +733,12 @@ assert(R->h_revision != localrev); #ifdef DUMP_EXTRA - fprintf(stderr, "%p->h_revision = %p (UpdateChainHeads2)\n", + fprintf(stderr, "%p->h_revision = %p | 2 (UpdateChainHeads2)\n", R, (gcptr)v); /*mark*/ #endif - ACCESS_ONCE(R->h_revision) = v; + assert(!(v & 3)); + ACCESS_ONCE(R->h_revision) = v | 2; if (R->h_tid & GCFLAG_PREBUILT_ORIGINAL) { diff --git a/c3/test/test_et.py b/c3/test/test_et.py --- a/c3/test/test_et.py +++ b/c3/test/test_et.py @@ -133,9 +133,11 @@ assert p2 != p assert classify(p) == "public" assert classify(p2) == "private" -lib.rawsetlong(p, 0, 1289222) +lib.rawsetlong(p2, 0, 1289222) lib.stm_commit_transaction() lib.stm_begin_inevitable_transaction() assert classify(p) == "public" assert classify(p2) == "protected" assert p.h_revision == int(ffi.cast("revision_t", p2)) + 2 +assert lib.rawgetlong(p, 0) == 28971289 +assert lib.rawgetlong(p2, 0) == 1289222 ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] stmgc default: Read barrier on public objects
Author: Armin Rigo Branch: Changeset: r72:b9dfe1e2b66e Date: 2013-06-05 18:22 +0200 http://bitbucket.org/pypy/stmgc/changeset/b9dfe1e2b66e/ Log:Read barrier on public objects diff --git a/c3/et.c b/c3/et.c --- a/c3/et.c +++ b/c3/et.c @@ -65,78 +65,6 @@ // -static gcptr HeadOfRevisionChainList(struct tx_descriptor *d, gcptr G) -{ - abort(); -#if 0 - gcptr R = G; - revision_t v; - - retry: - v = ACCESS_ONCE(R->h_revision); - if (!(v & 1)) // "is a pointer", i.e. -{// "has a more recent revision" - if (v & 2) -{ -old_to_young: - v &= ~2; - if (UNLIKELY(!stmgc_is_young_in(d, (gcptr)v))) -{ - stmgc_public_to_foreign_protected(R); - goto retry; -} - R = (gcptr)v; - goto retry; -} - - gcptr R_prev = R; - R = (gcptr)v; - -retry_threelevels: - v = ACCESS_ONCE(R->h_revision); - if (!(v & 1)) // "is a pointer", i.e. -{// "has a more recent revision" - if (v & 2) -goto old_to_young; - - /* we update R_prev->h_revision as a shortcut */ - /* XXX check if this really gives a worse performance than only - doing this write occasionally based on a counter in d */ - gcptr R_next = (gcptr)v; - if (R_next->h_revision == stm_local_revision) -{ - /* must not update an older h_revision to go directly to - the private copy at the end of a chain of protected - objects! */ - return R_next; -} - if (R_prev->h_tid & GCFLAG_STOLEN) -{ - /* must not update the h_revision of a stolen object! */ - R_prev = R; - R = R_next; - goto retry_threelevels; -} - R_prev->h_revision = v; - R = R_next; - goto retry; -} -} - - if (UNLIKELY(v > d->start_time)) // object too recent? -{ - if (v >= LOCKED) -{ - SpinLoop(SPLP_LOCKED_INFLIGHT); - goto retry;// spinloop until it is no longer LOCKED -} - ValidateNow(d); // try to move start_time forward - goto retry; // restart searching from R -} - return R; -#endif -} - #if 0 static inline gcptr AddInReadSet(struct tx_descriptor *d, gcptr R) { @@ -163,12 +91,57 @@ if (P->h_tid & GCFLAG_PUBLIC) { - abort(); - /*...*/ + /* follow the chained list of h_revision's as long as they are + regular pointers */ + revision_t v; + +retry: + v = ACCESS_ONCE(P->h_revision); + if (!(v & 1)) // "is a pointer", i.e. +{// "has a more recent revision" + if (v & 2) +{ +old_to_young: + abort(); +} + assert(P->h_tid & GCFLAG_PUBLIC); + + gcptr P_prev = P; + P = (gcptr)v; + + /* if we land on a P in read_barrier_cache: just return it */ + if (FXCACHE_AT(P) == P) +return P; + + v = ACCESS_ONCE(P->h_revision); + if (!(v & 1)) // "is a pointer", i.e. +{// "has a more recent revision" + if (v & 2) +goto old_to_young; + assert(P->h_tid & GCFLAG_PUBLIC); + + /* we update P_prev->h_revision as a shortcut */ + /* XXX check if this really gives a worse performance than only + doing this write occasionally based on a counter in d */ + P_prev->h_revision = v; + P = (gcptr)v; + goto retry; +} +} + + if (UNLIKELY(v > d->start_time)) // object too recent? +{ + if (v >= LOCKED) +{ + SpinLoop(SPLP_LOCKED_INFLIGHT); + goto retry; // spinloop until it is no longer LOCKED +} + ValidateNow(d); // try to move start_time forward + goto retry; // restart searching from P +} } - + fxcache_add(&d->recent_reads_cache, P); gcptrlist_insert(&d->list_of_read_objects, P); - fxcache_add(&d->recent_reads_cache, P); return P; } diff --git a/c3/test/test_et.py b/c3/test/test_et.py --- a/c3/test/test_et.py +++ b/c3/test/test_et.py @@ -156,3 +156,25 @@ assert list_of_read_objects() == [] assert lib.stm_read_barrier(p) == p # record as a read object assert list_of_read_objects() == [p] + +def test_read_barrier_public(): +p = palloc(HDR) +assert lib.stm_read_barrier(p) == p +assert list_of_read_objects() == [p] + +def test_read_barrier_public_outdated(): +p1 = palloc(HDR) +p2 = palloc(HDR) +p1.h_revision = ffi.cast("revision_t", p2) +asse
[pypy-commit] stmgc default: Starting on the read barrier.
Author: Armin Rigo Branch: Changeset: r71:27f0605ccd79 Date: 2013-06-05 18:08 +0200 http://bitbucket.org/pypy/stmgc/changeset/27f0605ccd79/ Log:Starting on the read barrier. diff --git a/c3/et.c b/c3/et.c --- a/c3/et.c +++ b/c3/et.c @@ -137,10 +137,9 @@ #endif } +#if 0 static inline gcptr AddInReadSet(struct tx_descriptor *d, gcptr R) { - abort(); -#if 0 fprintf(stderr, "AddInReadSet(%p)\n", R); d->count_reads++; if (!fxcache_add(&d->recent_reads_cache, R)) { @@ -155,37 +154,22 @@ // return Localize(d, R); // } return R; +} #endif -} -gcptr stm_DirectReadBarrier(gcptr G) +gcptr stm_DirectReadBarrier(gcptr P) { - abort(); -#if 0 - gcptr R; struct tx_descriptor *d = thread_descriptor; - assert(d->active >= 1); - /* XXX optimize me based on common patterns */ - R = HeadOfRevisionChainList(d, G); + if (P->h_tid & GCFLAG_PUBLIC) +{ + abort(); + /*...*/ +} - if (R->h_tid & GCFLAG_PUBLIC_TO_PRIVATE) -{ - if (gcptrlist_size(&d->stolen_objects) > 0) -stmgc_normalize_stolen_objects(); - - wlog_t *entry; - gcptr L; - G2L_FIND(d->public_to_private, R, entry, goto not_found); - L = entry->val; - assert(L->h_revision == stm_local_revision); - return L; - -not_found:; -} - R = AddInReadSet(d, R); - return R; -#endif + gcptrlist_insert(&d->list_of_read_objects, P); + fxcache_add(&d->recent_reads_cache, P); + return P; } static gcptr _latest_gcptr(gcptr R) @@ -371,6 +355,14 @@ return entry->val; } +gcptr stm_get_read_obj(long index) +{ + struct tx_descriptor *d = thread_descriptor; + if (index < gcptrlist_size(&d->list_of_read_objects)) +return d->list_of_read_objects.items[index]; + return NULL; +} + // static revision_t GetGlobalCurTime(struct tx_descriptor *d) diff --git a/c3/et.h b/c3/et.h --- a/c3/et.h +++ b/c3/et.h @@ -177,6 +177,7 @@ gcptr stm_WriteBarrier(gcptr); gcptr _stm_nonrecord_barrier(gcptr, int *); gcptr stm_get_backup_copy(gcptr); +gcptr stm_get_read_obj(long); /* debugging */ int DescriptorInit(void); void DescriptorDone(void); diff --git a/c3/lists.c b/c3/lists.c --- a/c3/lists.c +++ b/c3/lists.c @@ -223,6 +223,8 @@ // +__thread char *stm_read_barrier_cache; + void _fxcache_reset(struct FXCache *fxcache) { fxcache->shift = 0; diff --git a/c3/lists.h b/c3/lists.h --- a/c3/lists.h +++ b/c3/lists.h @@ -178,15 +178,17 @@ more. */ -#define FX_ENTRIES 8192 -#define FX_TOTAL (FX_ENTRIES * 2) +#define FX_MASK 65535 +#define FX_ENTRIES ((FX_MASK + 1) / sizeof(char *)) +#define FX_TOTAL (FX_ENTRIES * 4 / 3) struct FXCache { -char *cache_start; revision_t shift; revision_t cache[FX_TOTAL]; }; +extern __thread char *stm_read_barrier_cache; + void _fxcache_reset(struct FXCache *fxcache); static inline void fxcache_clear(struct FXCache *fxcache) @@ -194,7 +196,16 @@ fxcache->shift++; if (fxcache->shift > FX_TOTAL - FX_ENTRIES) _fxcache_reset(fxcache); -fxcache->cache_start = (char *)(fxcache->cache + fxcache->shift); +stm_read_barrier_cache = (char *)(fxcache->cache + fxcache->shift); +} + +#define FXCACHE_AT(obj) \ +(*(gcptr *)(stm_read_barrier_cache + ((revision_t)(obj) & FX_MASK))) + +static inline void fxcache_add(struct FXCache *fxcache, gcptr newobj) +{ +assert(stm_read_barrier_cache == (char*)(fxcache->cache + fxcache->shift)); +FXCACHE_AT(newobj) = newobj; } // diff --git a/c3/stmsync.c b/c3/stmsync.c --- a/c3/stmsync.c +++ b/c3/stmsync.c @@ -77,12 +77,10 @@ gcptr stm_read_barrier(gcptr obj) { -/* XXX inline in the caller */ -abort(); -#if 0 -if (UNLIKELY(obj->h_revision != stm_local_revision)) +/* XXX inline in the caller, optimize to get the smallest code */ +if (UNLIKELY((obj->h_revision != stm_private_rev_num) && + (FXCACHE_AT(obj) != obj))) obj = stm_DirectReadBarrier(obj); -#endif return obj; } diff --git a/c3/test/support.py b/c3/test/support.py --- a/c3/test/support.py +++ b/c3/test/support.py @@ -69,6 +69,7 @@ void stm_stop_sharedlock(void); void AbortTransaction(int); gcptr stm_get_backup_copy(gcptr); +gcptr stm_get_read_obj(long index); gcptr getptr(gcptr, long); void setptr(gcptr, long, gcptr); @@ -528,3 +529,14 @@ return "backup" else: return "protected" + +def list_of_read_objects(): +result = [] +index = 0 +while 1: +p = lib.stm_get_read_obj(index) +if p == ffi.NULL: +break +result.append(p) +index += 1 +return result diff --git a/c3/test/test_et.py b/c3/test/test_et.py --- a/c3/test/test_et.py +++ b/c3/test/test_et.py @@ -141,3 +141,18 @@ assert p.h_revision == int(ffi.cast(
[pypy-commit] pypy numpypy-nditer: Make the test less specific
Author: Romain Guillebert Branch: numpypy-nditer Changeset: r64803:1be2efa62157 Date: 2013-06-05 18:29 +0200 http://bitbucket.org/pypy/pypy/changeset/1be2efa62157/ Log:Make the test less specific diff --git a/pypy/module/micronumpy/test/test_nditer.py b/pypy/module/micronumpy/test/test_nditer.py --- a/pypy/module/micronumpy/test/test_nditer.py +++ b/pypy/module/micronumpy/test/test_nditer.py @@ -44,21 +44,21 @@ def test_external_loop(self): from numpypy import arange, nditer, array -a = arange(6).reshape(2,3) +a = arange(12).reshape(2,3,2) r = [] n = 0 for x in nditer(a, flags=['external_loop']): r.append(x) n += 1 assert n == 1 -assert (array(r) == [0, 1, 2, 3, 4, 5]).all() +assert (array(r) == [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11]).all() r = [] n = 0 for x in nditer(a, flags=['external_loop'], order='F'): r.append(x) n += 1 assert n == 3 -assert (array(r) == [[0, 3], [1, 4], [2, 5]]).all() +assert (array(r) == [[0, 6], [2, 8], [4, 10], [1, 7], [3, 9], [5, 11]]).all() def test_interface(self): from numpypy import arange, nditer, zeros ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] stmgc default: Next test.
Author: Armin Rigo Branch: Changeset: r73:e3da2bafef96 Date: 2013-06-05 18:44 +0200 http://bitbucket.org/pypy/stmgc/changeset/e3da2bafef96/ Log:Next test. diff --git a/c3/et.c b/c3/et.c --- a/c3/et.c +++ b/c3/et.c @@ -129,6 +129,18 @@ } } + if (P->h_tid & GCFLAG_PUBLIC_TO_PRIVATE) +{ + wlog_t *item; + G2L_FIND(d->public_to_private, P, item, goto no_private_obj); + + P = item->val; + assert(!(P->h_tid & GCFLAG_PUBLIC)); + assert(P->h_revision == stm_private_rev_num); + return P; +} +no_private_obj: + if (UNLIKELY(v > d->start_time)) // object too recent? { if (v >= LOCKED) @@ -299,6 +311,13 @@ 0); L->h_revision = stm_private_rev_num; g2l_insert(&d->public_to_private, R, L); + fprintf(stderr, "write_barrier: adding %p -> %p to public_to_private\n", + R, L); + + /* must remove R from the read_barrier_cache, because returning R is no + longer a valid result */ + fxcache_remove(&d->recent_reads_cache, R); + return L; } @@ -308,7 +327,7 @@ struct tx_descriptor *d = thread_descriptor; assert(d->active >= 1); - /*P = stm_DirectReadBarrier(P);*/ + P = stm_read_barrier(P); if (P->h_tid & GCFLAG_PUBLIC) W = LocalizePublic(d, P); diff --git a/c3/lists.h b/c3/lists.h --- a/c3/lists.h +++ b/c3/lists.h @@ -208,6 +208,12 @@ FXCACHE_AT(newobj) = newobj; } +static inline void fxcache_remove(struct FXCache *fxcache, gcptr oldobj) +{ +assert(stm_read_barrier_cache == (char*)(fxcache->cache + fxcache->shift)); +FXCACHE_AT(oldobj) = NULL; +} + // #endif diff --git a/c3/test/test_et.py b/c3/test/test_et.py --- a/c3/test/test_et.py +++ b/c3/test/test_et.py @@ -178,3 +178,16 @@ assert lib.stm_read_barrier(p1) == p3 assert list_of_read_objects() == [p3] assert p1.h_revision == int(ffi.cast("revision_t", p3)) # shortcutted + +def test_read_barrier_public_to_private(): +p = palloc(HDR) +p2 = lib.stm_write_barrier(p) +assert p2 != p +assert classify(p) == "public" +assert classify(p2) == "private" +assert list_of_read_objects() == [p] +assert p.h_tid & GCFLAG_PUBLIC +assert p.h_tid & GCFLAG_PUBLIC_TO_PRIVATE +p3 = lib.stm_read_barrier(p) +assert p3 == p2 +assert list_of_read_objects() == [p] ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] stmgc default: Add some more debugging prints
Author: Armin Rigo Branch: Changeset: r74:3a3dfae01632 Date: 2013-06-05 18:48 +0200 http://bitbucket.org/pypy/stmgc/changeset/3a3dfae01632/ Log:Add some more debugging prints diff --git a/c3/et.c b/c3/et.c --- a/c3/et.c +++ b/c3/et.c @@ -85,9 +85,10 @@ } #endif -gcptr stm_DirectReadBarrier(gcptr P) +gcptr stm_DirectReadBarrier(gcptr G) { struct tx_descriptor *d = thread_descriptor; + gcptr P = G; if (P->h_tid & GCFLAG_PUBLIC) { @@ -111,7 +112,10 @@ /* if we land on a P in read_barrier_cache: just return it */ if (FXCACHE_AT(P) == P) -return P; +{ + fprintf(stderr, "read_barrier: %p -> %p fxcache\n", G, P); + return P; +} v = ACCESS_ONCE(P->h_revision); if (!(v & 1)) // "is a pointer", i.e. @@ -137,6 +141,7 @@ P = item->val; assert(!(P->h_tid & GCFLAG_PUBLIC)); assert(P->h_revision == stm_private_rev_num); + fprintf(stderr, "read_barrier: %p -> %p public_to_private\n", G, P); return P; } no_private_obj: @@ -151,6 +156,11 @@ ValidateNow(d); // try to move start_time forward goto retry; // restart searching from P } + fprintf(stderr, "read_barrier: %p -> %p public\n", G, P); +} + else +{ + fprintf(stderr, "read_barrier: %p -> %p protected\n", G, P); } fxcache_add(&d->recent_reads_cache, P); gcptrlist_insert(&d->list_of_read_objects, P); ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] stmgc default: Introduce "handles" as written down in doc-objects.txt
Author: Armin Rigo Branch: Changeset: r75:d8c52869d637 Date: 2013-06-05 20:48 +0200 http://bitbucket.org/pypy/stmgc/changeset/d8c52869d637/ Log:Introduce "handles" as written down in doc-objects.txt diff --git a/c3/et.c b/c3/et.c --- a/c3/et.c +++ b/c3/et.c @@ -296,6 +296,7 @@ static gcptr LocalizePublic(struct tx_descriptor *d, gcptr R) { + assert(R->h_tid & GCFLAG_PUBLIC); if (R->h_tid & GCFLAG_PUBLIC_TO_PRIVATE) { wlog_t *entry; @@ -726,13 +727,22 @@ assert(!is_young(R)); assert(R->h_revision != localrev); + /* XXX compactify and don't leak! */ + revision_t *handle_block = stm_malloc(3 * WORD); + handle_block = (revision_t *) +intptr_t)handle_block) + HANDLE_BLOCK_SIZE-1) + & ~(HANDLE_BLOCK_SIZE-1)); + handle_block[0] = d->my_lock; + handle_block[1] = v; + + revision_t w = ((revision_t)(handle_block + 1)) + 2; + #ifdef DUMP_EXTRA - fprintf(stderr, "%p->h_revision = %p | 2 (UpdateChainHeads2)\n", - R, (gcptr)v); + fprintf(stderr, "%p->h_revision = %p (UpdateChainHeads2)\n", + R, (gcptr)w); /*mark*/ #endif - assert(!(v & 3)); - ACCESS_ONCE(R->h_revision) = v | 2; + ACCESS_ONCE(R->h_revision) = w; if (R->h_tid & GCFLAG_PREBUILT_ORIGINAL) { diff --git a/c3/et.h b/c3/et.h --- a/c3/et.h +++ b/c3/et.h @@ -13,6 +13,8 @@ #define LOCKED ((INTPTR_MAX - 0x) | 1) +#define HANDLE_BLOCK_SIZE (2 * WORD) + /* Description of the flags * * diff --git a/c3/test/support.py b/c3/test/support.py --- a/c3/test/support.py +++ b/c3/test/support.py @@ -84,6 +84,7 @@ gcptr pseudoprebuilt(size_t size, int tid); revision_t get_private_rev_num(void); revision_t get_start_time(void); +revision_t get_my_lock(void); gcptr *addr_of_thread_local(void); int in_nursery(gcptr); @@ -92,6 +93,8 @@ /* some constants normally private that are useful in the tests */ #define WORD ... #define GC_PAGE_SIZE ... +#define LOCKED ... +#define HANDLE_BLOCK_SIZE... #define GCFLAG_OLD ... #define GCFLAG_VISITED ... #define GCFLAG_PUBLIC... @@ -118,6 +121,7 @@ extern void stmgcpage_add_prebuilt_root(gcptr); extern void stm_clear_between_tests(void); extern revision_t get_private_rev_num(void); +extern local_gcpages_t *stm_local_gcpages(void); int gettid(gcptr obj) { @@ -205,6 +209,11 @@ return thread_descriptor->start_time; } +revision_t get_my_lock(void) +{ +return thread_descriptor->my_lock; +} + gcptr *addr_of_thread_local(void) { return &stm_thread_local_obj; @@ -540,3 +549,11 @@ result.append(p) index += 1 return result + +def decode_handle(r): +assert (r & 3) == 2 +p = r & ~(lib.HANDLE_BLOCK_SIZE-1) +my_lock = ffi.cast("revision_t *", p)[0] +assert my_lock >= lib.LOCKED +ptr = ffi.cast("gcptr *", r - 2)[0] +return ptr, my_lock diff --git a/c3/test/test_et.py b/c3/test/test_et.py --- a/c3/test/test_et.py +++ b/c3/test/test_et.py @@ -138,7 +138,7 @@ lib.stm_begin_inevitable_transaction() assert classify(p) == "public" assert classify(p2) == "protected" -assert p.h_revision == int(ffi.cast("revision_t", p2)) + 2 +assert decode_handle(p.h_revision) == (p2, lib.get_my_lock()) assert lib.rawgetlong(p, 0) == 28971289 assert lib.rawgetlong(p2, 0) == 1289222 ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] stmgc default: Read barriers through handle objects.
Author: Armin Rigo Branch: Changeset: r76:69fa4d0304c6 Date: 2013-06-05 21:03 +0200 http://bitbucket.org/pypy/stmgc/changeset/69fa4d0304c6/ Log:Read barriers through handle objects. diff --git a/c3/et.c b/c3/et.c --- a/c3/et.c +++ b/c3/et.c @@ -89,22 +89,18 @@ { struct tx_descriptor *d = thread_descriptor; gcptr P = G; + revision_t v; if (P->h_tid & GCFLAG_PUBLIC) { /* follow the chained list of h_revision's as long as they are regular pointers */ - revision_t v; - retry: v = ACCESS_ONCE(P->h_revision); if (!(v & 1)) // "is a pointer", i.e. {// "has a more recent revision" if (v & 2) -{ -old_to_young: - abort(); -} +goto old_to_young; assert(P->h_tid & GCFLAG_PUBLIC); gcptr P_prev = P; @@ -162,9 +158,42 @@ { fprintf(stderr, "read_barrier: %p -> %p protected\n", G, P); } + + register_in_list_of_read_objects: fxcache_add(&d->recent_reads_cache, P); gcptrlist_insert(&d->list_of_read_objects, P); return P; + + old_to_young:; + revision_t target_lock; + target_lock = *(revision_t *)(v & ~(HANDLE_BLOCK_SIZE-1)); + if (target_lock == d->my_lock) +{ + P = (gcptr)(*(revision_t *)(v - 2)); + assert(!(P->h_tid & GCFLAG_PUBLIC)); + if (P->h_revision == stm_private_rev_num) +{ + fprintf(stderr, "read_barrier: %p -> %p handle " + "private\n", G, P); + return P; +} + else if (FXCACHE_AT(P) == P) +{ + fprintf(stderr, "read_barrier: %p -> %p handle " + "protected fxcache\n", G, P); + return P; +} + else +{ + fprintf(stderr, "read_barrier: %p -> %p handle " + "protected\n", G, P); + goto register_in_list_of_read_objects; +} +} + else +{ + abort(); // stealing +} } static gcptr _latest_gcptr(gcptr R) diff --git a/c3/test/test_et.py b/c3/test/test_et.py --- a/c3/test/test_et.py +++ b/c3/test/test_et.py @@ -191,3 +191,35 @@ p3 = lib.stm_read_barrier(p) assert p3 == p2 assert list_of_read_objects() == [p] + +def test_read_barrier_handle_protected(): +p = palloc(HDR) +p2 = lib.stm_write_barrier(p) +lib.stm_commit_transaction() +lib.stm_begin_inevitable_transaction() +assert classify(p) == "public" +assert classify(p2) == "protected" +assert list_of_read_objects() == [] +p3 = lib.stm_read_barrier(p) +assert p3 == p2 +assert list_of_read_objects() == [p2] +p4 = lib.stm_read_barrier(p) +assert p4 == p2 +assert list_of_read_objects() == [p2] + +def test_read_barrier_handle_private(): +p = palloc(HDR) +p2 = lib.stm_write_barrier(p) +lib.stm_commit_transaction() +lib.stm_begin_inevitable_transaction() +p2b = lib.stm_write_barrier(p) +assert p2b == p2 +assert classify(p) == "public" +assert classify(p2) == "private" +assert list_of_read_objects() == [p2] +p3 = lib.stm_read_barrier(p) +assert p3 == p2 +assert list_of_read_objects() == [p2] +p4 = lib.stm_read_barrier(p) +assert p4 == p2 +assert list_of_read_objects() == [p2] ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy py3k: merge default
Author: Philip Jenvey Branch: py3k Changeset: r64804:54af5b1ed1de Date: 2013-06-05 11:49 -0700 http://bitbucket.org/pypy/pypy/changeset/54af5b1ed1de/ Log:merge default diff --git a/lib-python/2.7/opcode.py b/lib-python/2.7/opcode.py --- a/lib-python/2.7/opcode.py +++ b/lib-python/2.7/opcode.py @@ -193,5 +193,6 @@ hasname.append(201) def_op('CALL_METHOD', 202)# #args not including 'self' def_op('BUILD_LIST_FROM_ARG', 203) +jrel_op('JUMP_IF_NOT_DEBUG', 204) # jump over assert statements del def_op, name_op, jrel_op, jabs_op diff --git a/lib-python/2.7/test/test_code.py b/lib-python/2.7/test/test_code.py --- a/lib-python/2.7/test/test_code.py +++ b/lib-python/2.7/test/test_code.py @@ -75,7 +75,7 @@ cellvars: () freevars: () nlocals: 0 -flags: 67 +flags: 1048643 consts: ("'doc string'", 'None') """ diff --git a/lib-python/2.7/test/test_dis.py b/lib-python/2.7/test/test_dis.py --- a/lib-python/2.7/test/test_dis.py +++ b/lib-python/2.7/test/test_dis.py @@ -53,25 +53,26 @@ pass dis_bug1333982 = """\ - %-4d 0 LOAD_CONST 1 (0) - 3 POP_JUMP_IF_TRUE41 - 6 LOAD_GLOBAL 0 (AssertionError) - 9 LOAD_FAST0 (x) - 12 BUILD_LIST_FROM_ARG 0 - 15 GET_ITER ->> 16 FOR_ITER12 (to 31) - 19 STORE_FAST 1 (s) - 22 LOAD_FAST1 (s) - 25 LIST_APPEND 2 - 28 JUMP_ABSOLUTE 16 + %-4d 0 JUMP_IF_NOT_DEBUG 41 (to 44) + 3 LOAD_CONST 1 (0) + 6 POP_JUMP_IF_TRUE44 + 9 LOAD_GLOBAL 0 (AssertionError) + 12 LOAD_FAST0 (x) + 15 BUILD_LIST_FROM_ARG 0 + 18 GET_ITER +>> 19 FOR_ITER12 (to 34) + 22 STORE_FAST 1 (s) + 25 LOAD_FAST1 (s) + 28 LIST_APPEND 2 + 31 JUMP_ABSOLUTE 19 - %-4d >> 31 LOAD_CONST 2 (1) - 34 BINARY_ADD - 35 CALL_FUNCTION1 - 38 RAISE_VARARGS1 + %-4d >> 34 LOAD_CONST 2 (1) + 37 BINARY_ADD + 38 CALL_FUNCTION1 + 41 RAISE_VARARGS1 - %-4d >> 41 LOAD_CONST 0 (None) - 44 RETURN_VALUE + %-4d >> 44 LOAD_CONST 0 (None) + 47 RETURN_VALUE """%(bug1333982.func_code.co_firstlineno + 1, bug1333982.func_code.co_firstlineno + 2, bug1333982.func_code.co_firstlineno + 3) diff --git a/lib_pypy/_ctypes/pointer.py b/lib_pypy/_ctypes/pointer.py --- a/lib_pypy/_ctypes/pointer.py +++ b/lib_pypy/_ctypes/pointer.py @@ -119,6 +119,7 @@ return self._buffer[0] != 0 contents = property(getcontents, setcontents) +_obj = property(getcontents) # byref interface def _as_ffi_pointer_(self, ffitype): return as_ffi_pointer(self, ffitype) diff --git a/lib_pypy/_pypy_irc_topic.py b/lib_pypy/_pypy_irc_topic.py --- a/lib_pypy/_pypy_irc_topic.py +++ b/lib_pypy/_pypy_irc_topic.py @@ -1,4 +1,4 @@ -"""eclguba: flagnk naq frznagvpf bs clguba, fcrrq bs p, erfgevpgvbaf bs wnin naq pbzcvyre reebe zrffntrf nf crargenoyr nf ZHZCF +__doc__ = """eclguba: flagnk naq frznagvpf bs clguba, fcrrq bs p, erfgevpgvbaf bs wnin naq pbzcvyre reebe zrffntrf nf crargenoyr nf ZHZCF pglcrf unf n fcva bs 1/3 ' ' vf n fcnpr gbb Clguba 2.k rfg cerfdhr zbeg, ivir Clguba! diff --git a/pypy/bin/pyinteractive.py b/pypy/bin/pyinteractive.py --- a/pypy/bin/pyinteractive.py +++ b/pypy/bin/pyinteractive.py @@ -27,7 +27,8 @@ BoolOption("completer", "use readline commandline completer", default=False, cmdline="-C"), BoolOption("optimize", - "dummy optimization flag for compatibility with CPython", + "skip assert statements and remove docstrings when importing modules" + " (this is -OO in regular CPython)", default=False, cmdline="-O"), BoolOption("no_site_import", "do not 'import site' on initialization", default=False, cmdline="-S"), @@ -94,6 +95,17 @@ space.setitem(space.sys.w_dict, space.wrap('executable'), space.wrap(argv[0])) +if interactiveconfig.optimize: +#change the optimize flag's value and set __debug__ to False +space.appexec([], """(): +import sys +flags = list(sys.flags) +flags[6] = 2 +sys.flags = type(sys.flags)(flags) +import __pypy__ +__pypy__.set_debug(False) +""") + # call pypy_find_stdlib: the side-effect is that it sets sys.prefix and # sys.exec_prefix executable = argv[0] diff --git a/pypy/doc/man/pypy.1.rst b/pypy/doc/man/pypy.1.r
[pypy-commit] pypy default: have recursive Cache build failures trigger a more specific RuntimeError
Author: Philip Jenvey Branch: Changeset: r64807:e258a99e3784 Date: 2013-06-05 14:46 -0700 http://bitbucket.org/pypy/pypy/changeset/e258a99e3784/ Log:have recursive Cache build failures trigger a more specific RuntimeError 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 @@ -917,7 +917,8 @@ try: optimize = space.sys.get_flag('optimize') -except Exception: +except RuntimeError: +# during bootstrapping optimize = 0 if optimize >= 2: code_w.remove_docstrings(space) @@ -1018,7 +1019,8 @@ code_w = read_compiled_module(space, cpathname, source) try: optimize = space.sys.get_flag('optimize') -except Exception: +except RuntimeError: +# during bootstrapping optimize = 0 if optimize >= 2: code_w.remove_docstrings(space) diff --git a/rpython/rlib/cache.py b/rpython/rlib/cache.py --- a/rpython/rlib/cache.py +++ b/rpython/rlib/cache.py @@ -44,8 +44,8 @@ return self.content[key] except KeyError: if key in self._building: -raise Exception, "%s recursive building of %r" % ( -self, key) +raise RuntimeError("%s recursive building of %r" % + (self, key)) self._building[key] = True try: result = self._build(key) ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy py3k: fix
Author: Philip Jenvey Branch: py3k Changeset: r64805:88ea391ffde6 Date: 2013-06-05 12:00 -0700 http://bitbucket.org/pypy/pypy/changeset/88ea391ffde6/ Log:fix diff --git a/pypy/interpreter/app_main.py b/pypy/interpreter/app_main.py --- a/pypy/interpreter/app_main.py +++ b/pypy/interpreter/app_main.py @@ -462,13 +462,13 @@ sys.flags = type(sys.flags)(flags) sys.dont_write_bytecode = bool(sys.flags.dont_write_bytecode) -sys._xoptions = dict(x.split('=', 1) if '=' in x else (x, True) - for x in options['_xoptions']) - if sys.flags.optimize >= 1: import __pypy__ __pypy__.set_debug(False) +sys._xoptions = dict(x.split('=', 1) if '=' in x else (x, True) + for x in options['_xoptions']) + ##if not we_are_translated(): ##for key in sorted(options): ##print '%40s: %s' % (key, options[key]) ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy py3k: apply stdlib changes from e953dfbc7f0a
Author: Philip Jenvey Branch: py3k Changeset: r64806:739db6f6edc0 Date: 2013-06-05 14:44 -0700 http://bitbucket.org/pypy/pypy/changeset/739db6f6edc0/ Log:apply stdlib changes from e953dfbc7f0a diff --git a/lib-python/3/opcode.py b/lib-python/3/opcode.py --- a/lib-python/3/opcode.py +++ b/lib-python/3/opcode.py @@ -182,5 +182,6 @@ hasname.append(201) def_op('CALL_METHOD', 202)# #args not including 'self' def_op('BUILD_LIST_FROM_ARG', 203) +jrel_op('JUMP_IF_NOT_DEBUG', 204) # jump over assert statements del def_op, name_op, jrel_op, jabs_op diff --git a/lib-python/3/test/test_code.py b/lib-python/3/test/test_code.py --- a/lib-python/3/test/test_code.py +++ b/lib-python/3/test/test_code.py @@ -81,7 +81,7 @@ cellvars: () freevars: () nlocals: 0 -flags: 67 +flags: 1048643 consts: ("'doc string'", 'None') >>> def keywordonly_args(a,b,*,k1): diff --git a/lib-python/3/test/test_dis.py b/lib-python/3/test/test_dis.py --- a/lib-python/3/test/test_dis.py +++ b/lib-python/3/test/test_dis.py @@ -218,7 +218,7 @@ Kw-only arguments: 0 Number of locals: 1 Stack size:4 -Flags: OPTIMIZED, NEWLOCALS, NOFREE +Flags: OPTIMIZED, NEWLOCALS, NOFREE, 0x10 Constants: 0: %r 1: '__func__' ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit
[pypy-commit] pypy py3k: (amaury) oops, don't double wrap
Author: Philip Jenvey Branch: py3k Changeset: r64808:162c471d831c Date: 2013-06-05 14:48 -0700 http://bitbucket.org/pypy/pypy/changeset/162c471d831c/ Log:(amaury) oops, don't double wrap diff --git a/pypy/interpreter/pyparser/error.py b/pypy/interpreter/pyparser/error.py --- a/pypy/interpreter/pyparser/error.py +++ b/pypy/interpreter/pyparser/error.py @@ -24,7 +24,7 @@ space.newtuple([w_filename, space.wrap(self.lineno), space.wrap(self.offset), - space.wrap(w_text), + w_text, space.wrap(self.lastlineno)])]) def __str__(self): ___ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit