Ejemplo n.º 1
0
    def test_hash_preservation(self):
        from rpython.rlib.objectmodel import current_object_addr_as_int
        from rpython.rlib.objectmodel import compute_identity_hash

        class C:
            pass

        class D(C):
            pass

        c = C()
        d = D()
        h_c = compute_identity_hash(c)
        h_d = compute_identity_hash(d)

        #
        def f():
            d2 = D()
            return (compute_identity_hash(d2), current_object_addr_as_int(d2),
                    compute_identity_hash(c), compute_identity_hash(d))

        res = self.interpret(f, [])
        # xxx the following test is too precise, checking the exact
        # implementation.  On Python 2.7 it doesn't work anyway, because
        # object.__hash__(x) is different from id(x).  The test is disabled
        # for now, and nobody should rely on compute_identity_hash() returning
        # a value that is (or was) the current_object_addr_as_int().
        # --- disabled: assert res.item0 == res.item1
        # the following property is essential on top of the lltypesystem
        # otherwise prebuilt dictionaries are broken.
        assert res.item2 == h_c
        assert res.item3 == h_d
Ejemplo n.º 2
0
    def test_hash_preservation(self):
        from rpython.rlib.objectmodel import current_object_addr_as_int
        from rpython.rlib.objectmodel import compute_identity_hash
        class C:
            pass
        class D(C):
            pass
        c = C()
        d = D()
        h_c = compute_identity_hash(c)
        h_d = compute_identity_hash(d)
        #
        def f():
            d2 = D()
            return (compute_identity_hash(d2),
                    current_object_addr_as_int(d2),
                    compute_identity_hash(c),
                    compute_identity_hash(d))

        res = self.interpret(f, [])
        # xxx the following test is too precise, checking the exact
        # implementation.  On Python 2.7 it doesn't work anyway, because
        # object.__hash__(x) is different from id(x).  The test is disabled
        # for now, and nobody should rely on compute_identity_hash() returning
        # a value that is (or was) the current_object_addr_as_int().
        # --- disabled: assert res.item0 == res.item1
        # the following property is essential on top of the lltypesystem
        # otherwise prebuilt dictionaries are broken.
        assert res.item2 == h_c
        assert res.item3 == h_d
Ejemplo n.º 3
0
 def main(argv):
     print[
         objectmodel.compute_identity_hash(argv),
         objectmodel.compute_identity_hash(argv),
         objectmodel.compute_identity_hash(argv)
     ]
     return 9
Ejemplo n.º 4
0
def _func_key_hash(unique_cache, fargs, fresult, ellipsis, abi):
    x = compute_identity_hash(fresult)
    for w_arg in fargs:
        y = compute_identity_hash(w_arg)
        x = intmask((1000003 * x) ^ y)
    x ^= (ellipsis - abi)
    if unique_cache.for_testing:    # constant-folded to False in translation;
        x &= 3                      # but for test, keep only 2 bits of hash
    return x
Ejemplo n.º 5
0
def _func_key_hash(unique_cache, fargs, fresult, ellipsis, abi):
    x = compute_identity_hash(fresult)
    for w_arg in fargs:
        y = compute_identity_hash(w_arg)
        x = intmask((1000003 * x) ^ y)
    x ^= ellipsis + 2 * abi
    if unique_cache.for_testing:  # constant-folded to False in translation;
        x &= 3  # but for test, keep only 2 bits of hash
    return x
Ejemplo n.º 6
0
 def fn():
     objects = []
     hashes = []
     for i in range(200):
         rgc.collect(0)     # nursery-only collection, if possible
         obj = A()
         objects.append(obj)
         hashes.append(compute_identity_hash(obj))
     unique = {}
     for i in range(len(objects)):
         assert compute_identity_hash(objects[i]) == hashes[i]
         unique[hashes[i]] = None
     return len(unique)
Ejemplo n.º 7
0
 def fn():
     objects = []
     hashes = []
     for i in range(200):
         rgc.collect(0)  # nursery-only collection, if possible
         obj = A()
         objects.append(obj)
         hashes.append(compute_identity_hash(obj))
     unique = {}
     for i in range(len(objects)):
         assert compute_identity_hash(objects[i]) == hashes[i]
         unique[hashes[i]] = None
     return len(unique)
Ejemplo n.º 8
0
 def f1():
     d2 = D()
     # xxx we assume that current_object_addr_as_int is defined as
     # simply returning the identity hash
     current_identityhash = current_object_addr_as_int(d2)
     instance_hash = compute_identity_hash(d2)
     return current_identityhash == instance_hash
Ejemplo n.º 9
0
 def define_hash_preservation(cls):
     class C:
         pass
     class D(C):
         pass
     c = C()
     d = D()
     h_d = compute_hash(d)     # force to be cached on 'd', but not on 'c'
     h_t = compute_hash(("Hi", None, (7.5, 2, d)))
     S = lltype.GcStruct('S', ('x', lltype.Signed),
                              ('a', lltype.Array(lltype.Signed)))
     s = lltype.malloc(S, 15, zero=True)
     h_s = compute_identity_hash(s)   # varsized: hash not saved/restored
     #
     def f():
         if compute_hash(c) != compute_identity_hash(c):
             return 12
         if compute_hash(d) != h_d:
             return 13
         if compute_hash(("Hi", None, (7.5, 2, d))) != h_t:
             return 14
         c2 = C()
         h_c2 = compute_hash(c2)
         if compute_hash(c2) != h_c2:
             return 15
         if compute_identity_hash(s) == h_s:
             return 16   # unlikely
         i = 0
         while i < 6:
             rgc.collect()
             if compute_hash(c2) != h_c2:
                 return i
             i += 1
         return 42
     return f
Ejemplo n.º 10
0
 def f1():
     d2 = D()
     # xxx we assume that current_object_addr_as_int is defined as
     # simply returning the identity hash
     current_identityhash = current_object_addr_as_int(d2)
     instance_hash = compute_identity_hash(d2)
     return current_identityhash == instance_hash
Ejemplo n.º 11
0
def test_compute_identity_hash():
    class Foo(object):
        def __hash__(self):
            return 42
    foo = Foo()
    h = compute_identity_hash(foo)
    assert h == object.__hash__(foo)
    assert h == getattr(foo, '__precomputed_identity_hash')
Ejemplo n.º 12
0
    def hash(self):
        """
        Create a conservative integer hash of this object.

        If two objects are equal, then they must hash equal.
        """

        return compute_identity_hash(self)
Ejemplo n.º 13
0
    def hash(self):
        """
        Create a conservative integer hash of this object.

        If two objects are equal, then they must hash equal.
        """

        return compute_identity_hash(self)
Ejemplo n.º 14
0
def test_compute_identity_hash():
    class Foo(object):
        def __hash__(self):
            return 42

    foo = Foo()
    h = compute_identity_hash(foo)
    assert h == object.__hash__(foo)
Ejemplo n.º 15
0
def ll_set_null(d, llkey):
    hash = compute_identity_hash(llkey)
    i = rdict.ll_dict_lookup(d, llkey, hash) & rdict.MASK
    if d.entries.everused(i):
        # If the entry was ever used, clean up its key and value.
        # We don't store a NULL value, but a dead weakref, because
        # the entry must still be marked as everused().
        d.entries[i].key = llmemory.dead_wref
        d.entries[i].value = NULLVALUE
Ejemplo n.º 16
0
 def build(xr, n):
     "Build the identity hashes of all n objects of the chain."
     i = 0
     while i < n:
         xr.hash = compute_identity_hash(xr)
         # ^^^ likely to trigger a collection
         xr = xr.prev
         i += 1
     assert xr is None
Ejemplo n.º 17
0
def ll_set_null(d, llkey):
    hash = compute_identity_hash(llkey)
    i = rdict.ll_dict_lookup(d, llkey, hash) & rdict.MASK
    if d.entries.everused(i):
        # If the entry was ever used, clean up its key and value.
        # We don't store a NULL value, but a dead weakref, because
        # the entry must still be marked as everused().
        d.entries[i].key = llmemory.dead_wref
        d.entries[i].value = NULLVALUE
Ejemplo n.º 18
0
def ll_get(d, llkey):
    hash = compute_identity_hash(llkey)
    i = rdict.ll_dict_lookup(d, llkey, hash) & rdict.MASK
    #llop.debug_print(lltype.Void, i, 'get', hex(hash),
    #                 ll_debugrepr(d.entries[i].key),
    #                 ll_debugrepr(d.entries[i].value))
    # NB. ll_valid() above was just called at least on entry i, so if
    # it is an invalid entry with a dead weakref, the value was reset
    # to NULLVALUE.
    return d.entries[i].value
Ejemplo n.º 19
0
def ll_get(d, llkey):
    hash = compute_identity_hash(llkey)
    i = rdict.ll_dict_lookup(d, llkey, hash) & rdict.MASK
    # llop.debug_print(lltype.Void, i, 'get', hex(hash),
    #                 ll_debugrepr(d.entries[i].key),
    #                 ll_debugrepr(d.entries[i].value))
    # NB. ll_valid() above was just called at least on entry i, so if
    # it is an invalid entry with a dead weakref, the value was reset
    # to NULLVALUE.
    return d.entries[i].value
Ejemplo n.º 20
0
 def check(xr, n, step):
     "Check that the identity hashes are still correct."
     i = 0
     while i < n:
         if xr.hash != compute_identity_hash(xr):
             os.write(2, "wrong hash! i=%d, n=%d, step=%d\n" % (i, n,
                                                                step))
             raise ValueError
         xr = xr.prev
         i += 1
     assert xr is None
Ejemplo n.º 21
0
 def f():
     if compute_hash(c) != compute_identity_hash(c):
         return 12
     if compute_hash(d) != h_d:
         return 13
     if compute_hash(("Hi", None, (7.5, 2, d))) != h_t:
         return 14
     c2 = C()
     h_c2 = compute_hash(c2)
     if compute_hash(c2) != h_c2:
         return 15
     if compute_identity_hash(s) == h_s:
         return 16   # unlikely
     i = 0
     while i < 6:
         rgc.collect()
         if compute_hash(c2) != h_c2:
             return i
         i += 1
     return 42
Ejemplo n.º 22
0
 def descr_hash(self, space):
     w_func = self.getattr(space, "__hash__", False)
     if w_func is None:
         w_eq = self.getattr(space, "__eq__", False)
         w_cmp = self.getattr(space, "__cmp__", False)
         if w_eq is not None or w_cmp is not None:
             raise OperationError(space.w_TypeError, space.wrap("unhashable instance"))
         else:
             return space.wrap(compute_identity_hash(self))
     w_ret = space.call_function(w_func)
     if not space.isinstance_w(w_ret, space.w_int) and not space.isinstance_w(w_ret, space.w_long):
         raise OperationError(space.w_TypeError, space.wrap("__hash__ must return int or long"))
     return w_ret
Ejemplo n.º 23
0
 def descr_hash(self, space):
     w_func = self.getattr(space, '__hash__', False)
     if w_func is None:
         w_eq = self.getattr(space, '__eq__', False)
         w_cmp = self.getattr(space, '__cmp__', False)
         if w_eq is not None or w_cmp is not None:
             raise oefmt(space.w_TypeError, "unhashable instance")
         else:
             return space.newint(compute_identity_hash(self))
     w_ret = space.call_function(w_func)
     if (not space.isinstance_w(w_ret, space.w_int)
             and not space.isinstance_w(w_ret, space.w_long)):
         raise oefmt(space.w_TypeError, "__hash__ must return int or long")
     return w_ret
Ejemplo n.º 24
0
def ll_set_nonnull(d, llkey, llvalue):
    hash = compute_identity_hash(llkey)
    keyref = weakref_create(llkey)  # GC effects here, before the rest
    i = rdict.ll_dict_lookup(d, llkey, hash) & rdict.MASK
    everused = d.entries.everused(i)
    d.entries[i].key = keyref
    d.entries[i].value = llvalue
    d.entries[i].f_hash = hash
    #llop.debug_print(lltype.Void, i, 'stored', hex(hash),
    #                 ll_debugrepr(llkey),
    #                 ll_debugrepr(llvalue))
    if not everused:
        d.resize_counter -= 3
        if d.resize_counter <= 0:
            #llop.debug_print(lltype.Void, 'RESIZE')
            ll_weakdict_resize(d)
Ejemplo n.º 25
0
def ll_set_nonnull(d, llkey, llvalue):
    hash = compute_identity_hash(llkey)
    keyref = weakref_create(llkey)  # GC effects here, before the rest
    i = rdict.ll_dict_lookup(d, llkey, hash) & rdict.MASK
    everused = d.entries.everused(i)
    d.entries[i].key = keyref
    d.entries[i].value = llvalue
    d.entries[i].f_hash = hash
    # llop.debug_print(lltype.Void, i, 'stored', hex(hash),
    #                 ll_debugrepr(llkey),
    #                 ll_debugrepr(llvalue))
    if not everused:
        d.resize_counter -= 3
        if d.resize_counter <= 0:
            # llop.debug_print(lltype.Void, 'RESIZE')
            ll_weakdict_resize(d)
Ejemplo n.º 26
0
    def computeHash(self, depth):
        """
        Compute the sameness hash.

        This is the correct method to override to customize the sameness hash.

        Transparent objects are expected to customize their sameness hash.

        The `depth` parameter controls how many levels of structural recursion
        a nested object should include in the hash.
        """
        from typhon.objects.auditors import selfless, transparentStamp
        stamps = self.auditorStamps()
        if selfless in stamps and transparentStamp in stamps:
            return self.call(u"_uncall", []).computeHash(depth)
        # Here, if it existed, would lie Semitransparent hashing.
        return compute_identity_hash(self)
Ejemplo n.º 27
0
    def computeHash(self, depth):
        """
        Compute the sameness hash.

        This is the correct method to override to customize the sameness hash.

        Transparent objects are expected to customize their sameness hash.

        The `depth` parameter controls how many levels of structural recursion
        a nested object should include in the hash.
        """
        from typhon.objects.auditors import selfless, transparentStamp
        stamps = self.auditorStamps()
        if selfless in stamps and transparentStamp in stamps:
            return self.call(u"_uncall", []).computeHash(depth)
        # Here, if it existed, would lie Semitransparent hashing.
        return compute_identity_hash(self)
Ejemplo n.º 28
0
 def f(i):
     assert compute_hash(i) == compute_hash(42)
     assert compute_hash(i + 1.0) == compute_hash(43.0)
     assert compute_hash("Hello" + str(i)) == compute_hash("Hello42")
     if i == 42:
         p = None
     else:
         p = Foo()
     assert compute_hash(p) == compute_hash(None)
     assert (compute_hash(("world", None, i, 7.5)) == compute_hash(
         ("world", None, 42, 7.5)))
     q = Foo()
     assert compute_hash(q) == compute_identity_hash(q)
     from rpython.rlib.rfloat import INFINITY, NAN
     assert compute_hash(INFINITY) == 314159
     assert compute_hash(-INFINITY) == -271828
     assert compute_hash(NAN) == 0
     return i * 2
Ejemplo n.º 29
0
 def f(i):
     assert compute_hash(i) == compute_hash(42)
     assert compute_hash(i + 1.0) == compute_hash(43.0)
     assert compute_hash("Hello" + str(i)) == compute_hash("Hello42")
     if i == 42:
         p = None
     else:
         p = Foo()
     assert compute_hash(p) == compute_hash(None)
     assert (compute_hash(("world", None, i, 7.5)) ==
             compute_hash(("world", None, 42, 7.5)))
     q = Foo()
     assert compute_hash(q) == compute_identity_hash(q)
     from rpython.rlib.rfloat import INFINITY, NAN
     assert compute_hash(INFINITY) == 314159
     assert compute_hash(-INFINITY) == -271828
     assert compute_hash(NAN) == 0
     return i * 2
Ejemplo n.º 30
0
def _func_key_hash((fargs, w_fresult, ellipsis)):
    x = compute_identity_hash(w_fresult) ^ ellipsis
    for w_arg in fargs:
        y = compute_identity_hash(w_arg)
        x = intmask((1000003 * x) ^ y)
    return x
Ejemplo n.º 31
0
def _func_key_hash((fargs, w_fresult, ellipsis)):
    x = compute_identity_hash(w_fresult) ^ ellipsis
    for w_arg in fargs:
        y = compute_identity_hash(w_arg)
        x = intmask((1000003 * x) ^ y)
    return x
Ejemplo n.º 32
0
 def _get_hash_(self):
     return compute_identity_hash(self)
Ejemplo n.º 33
0
 def fringeHash(self):
     return compute_identity_hash(self.identity) ^ hashFringePath(self.path)
Ejemplo n.º 34
0
def samenessHash(obj, depth, path, fringe):
    """
    Generate a hash code for an object that may not be completely
    settled. Equality of hash code implies sameness of objects. The generated
    hash is valid until settledness of a component changes.
    """

    if depth <= 0:
        # not gonna look any further for the purposes of hash computation, but
        # we do have to know about unsettled refs
        if samenessFringe(obj, path, fringe):
            # obj is settled.
            return -1
        elif fringe is None:
            raise userError(u"Must be settled")
        else:
            # not settled.
            return -1

    o = resolution(obj)
    if o is NullObject:
        return 0

    # Objects that do their own hashing.
    if (
        isinstance(o, BoolObject)
        or isinstance(o, CharObject)
        or isinstance(o, DoubleObject)
        or isinstance(o, IntObject)
        or isinstance(o, BigInt)
        or isinstance(o, StrObject)
        or isinstance(o, BytesObject)
        or isinstance(o, TraversalKey)
    ):
        return o.hash()

    # Lists.
    if isinstance(o, ConstList):

        oList = unwrapList(o)
        result = len(oList)
        for i, x in enumerate(oList):
            if fringe is None:
                fr = None
            else:
                fr = FringePath(i, path)
            result ^= i ^ samenessHash(x, depth - 1, fr, fringe)
        return result

    # The empty map. (Uncalls contain maps, thus this base case.)
    if isinstance(o, ConstMap) and len(o.objectMap) == 0:
        return 127
    from typhon.objects.proxy import FarRef, DisconnectedRef

    if isinstance(o, FarRef) or isinstance(o, DisconnectedRef):
        return samenessHash(o.handler, depth, path, fringe)

    # Other objects compared by structure.
    if selfless in o.auditorStamps():
        if transparentStamp in o.auditorStamps():
            return samenessHash(o.call(u"_uncall", []), depth, path, fringe)
        # XXX Semitransparent support goes here

    # Objects compared by identity.
    if isResolved(o):
        return compute_identity_hash(o)
    elif fringe is None:
        raise userError(u"Must be settled")
    # Unresolved refs.
    fringe.append(FringeNode(o, path))
    return -1
Ejemplo n.º 35
0
 def fringeHash(self):
     return compute_identity_hash(self.identity) ^ hashFringePath(self.path)
Ejemplo n.º 36
0
def descrlist_hash(l):
    res = 0x345678
    for descr in l:
        y = compute_identity_hash(descr)
        res = intmask((1000003 * res) ^ y)
    return res
Ejemplo n.º 37
0
def ll_debugrepr(x):
    if x:
        h = compute_identity_hash(x)
    else:
        h = 0
    return "<%x>" % (h,)
Ejemplo n.º 38
0
 def method_hash(self, space):
     return space.newint(compute_identity_hash(self))
Ejemplo n.º 39
0
def ll_debugrepr(x):
    if x:
        h = compute_identity_hash(x)
    else:
        h = 0
    return '<%x>' % (h, )
Ejemplo n.º 40
0
def _hashcode(ivkbl, frame, interpreter):
    rcvr = frame.pop()
    frame.push(interpreter.get_universe().new_integer(
        compute_identity_hash(rcvr.get_embedded_string())))
Ejemplo n.º 41
0
 def hash(self):
     import pixie.vm.rt as rt
     return rt.wrap(compute_identity_hash(self))
Ejemplo n.º 42
0
def descrlist_hash(l):
    res = 0x345678
    for descr in l:
        y = compute_identity_hash(descr)
        res = intmask((1000003 * res) ^ y)
    return res
Ejemplo n.º 43
0
 def hash(self):
     return compute_identity_hash(self.content)
Ejemplo n.º 44
0
def samenessHash(obj, depth, path, fringe):
    """
    Generate a hash code for an object that may not be completely
    settled. Equality of hash code implies sameness of objects. The generated
    hash is valid until settledness of a component changes.
    """

    if depth <= 0:
        # not gonna look any further for the purposes of hash computation, but
        # we do have to know about unsettled refs
        if samenessFringe(obj, path, fringe):
            # obj is settled.
            return -1
        elif fringe is None:
            raise userError(u"Must be settled")
        else:
            # not settled.
            return -1

    o = resolution(obj)
    if o is NullObject:
        return 0

    # Objects that do their own hashing.
    if (isinstance(o, BoolObject) or isinstance(o, CharObject)
            or isinstance(o, DoubleObject) or isinstance(o, IntObject)
            or isinstance(o, BigInt) or isinstance(o, StrObject)
            or isinstance(o, BytesObject) or isinstance(o, TraversalKey)):
        return o.hash()

    # Lists.
    if isinstance(o, ConstList):

        oList = unwrapList(o)
        result = len(oList)
        for i, x in enumerate(oList):
            if fringe is None:
                fr = None
            else:
                fr = FringePath(i, path)
            result ^= i ^ samenessHash(x, depth - 1, fr, fringe)
        return result

    # The empty map. (Uncalls contain maps, thus this base case.)
    if isinstance(o, ConstMap) and len(o.objectMap) == 0:
        return 127
    from typhon.objects.proxy import FarRef, DisconnectedRef
    if isinstance(o, FarRef) or isinstance(o, DisconnectedRef):
        return samenessHash(o.handler, depth, path, fringe)

    # Other objects compared by structure.
    if selfless in o.auditorStamps():
        if transparentStamp in o.auditorStamps():
            return samenessHash(o.call(u"_uncall", []), depth, path, fringe)
        # XXX Semitransparent support goes here

    # Objects compared by identity.
    if isResolved(o):
        return compute_identity_hash(o)
    elif fringe is None:
        raise userError(u"Must be settled")
    # Unresolved refs.
    fringe.append(FringeNode(o, path))
    return -1
Ejemplo n.º 45
0
def _hashcode(ivkbl, rcvr, args, meta_level):
    return ivkbl.get_universe().new_integer(compute_identity_hash(rcvr))
Ejemplo n.º 46
0
 def f(n):
     z = Z()
     got = my_gethash(z)
     expected = compute_identity_hash(z)
     return got - expected
Ejemplo n.º 47
0
 def _get_hash_(self):
     return compute_identity_hash(self)
Ejemplo n.º 48
0
 def f():
     d2 = D()
     return (compute_identity_hash(d2), compute_identity_hash(c),
             compute_identity_hash(d))
Ejemplo n.º 49
0
 def hash(self):
     import pixie.vm.rt as rt
     return rt.wrap(compute_identity_hash(self))
Ejemplo n.º 50
0
def default_identity_hash(space, w_obj):
    w_unique_id = w_obj.immutable_unique_id(space)
    if w_unique_id is None:     # common case
        return space.wrap(compute_identity_hash(w_obj))
    else:
        return space.hash(w_unique_id)
Ejemplo n.º 51
0
 def method_hash(self, space):
     return space.newint(compute_identity_hash(self))
Ejemplo n.º 52
0
 def computeHash(self, depth):
     return compute_identity_hash(self)
Ejemplo n.º 53
0
 def f(n):
     z = Z()
     got = my_gethash(z)
     expected = compute_identity_hash(z)
     return got - expected
Ejemplo n.º 54
0
 def f():
     d2 = D()
     return (compute_identity_hash(d2), current_object_addr_as_int(d2),
             compute_identity_hash(c), compute_identity_hash(d))
Ejemplo n.º 55
0
def _hashcode(ivkbl, frame, interpreter):
    rcvr = frame.pop()
    frame.push(interpreter.get_universe().new_integer(
        compute_identity_hash(rcvr.get_embedded_string())))
Ejemplo n.º 56
0
 def computeHash(self, depth):
     return compute_identity_hash(self)
Ejemplo n.º 57
0
 def f():
     d2 = D()
     return (compute_identity_hash(d2),
             current_object_addr_as_int(d2),
             compute_identity_hash(c),
             compute_identity_hash(d))
Ejemplo n.º 58
0
def samenessHash(obj, depth, fringe, path=None):
    """
    Generate a hash code for an object that may not be completely
    settled. If two objects are the same, then they will have identical
    hashes. The generated hash is valid until settledness of a component
    changes.
    """

    if depth <= 0:
        # not gonna look any further for the purposes of hash computation, but
        # we do have to know about unsettled refs
        if samenessFringe(obj, path, fringe):
            # obj is settled.
            return -1
        elif fringe is None:
            raise userError(u"Must be settled")
        else:
            # not settled.
            return -1

    o = resolution(obj)
    # The constants have their own special hash values.
    if o is NullObject:
        return 0
    if o is TrueObject:
        return 1
    if o is FalseObject:
        return 2

    # Objects that do their own hashing.
    if (isinstance(o, CharObject) or isinstance(o, DoubleObject)
            or isinstance(o, IntObject) or isinstance(o, BigInt)
            or isinstance(o, StrObject) or isinstance(o, BytesObject)
            or isinstance(o, TraversalKey)):
        return o.computeHash(depth)

    # Lists.
    if isinstance(o, ConstList):

        oList = unwrapList(o)
        result = len(oList)
        for i, x in enumerate(oList):
            if fringe is None:
                fr = None
            else:
                fr = FringePath(i, path)
            result ^= i ^ samenessHash(x, depth - 1, fringe, path=fr)
        return result

    # The empty map. (Uncalls contain maps, thus this base case.)
    if isinstance(o, ConstMap) and o.empty():
        return 127
    from typhon.objects.proxy import FarRef, DisconnectedRef
    if isinstance(o, FarRef) or isinstance(o, DisconnectedRef):
        return samenessHash(o.handler, depth, fringe, path=path)

    # Other objects compared by structure.
    if selfless in o.auditorStamps():
        if transparentStamp in o.auditorStamps():
            return samenessHash(o.call(u"_uncall", []),
                                depth,
                                fringe,
                                path=path)
        if semitransparentStamp in o.auditorStamps():
            p = o.call(u"_uncall", [])
            if not isinstance(p, SealedPortrayal):
                userError(
                    u'Semitransparent portrayal was not a SealedPortrayal!')
            return samenessHash(p.portrayal, depth, fringe, path=path)

    # Objects compared by identity.
    if isResolved(o):
        return compute_identity_hash(o)
    elif fringe is None:
        raise userError(u"Must be settled")
    # Unresolved refs.
    fringe.append(FringeNode(o, path))
    return -1
Ejemplo n.º 59
0
def default_identity_hash(space, w_obj):
    w_unique_id = w_obj.immutable_unique_id(space)
    if w_unique_id is None:  # common case
        return space.wrap(compute_identity_hash(w_obj))
    else:
        return space.hash(w_unique_id)
Ejemplo n.º 60
0
 def hash(self):
     return compute_identity_hash(self.content)