Exemplo n.º 1
0
def test_return_none(capture):
    n_inst = ConstructorStats.detail_reg_inst()
    with capture:
        p = m.Parent()
    assert capture == "Allocating parent."
    with capture:
        p.returnNullChildKeepAliveChild()
        assert ConstructorStats.detail_reg_inst() == n_inst + 1
    assert capture == ""
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == "Releasing parent."

    with capture:
        p = m.Parent()
    assert capture == "Allocating parent."
    with capture:
        p.returnNullChildKeepAliveParent()
        assert ConstructorStats.detail_reg_inst() == n_inst + 1
    assert capture == ""
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == "Releasing parent."
Exemplo n.º 2
0
def test_pointers(msg):
    from pybind11_tests import (return_void_ptr, get_void_ptr_value, ExampleMandA,
                                print_opaque_list, return_null_str, get_null_str_value,
                                return_unique_ptr, ConstructorStats)

    living_before = ConstructorStats.get(ExampleMandA).alive()
    assert get_void_ptr_value(return_void_ptr()) == 0x1234
    assert get_void_ptr_value(ExampleMandA())  # Should also work for other C++ types
    assert ConstructorStats.get(ExampleMandA).alive() == living_before

    with pytest.raises(TypeError) as excinfo:
        get_void_ptr_value([1, 2, 3])  # This should not work
    assert msg(excinfo.value) == """
        get_void_ptr_value(): incompatible function arguments. The following argument types are supported:
            1. (arg0: capsule) -> int

        Invoked with: [1, 2, 3]
    """  # noqa: E501 line too long

    assert return_null_str() is None
    assert get_null_str_value(return_null_str()) is not None

    ptr = return_unique_ptr()
    assert "StringList" in repr(ptr)
    assert print_opaque_list(ptr) == "Opaque list: [some value]"
Exemplo n.º 3
0
def test_keep_alive_argument(capture):
    n_inst = ConstructorStats.detail_reg_inst()
    with capture:
        p = m.Parent()
    assert capture == "Allocating parent."
    with capture:
        p.addChild(m.Child())
        assert ConstructorStats.detail_reg_inst() == n_inst + 1
    assert capture == """
        Allocating child.
        Releasing child.
    """
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == "Releasing parent."

    with capture:
        p = m.Parent()
    assert capture == "Allocating parent."
    with capture:
        p.addChildKeepAlive(m.Child())
        assert ConstructorStats.detail_reg_inst() == n_inst + 2
    assert capture == "Allocating child."
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == """
Exemplo n.º 4
0
def test_reference_internal():
    from pybind11_tests import ConstructorStats
    from pybind11_tests.submodule import A, B

    b = B()
    assert str(b.get_a1()) == "A[1]"
    assert str(b.a1) == "A[1]"
    assert str(b.get_a2()) == "A[2]"
    assert str(b.a2) == "A[2]"

    b.a1 = A(42)
    b.a2 = A(43)
    assert str(b.get_a1()) == "A[42]"
    assert str(b.a1) == "A[42]"
    assert str(b.get_a2()) == "A[43]"
    assert str(b.a2) == "A[43]"

    astats, bstats = ConstructorStats.get(A), ConstructorStats.get(B)
    assert astats.alive() == 2
    assert bstats.alive() == 1
    del b
    assert astats.alive() == 0
    assert bstats.alive() == 0
    assert astats.values() == ['1', '2', '42', '43']
    assert bstats.values() == []
    assert astats.default_constructions == 0
    assert bstats.default_constructions == 1
    assert astats.copy_constructions == 0
    assert bstats.copy_constructions == 0
    # assert astats.move_constructions >= 0  # Don't invoke any
    # assert bstats.move_constructions >= 0  # Don't invoke any
    assert astats.copy_assignments == 2
    assert bstats.copy_assignments == 0
    assert astats.move_assignments == 0
    assert bstats.move_assignments == 0
Exemplo n.º 5
0
def test_keep_alive_return_value(capture):
    from pybind11_tests import Parent, ConstructorStats

    n_inst = ConstructorStats.detail_reg_inst()
    with capture:
        p = Parent()
    assert capture == "Allocating parent."
    with capture:
        p.returnChild()
        assert ConstructorStats.detail_reg_inst() == n_inst + 1
    assert capture == """
        Allocating child.
        Releasing child.
    """
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == "Releasing parent."

    with capture:
        p = Parent()
    assert capture == "Allocating parent."
    with capture:
        p.returnChildKeepAlive()
        assert ConstructorStats.detail_reg_inst() == n_inst + 2
    assert capture == "Allocating child."
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == """
Exemplo n.º 6
0
def test_unique_nodelete():
    from pybind11_tests import MyObject4
    o = MyObject4(23)
    assert o.value == 23
    cstats = ConstructorStats.get(MyObject4)
    assert cstats.alive() == 1
    del o
    cstats = ConstructorStats.get(MyObject4)
    assert cstats.alive() == 1  # Leak, but that's intentional
Exemplo n.º 7
0
def test_alive_gc(capture):
    n_inst = ConstructorStats.detail_reg_inst()
    p = m.ParentGC()
    p.addChildKeepAlive(m.Child())
    assert ConstructorStats.detail_reg_inst() == n_inst + 2
    lst = [p]
    lst.append(lst)   # creates a circular reference
    with capture:
        del p, lst
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == """
Exemplo n.º 8
0
def test_alive_gc(capture):
    from pybind11_tests import ParentGC, Child, ConstructorStats

    n_inst = ConstructorStats.detail_reg_inst()
    p = ParentGC()
    p.addChildKeepAlive(Child())
    assert ConstructorStats.detail_reg_inst() == n_inst + 2
    lst = [p]
    lst.append(lst)   # creates a circular reference
    with capture:
        del p, lst
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == """
Exemplo n.º 9
0
def test_keep_alive_constructor(capture):
    n_inst = ConstructorStats.detail_reg_inst()

    with capture:
        p = m.Parent(m.Child())
        assert ConstructorStats.detail_reg_inst() == n_inst + 2
    assert capture == """
        Allocating child.
        Allocating parent.
    """
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == """
Exemplo n.º 10
0
def test_stl_ownership():
    cstats = ConstructorStats.get(m.Placeholder)
    assert cstats.alive() == 0
    r = m.test_stl_ownership()
    assert len(r) == 1
    del r
    assert cstats.alive() == 0
Exemplo n.º 11
0
def test_to_python():
    m = Matrix(5, 5)

    assert m[2, 3] == 0
    m[2, 3] = 4
    assert m[2, 3] == 4

    m2 = np.array(m, copy=False)
    assert m2.shape == (5, 5)
    assert abs(m2).sum() == 4
    assert m2[2, 3] == 4
    m2[2, 3] = 5
    assert m2[2, 3] == 5

    cstats = ConstructorStats.get(Matrix)
    assert cstats.alive() == 1
    del m
    pytest.gc_collect()
    assert cstats.alive() == 1
    del m2  # holds an m reference
    pytest.gc_collect()
    assert cstats.alive() == 0
    assert cstats.values() == ["5x5 matrix"]
    assert cstats.copy_constructions == 0
    # assert cstats.move_constructions >= 0  # Don't invoke any
    assert cstats.copy_assignments == 0
    assert cstats.move_assignments == 0
Exemplo n.º 12
0
def test_shared_ptr_and_references():
    from pybind11_tests.smart_ptr import SharedPtrRef, A

    s = SharedPtrRef()
    stats = ConstructorStats.get(A)
    assert stats.alive() == 2

    ref = s.ref  # init_holder_helper(holder_ptr=false, owned=false)
    assert stats.alive() == 2
    assert s.set_ref(ref)
    with pytest.raises(RuntimeError) as excinfo:
        assert s.set_holder(ref)
    assert "Unable to cast from non-held to held instance" in str(excinfo.value)

    copy = s.copy  # init_holder_helper(holder_ptr=false, owned=true)
    assert stats.alive() == 3
    assert s.set_ref(copy)
    assert s.set_holder(copy)

    holder_ref = s.holder_ref  # init_holder_helper(holder_ptr=true, owned=false)
    assert stats.alive() == 3
    assert s.set_ref(holder_ref)
    assert s.set_holder(holder_ref)

    holder_copy = s.holder_copy  # init_holder_helper(holder_ptr=true, owned=true)
    assert stats.alive() == 3
    assert s.set_ref(holder_copy)
    assert s.set_holder(holder_copy)

    del ref, copy, holder_ref, holder_copy, s
    assert stats.alive() == 0
Exemplo n.º 13
0
def test_unique_nodelete():
    o = m.MyObject4(23)
    assert o.value == 23
    cstats = ConstructorStats.get(m.MyObject4)
    assert cstats.alive() == 1
    del o
    assert cstats.alive() == 1  # Leak, but that's intentional
Exemplo n.º 14
0
def test_large_holder():
    o = m.MyObject5(5)
    assert o.value == 5
    cstats = ConstructorStats.get(m.MyObject5)
    assert cstats.alive() == 1
    del o
    assert cstats.alive() == 0
Exemplo n.º 15
0
def test_holder_with_addressof_operator():
    # this test must not throw exception from c++
    a = m.TypeForHolderWithAddressOf.make()
    a.print_object_1()
    a.print_object_2()
    a.print_object_3()
    a.print_object_4()

    stats = ConstructorStats.get(m.TypeForHolderWithAddressOf)
    assert stats.alive() == 1

    np = m.TypeForHolderWithAddressOf.make()
    assert stats.alive() == 2
    del a
    assert stats.alive() == 1
    del np
    assert stats.alive() == 0

    b = m.TypeForHolderWithAddressOf.make()
    c = b
    assert b.get() is c.get()
    assert stats.alive() == 1

    del b
    assert stats.alive() == 1

    del c
    assert stats.alive() == 0
Exemplo n.º 16
0
def test_to_python():
    mat = m.Matrix(5, 5)
    assert memoryview(mat).shape == (5, 5)

    assert mat[2, 3] == 0
    mat[2, 3] = 4
    assert mat[2, 3] == 4

    mat2 = np.array(mat, copy=False)
    assert mat2.shape == (5, 5)
    assert abs(mat2).sum() == 4
    assert mat2[2, 3] == 4
    mat2[2, 3] = 5
    assert mat2[2, 3] == 5

    cstats = ConstructorStats.get(m.Matrix)
    assert cstats.alive() == 1
    del mat
    pytest.gc_collect()
    assert cstats.alive() == 1
    del mat2  # holds a mat reference
    pytest.gc_collect()
    assert cstats.alive() == 0
    assert cstats.values() == ["5x5 matrix"]
    assert cstats.copy_constructions == 0
    # assert cstats.move_constructions >= 0  # Don't invoke any
    assert cstats.copy_assignments == 0
    assert cstats.move_assignments == 0
def test_mi_base_return():
    """Tests returning an offset (non-first MI) base class pointer to a derived instance"""
    from pybind11_tests import (I801B2, I801C, I801D, i801c_b1, i801c_b2, i801d_b1, i801d_b2,
                                i801e_c, i801e_b2)

    n_inst = ConstructorStats.detail_reg_inst()

    c1 = i801c_b1()
    assert type(c1) is I801C
    assert c1.a == 1
    assert c1.b == 2

    d1 = i801d_b1()
    assert type(d1) is I801D
    assert d1.a == 1
    assert d1.b == 2

    assert ConstructorStats.detail_reg_inst() == n_inst + 4

    c2 = i801c_b2()
    assert type(c2) is I801C
    assert c2.a == 1
    assert c2.b == 2

    d2 = i801d_b2()
    assert type(d2) is I801D
    assert d2.a == 1
    assert d2.b == 2

    assert ConstructorStats.detail_reg_inst() == n_inst + 8

    del c2
    assert ConstructorStats.detail_reg_inst() == n_inst + 6
    del c1, d1, d2
    assert ConstructorStats.detail_reg_inst() == n_inst

    # Returning an unregistered derived type with a registered base; we won't
    # pick up the derived type, obviously, but should still work (as an object
    # of whatever type was returned).
    e1 = i801e_c()
    assert type(e1) is I801C
    assert e1.a == 1
    assert e1.b == 2

    e2 = i801e_b2()
    assert type(e2) is I801B2
    assert e2.b == 2
Exemplo n.º 18
0
def test_methods_and_attributes():
    instance1 = m.ExampleMandA()
    instance2 = m.ExampleMandA(32)

    instance1.add1(instance2)
    instance1.add2(instance2)
    instance1.add3(instance2)
    instance1.add4(instance2)
    instance1.add5(instance2)
    instance1.add6(32)
    instance1.add7(32)
    instance1.add8(32)
    instance1.add9(32)
    instance1.add10(32)

    assert str(instance1) == "ExampleMandA[value=320]"
    assert str(instance2) == "ExampleMandA[value=32]"
    assert str(instance1.self1()) == "ExampleMandA[value=320]"
    assert str(instance1.self2()) == "ExampleMandA[value=320]"
    assert str(instance1.self3()) == "ExampleMandA[value=320]"
    assert str(instance1.self4()) == "ExampleMandA[value=320]"
    assert str(instance1.self5()) == "ExampleMandA[value=320]"

    assert instance1.internal1() == 320
    assert instance1.internal2() == 320
    assert instance1.internal3() == 320
    assert instance1.internal4() == 320
    assert instance1.internal5() == 320

    assert instance1.overloaded() == "()"
    assert instance1.overloaded(0) == "(int)"
    assert instance1.overloaded(1, 1.0) == "(int, float)"
    assert instance1.overloaded(2.0, 2) == "(float, int)"
    assert instance1.overloaded(3,   3) == "(int, int)"
    assert instance1.overloaded(4., 4.) == "(float, float)"
    assert instance1.overloaded_const(-3) == "(int) const"
    assert instance1.overloaded_const(5, 5.0) == "(int, float) const"
    assert instance1.overloaded_const(6.0, 6) == "(float, int) const"
    assert instance1.overloaded_const(7,   7) == "(int, int) const"
    assert instance1.overloaded_const(8., 8.) == "(float, float) const"
    assert instance1.overloaded_float(1, 1) == "(float, float)"
    assert instance1.overloaded_float(1, 1.) == "(float, float)"
    assert instance1.overloaded_float(1., 1) == "(float, float)"
    assert instance1.overloaded_float(1., 1.) == "(float, float)"

    assert instance1.value == 320
    instance1.value = 100
    assert str(instance1) == "ExampleMandA[value=100]"

    cstats = ConstructorStats.get(m.ExampleMandA)
    assert cstats.alive() == 2
    del instance1, instance2
    assert cstats.alive() == 0
    assert cstats.values() == ["32"]
    assert cstats.default_constructions == 1
    assert cstats.copy_constructions == 3
    assert cstats.move_constructions >= 1
    assert cstats.copy_assignments == 0
    assert cstats.move_assignments == 0
Exemplo n.º 19
0
def test_large_holder():
    from pybind11_tests import MyObject5
    o = MyObject5(5)
    assert o.value == 5
    cstats = ConstructorStats.get(MyObject5)
    assert cstats.alive() == 1
    del o
    assert cstats.alive() == 0
def test_alive_gc_derived(capture):
    class Derived(m.Parent):
        pass

    n_inst = ConstructorStats.detail_reg_inst()
    p = Derived()
    p.addChildKeepAlive(m.Child())
    assert ConstructorStats.detail_reg_inst() == n_inst + 2
    lst = [p]
    lst.append(lst)  # creates a circular reference
    with capture:
        del p, lst
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert (capture == """
        Releasing parent.
        Releasing child.
    """)
def test_keep_alive_constructor(capture):
    n_inst = ConstructorStats.detail_reg_inst()

    with capture:
        p = m.Parent(m.Child())
        assert ConstructorStats.detail_reg_inst() == n_inst + 2
    assert (capture == """
        Allocating child.
        Allocating parent.
    """)
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert (capture == """
        Releasing parent.
        Releasing child.
    """)
Exemplo n.º 22
0
def test_alive_gc_multi_derived(capture):
    class Derived(m.Parent, m.Child):
        def __init__(self):
            m.Parent.__init__(self)
            m.Child.__init__(self)

    n_inst = ConstructorStats.detail_reg_inst()
    p = Derived()
    p.addChildKeepAlive(m.Child())
    # +3 rather than +2 because Derived corresponds to two registered instances
    assert ConstructorStats.detail_reg_inst() == n_inst + 3
    lst = [p]
    lst.append(lst)   # creates a circular reference
    with capture:
        del p, lst
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == """
Exemplo n.º 23
0
def test_alive_gc_multi_derived(capture):
    class Derived(m.Parent, m.Child):
        def __init__(self):
            m.Parent.__init__(self)
            m.Child.__init__(self)

    n_inst = ConstructorStats.detail_reg_inst()
    p = Derived()
    p.addChildKeepAlive(m.Child())
    # +3 rather than +2 because Derived corresponds to two registered instances
    assert ConstructorStats.detail_reg_inst() == n_inst + 3
    lst = [p]
    lst.append(lst)  # creates a circular reference
    with capture:
        del p, lst
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == """
Exemplo n.º 24
0
def test_alive_gc_multi_derived(capture):
    from pybind11_tests import Parent, Child, ConstructorStats

    class Derived(Parent, Child):
        pass

    n_inst = ConstructorStats.detail_reg_inst()
    p = Derived()
    p.addChildKeepAlive(Child())
    # +3 rather than +2 because Derived corresponds to two registered instances
    assert ConstructorStats.detail_reg_inst() == n_inst + 3
    lst = [p]
    lst.append(lst)   # creates a circular reference
    with capture:
        del p, lst
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == """
Exemplo n.º 25
0
def test_move_only_holder():
    from pybind11_tests.smart_ptr import TypeWithMoveOnlyHolder

    a = TypeWithMoveOnlyHolder.make()
    stats = ConstructorStats.get(TypeWithMoveOnlyHolder)
    assert stats.alive() == 1
    del a
    assert stats.alive() == 0
Exemplo n.º 26
0
def test_move_support():
    from pybind11_tests import NCVirt, NonCopyable, Movable

    class NCVirtExt(NCVirt):
        def get_noncopyable(self, a, b):
            # Constructs and returns a new instance:
            nc = NonCopyable(a * a, b * b)
            return nc

        def get_movable(self, a, b):
            # Return a referenced copy
            self.movable = Movable(a, b)
            return self.movable

    class NCVirtExt2(NCVirt):
        def get_noncopyable(self, a, b):
            # Keep a reference: this is going to throw an exception
            self.nc = NonCopyable(a, b)
            return self.nc

        def get_movable(self, a, b):
            # Return a new instance without storing it
            return Movable(a, b)

    ncv1 = NCVirtExt()
    assert ncv1.print_nc(2, 3) == "36"
    assert ncv1.print_movable(4, 5) == "9"
    ncv2 = NCVirtExt2()
    assert ncv2.print_movable(7, 7) == "14"
    # Don't check the exception message here because it differs under debug/non-debug mode
    with pytest.raises(RuntimeError):
        ncv2.print_nc(9, 9)

    nc_stats = ConstructorStats.get(NonCopyable)
    mv_stats = ConstructorStats.get(Movable)
    assert nc_stats.alive() == 1
    assert mv_stats.alive() == 1
    del ncv1, ncv2
    assert nc_stats.alive() == 0
    assert mv_stats.alive() == 0
    assert nc_stats.values() == ['4', '9', '9', '9']
    assert mv_stats.values() == ['4', '5', '7', '7']
    assert nc_stats.copy_constructions == 0
    assert mv_stats.copy_constructions == 1
    assert nc_stats.move_constructions >= 0
    assert mv_stats.move_constructions >= 0
def test_move_support():
    from pybind11_tests import NCVirt, NonCopyable, Movable

    class NCVirtExt(NCVirt):
        def get_noncopyable(self, a, b):
            # Constructs and returns a new instance:
            nc = NonCopyable(a * a, b * b)
            return nc

        def get_movable(self, a, b):
            # Return a referenced copy
            self.movable = Movable(a, b)
            return self.movable

    class NCVirtExt2(NCVirt):
        def get_noncopyable(self, a, b):
            # Keep a reference: this is going to throw an exception
            self.nc = NonCopyable(a, b)
            return self.nc

        def get_movable(self, a, b):
            # Return a new instance without storing it
            return Movable(a, b)

    ncv1 = NCVirtExt()
    assert ncv1.print_nc(2, 3) == "36"
    assert ncv1.print_movable(4, 5) == "9"
    ncv2 = NCVirtExt2()
    assert ncv2.print_movable(7, 7) == "14"
    # Don't check the exception message here because it differs under debug/non-debug mode
    with pytest.raises(RuntimeError):
        ncv2.print_nc(9, 9)

    nc_stats = ConstructorStats.get(NonCopyable)
    mv_stats = ConstructorStats.get(Movable)
    assert nc_stats.alive() == 1
    assert mv_stats.alive() == 1
    del ncv1, ncv2
    assert nc_stats.alive() == 0
    assert mv_stats.alive() == 0
    assert nc_stats.values() == ['4', '9', '9', '9']
    assert mv_stats.values() == ['4', '5', '7', '7']
    assert nc_stats.copy_constructions == 0
    assert mv_stats.copy_constructions == 1
    assert nc_stats.move_constructions >= 0
    assert mv_stats.move_constructions >= 0
def test_mi_base_return():
    """Tests returning an offset (non-first MI) base class pointer to a derived instance"""

    n_inst = ConstructorStats.detail_reg_inst()

    c1 = m.i801c_b1()
    assert type(c1) is m.I801C
    assert c1.a == 1
    assert c1.b == 2

    d1 = m.i801d_b1()
    assert type(d1) is m.I801D
    assert d1.a == 1
    assert d1.b == 2

    assert ConstructorStats.detail_reg_inst() == n_inst + 4

    c2 = m.i801c_b2()
    assert type(c2) is m.I801C
    assert c2.a == 1
    assert c2.b == 2

    d2 = m.i801d_b2()
    assert type(d2) is m.I801D
    assert d2.a == 1
    assert d2.b == 2

    assert ConstructorStats.detail_reg_inst() == n_inst + 8

    del c2
    assert ConstructorStats.detail_reg_inst() == n_inst + 6
    del c1, d1, d2
    assert ConstructorStats.detail_reg_inst() == n_inst

    # Returning an unregistered derived type with a registered base; we won't
    # pick up the derived type, obviously, but should still work (as an object
    # of whatever type was returned).
    e1 = m.i801e_c()
    assert type(e1) is m.I801C
    assert e1.a == 1
    assert e1.b == 2

    e2 = m.i801e_b2()
    assert type(e2) is m.I801B2
    assert e2.b == 2
Exemplo n.º 29
0
def test_operator_overloading():
    v1 = m.Vector2(1, 2)
    v2 = m.Vector(3, -1)
    assert str(v1) == "[1.000000, 2.000000]"
    assert str(v2) == "[3.000000, -1.000000]"

    assert str(-v2) == "[-3.000000, 1.000000]"

    assert str(v1 + v2) == "[4.000000, 1.000000]"
    assert str(v1 - v2) == "[-2.000000, 3.000000]"
    assert str(v1 - 8) == "[-7.000000, -6.000000]"
    assert str(v1 + 8) == "[9.000000, 10.000000]"
    assert str(v1 * 8) == "[8.000000, 16.000000]"
    assert str(v1 / 8) == "[0.125000, 0.250000]"
    assert str(8 - v1) == "[7.000000, 6.000000]"
    assert str(8 + v1) == "[9.000000, 10.000000]"
    assert str(8 * v1) == "[8.000000, 16.000000]"
    assert str(8 / v1) == "[8.000000, 4.000000]"
    assert str(v1 * v2) == "[3.000000, -2.000000]"
    assert str(v2 / v1) == "[3.000000, -0.500000]"

    v1 += 2 * v2
    assert str(v1) == "[7.000000, 0.000000]"
    v1 -= v2
    assert str(v1) == "[4.000000, 1.000000]"
    v1 *= 2
    assert str(v1) == "[8.000000, 2.000000]"
    v1 /= 16
    assert str(v1) == "[0.500000, 0.125000]"
    v1 *= v2
    assert str(v1) == "[1.500000, -0.125000]"
    v2 /= v1
    assert str(v2) == "[2.000000, 8.000000]"

    assert hash(v1) == 4

    cstats = ConstructorStats.get(m.Vector2)
    assert cstats.alive() == 2
    del v1
    assert cstats.alive() == 1
    del v2
    assert cstats.alive() == 0
    assert cstats.values() == [
        '[1.000000, 2.000000]', '[3.000000, -1.000000]',
        '[-3.000000, 1.000000]', '[4.000000, 1.000000]',
        '[-2.000000, 3.000000]', '[-7.000000, -6.000000]',
        '[9.000000, 10.000000]', '[8.000000, 16.000000]',
        '[0.125000, 0.250000]', '[7.000000, 6.000000]',
        '[9.000000, 10.000000]', '[8.000000, 16.000000]',
        '[8.000000, 4.000000]', '[3.000000, -2.000000]',
        '[3.000000, -0.500000]', '[6.000000, -2.000000]'
    ]
    assert cstats.default_constructions == 0
    assert cstats.copy_constructions == 0
    assert cstats.move_constructions >= 10
    assert cstats.copy_assignments == 0
    assert cstats.move_assignments == 0
Exemplo n.º 30
0
def test_unique_nodelete4a():
    o = m.MyObject4a(23)
    assert o.value == 23
    cstats = ConstructorStats.get(m.MyObject4a)
    assert cstats.alive() == 1
    del o
    assert cstats.alive() == 1
    m.MyObject4a.cleanup_all_instances()
    assert cstats.alive() == 0
Exemplo n.º 31
0
def test_move_only_holder():
    a = m.TypeWithMoveOnlyHolder.make()
    b = m.TypeWithMoveOnlyHolder.make_as_object()
    stats = ConstructorStats.get(m.TypeWithMoveOnlyHolder)
    assert stats.alive() == 2
    del b
    assert stats.alive() == 1
    del a
    assert stats.alive() == 0
def test_init_factory_basic():
    """Tests py::init_factory() wrapper around various ways of returning the object"""

    cstats = [
        ConstructorStats.get(c)
        for c in [m.TestFactory1, m.TestFactory2, m.TestFactory3]
    ]
    cstats[0].alive()  # force gc
    n_inst = ConstructorStats.detail_reg_inst()

    x1 = m.TestFactory1(tag.unique_ptr, 3)
    assert x1.value == "3"
    y1 = m.TestFactory1(tag.pointer)
    assert y1.value == "(empty)"
    z1 = m.TestFactory1("hi!")
    assert z1.value == "hi!"

    assert ConstructorStats.detail_reg_inst() == n_inst + 3

    x2 = m.TestFactory2(tag.move)
    assert x2.value == "(empty2)"
    y2 = m.TestFactory2(tag.pointer, 7)
    assert y2.value == "7"
    z2 = m.TestFactory2(tag.unique_ptr, "hi again")
    assert z2.value == "hi again"

    assert ConstructorStats.detail_reg_inst() == n_inst + 6

    x3 = m.TestFactory3(tag.shared_ptr)
    assert x3.value == "(empty3)"
    y3 = m.TestFactory3(tag.pointer, 42)
    assert y3.value == "42"
    z3 = m.TestFactory3("bye")
    assert z3.value == "bye"

    for null_ptr_kind in [
            tag.null_ptr, tag.null_unique_ptr, tag.null_shared_ptr
    ]:
        with pytest.raises(TypeError) as excinfo:
            m.TestFactory3(null_ptr_kind)
        assert (str(excinfo.value) ==
                "pybind11::init(): factory function returned nullptr")

    assert [i.alive() for i in cstats] == [3, 3, 3]
    assert ConstructorStats.detail_reg_inst() == n_inst + 9

    del x1, y2, y3, z3
    assert [i.alive() for i in cstats] == [2, 2, 1]
    assert ConstructorStats.detail_reg_inst() == n_inst + 5
    del x2, x3, y1, z1, z2
    assert [i.alive() for i in cstats] == [0, 0, 0]
    assert ConstructorStats.detail_reg_inst() == n_inst

    assert [i.values() for i in cstats] == [
        ["3", "hi!"],
        ["7", "hi again"],
        ["42", "bye"],
    ]
    assert [i.default_constructions for i in cstats] == [1, 1, 1]
Exemplo n.º 33
0
def test_methods_and_attributes():
    instance1 = ExampleMandA()
    instance2 = ExampleMandA(32)

    instance1.add1(instance2)
    instance1.add2(instance2)
    instance1.add3(instance2)
    instance1.add4(instance2)
    instance1.add5(instance2)
    instance1.add6(32)
    instance1.add7(32)
    instance1.add8(32)
    instance1.add9(32)
    instance1.add10(32)

    assert str(instance1) == "ExampleMandA[value=320]"
    assert str(instance2) == "ExampleMandA[value=32]"
    assert str(instance1.self1()) == "ExampleMandA[value=320]"
    assert str(instance1.self2()) == "ExampleMandA[value=320]"
    assert str(instance1.self3()) == "ExampleMandA[value=320]"
    assert str(instance1.self4()) == "ExampleMandA[value=320]"
    assert str(instance1.self5()) == "ExampleMandA[value=320]"

    assert instance1.internal1() == 320
    assert instance1.internal2() == 320
    assert instance1.internal3() == 320
    assert instance1.internal4() == 320
    assert instance1.internal5() == 320

    assert instance1.overloaded(1, 1.0) == "(int, float)"
    assert instance1.overloaded(2.0, 2) == "(float, int)"
    assert instance1.overloaded(3, 3) == "(int, int)"
    assert instance1.overloaded(4., 4.) == "(float, float)"
    assert instance1.overloaded_const(5, 5.0) == "(int, float) const"
    assert instance1.overloaded_const(6.0, 6) == "(float, int) const"
    assert instance1.overloaded_const(7, 7) == "(int, int) const"
    assert instance1.overloaded_const(8., 8.) == "(float, float) const"
    assert instance1.overloaded_float(1, 1) == "(float, float)"
    assert instance1.overloaded_float(1, 1.) == "(float, float)"
    assert instance1.overloaded_float(1., 1) == "(float, float)"
    assert instance1.overloaded_float(1., 1.) == "(float, float)"

    assert instance1.value == 320
    instance1.value = 100
    assert str(instance1) == "ExampleMandA[value=100]"

    cstats = ConstructorStats.get(ExampleMandA)
    assert cstats.alive() == 2
    del instance1, instance2
    assert cstats.alive() == 0
    assert cstats.values() == ["32"]
    assert cstats.default_constructions == 1
    assert cstats.copy_constructions == 3
    assert cstats.move_constructions >= 1
    assert cstats.copy_assignments == 0
    assert cstats.move_assignments == 0
Exemplo n.º 34
0
def test_move_only_holder():
    from pybind11_tests.smart_ptr import TypeWithMoveOnlyHolder

    a = TypeWithMoveOnlyHolder.make()
    stats = ConstructorStats.get(TypeWithMoveOnlyHolder)
    if stats.alive() != 1:
        raise AssertionError
    del a
    if stats.alive() != 0:
        raise AssertionError
def test_dynamic_attributes():
    from pybind11_tests import DynamicClass, CppDerivedDynamicClass

    instance = DynamicClass()
    if hasattr(instance, "foo"):
        raise AssertionError
    if "foo" in dir(instance):
        raise AssertionError

    # Dynamically add attribute
    instance.foo = 42
    if not hasattr(instance, "foo"):
        raise AssertionError
    if instance.foo != 42:
        raise AssertionError
    if "foo" not in dir(instance):
        raise AssertionError

    # __dict__ should be accessible and replaceable
    if "foo" not in instance.__dict__:
        raise AssertionError
    instance.__dict__ = {"bar": True}
    if hasattr(instance, "foo"):
        raise AssertionError
    if not hasattr(instance, "bar"):
        raise AssertionError

    with pytest.raises(TypeError) as excinfo:
        instance.__dict__ = []
    if str(excinfo.value
           ) != "__dict__ must be set to a dictionary, not a 'list'":
        raise AssertionError

    cstats = ConstructorStats.get(DynamicClass)
    if cstats.alive() != 1:
        raise AssertionError
    del instance
    if cstats.alive() != 0:
        raise AssertionError

    # Derived classes should work as well
    class PythonDerivedDynamicClass(DynamicClass):
        pass

    for cls in CppDerivedDynamicClass, PythonDerivedDynamicClass:
        derived = cls()
        derived.foobar = 100
        if derived.foobar != 100:
            raise AssertionError

        if cstats.alive() != 1:
            raise AssertionError
        del derived
        if cstats.alive() != 0:
            raise AssertionError
def test_sequence():
    from pybind11_tests import ConstructorStats
    from pybind11_tests.sequences_and_iterators import Sequence

    cstats = ConstructorStats.get(Sequence)

    s = Sequence(5)
    assert cstats.values() == ['of size', '5']

    assert "Sequence" in repr(s)
    assert len(s) == 5
    assert s[0] == 0 and s[3] == 0
    assert 12.34 not in s
    s[0], s[3] = 12.34, 56.78
    assert 12.34 in s
    assert isclose(s[0], 12.34) and isclose(s[3], 56.78)

    rev = reversed(s)
    assert cstats.values() == ['of size', '5']

    rev2 = s[::-1]
    assert cstats.values() == ['of size', '5']

    it = iter(Sequence(0))
    for _ in range(3):  # __next__ must continue to raise StopIteration
        with pytest.raises(StopIteration):
            next(it)
    assert cstats.values() == ['of size', '0']

    expected = [0, 56.78, 0, 0, 12.34]
    assert allclose(rev, expected)
    assert allclose(rev2, expected)
    assert rev == rev2

    rev[0::2] = Sequence([2.0, 2.0, 2.0])
    assert cstats.values() == ['of size', '3', 'from std::vector']

    assert allclose(rev, [2, 56.78, 2, 0, 2])

    assert cstats.alive() == 4
    del it
    assert cstats.alive() == 3
    del s
    assert cstats.alive() == 2
    del rev
    assert cstats.alive() == 1
    del rev2
    assert cstats.alive() == 0

    assert cstats.values() == []
    assert cstats.default_constructions == 0
    assert cstats.copy_constructions == 0
    assert cstats.move_constructions >= 1
    assert cstats.copy_assignments == 0
    assert cstats.move_assignments == 0
Exemplo n.º 37
0
def test_shared_ptr_from_this_and_references():
    from pybind11_tests.smart_ptr import SharedFromThisRef, B

    s = SharedFromThisRef()
    stats = ConstructorStats.get(B)
    if stats.alive() != 2:
        raise AssertionError

    ref = s.ref  # init_holder_helper(holder_ptr=false, owned=false, bad_wp=false)
    if stats.alive() != 2:
        raise AssertionError
    if not s.set_ref(ref):
        raise AssertionError
    if not s.set_holder(ref):
        raise AssertionError

    bad_wp = s.bad_wp  # init_holder_helper(holder_ptr=false, owned=false, bad_wp=true)
    if stats.alive() != 2:
        raise AssertionError
    if not s.set_ref(bad_wp):
        raise AssertionError
    with pytest.raises(RuntimeError) as excinfo:
        if not s.set_holder(bad_wp):
            raise AssertionError
    if "Unable to cast from non-held to held instance" not in str(
            excinfo.value):
        raise AssertionError

    copy = s.copy  # init_holder_helper(holder_ptr=false, owned=true, bad_wp=false)
    if stats.alive() != 3:
        raise AssertionError
    if not s.set_ref(copy):
        raise AssertionError
    if not s.set_holder(copy):
        raise AssertionError

    holder_ref = s.holder_ref  # init_holder_helper(holder_ptr=true, owned=false, bad_wp=false)
    if stats.alive() != 3:
        raise AssertionError
    if not s.set_ref(holder_ref):
        raise AssertionError
    if not s.set_holder(holder_ref):
        raise AssertionError

    holder_copy = s.holder_copy  # init_holder_helper(holder_ptr=true, owned=true, bad_wp=false)
    if stats.alive() != 3:
        raise AssertionError
    if not s.set_ref(holder_copy):
        raise AssertionError
    if not s.set_holder(holder_copy):
        raise AssertionError

    del ref, bad_wp, copy, holder_ref, holder_copy, s
    if stats.alive() != 0:
        raise AssertionError
Exemplo n.º 38
0
def test_enable_shared_from_this_with_reference_rvp():
    """ Issue #471: shared pointer instance not dellocated """
    from pybind11_tests import SharedParent, SharedChild

    parent = SharedParent()
    child = parent.get_child()

    cstats = ConstructorStats.get(SharedChild)
    assert cstats.alive() == 1
    del child, parent
    assert cstats.alive() == 0
Exemplo n.º 39
0
def test_enable_shared_from_this_with_reference_rvp():
    """ Issue #471: shared pointer instance not dellocated """
    from pybind11_tests import SharedParent, SharedChild

    parent = SharedParent()
    child = parent.get_child()

    cstats = ConstructorStats.get(SharedChild)
    assert cstats.alive() == 1
    del child, parent
    assert cstats.alive() == 0
Exemplo n.º 40
0
def test_instance(msg):
    with pytest.raises(TypeError) as excinfo:
        m.NoConstructor()
    assert msg(excinfo.value) == "m.class_.NoConstructor: No constructor defined!"

    instance = m.NoConstructor.new_instance()

    cstats = ConstructorStats.get(m.NoConstructor)
    assert cstats.alive() == 1
    del instance
    assert cstats.alive() == 0
Exemplo n.º 41
0
def test_instance(msg):
    with pytest.raises(TypeError) as excinfo:
        m.NoConstructor()
    assert msg(excinfo.value) == "m.class_.NoConstructor: No constructor defined!"

    instance = m.NoConstructor.new_instance()

    cstats = ConstructorStats.get(m.NoConstructor)
    assert cstats.alive() == 1
    del instance
    assert cstats.alive() == 0
Exemplo n.º 42
0
def test_move_only_holder_with_addressof_operator():
    a = m.TypeForMoveOnlyHolderWithAddressOf.make()
    a.print_object()

    stats = ConstructorStats.get(m.TypeForMoveOnlyHolderWithAddressOf)
    assert stats.alive() == 1

    a.value = 42
    assert a.value == 42

    del a
    assert stats.alive() == 0
Exemplo n.º 43
0
def test_operator_overloading():
    from pybind11_tests import Vector2, Vector, ConstructorStats

    v1 = Vector2(1, 2)
    v2 = Vector(3, -1)
    assert str(v1) == "[1.000000, 2.000000]"
    assert str(v2) == "[3.000000, -1.000000]"

    assert str(v1 + v2) == "[4.000000, 1.000000]"
    assert str(v1 - v2) == "[-2.000000, 3.000000]"
    assert str(v1 - 8) == "[-7.000000, -6.000000]"
    assert str(v1 + 8) == "[9.000000, 10.000000]"
    assert str(v1 * 8) == "[8.000000, 16.000000]"
    assert str(v1 / 8) == "[0.125000, 0.250000]"
    assert str(8 - v1) == "[7.000000, 6.000000]"
    assert str(8 + v1) == "[9.000000, 10.000000]"
    assert str(8 * v1) == "[8.000000, 16.000000]"
    assert str(8 / v1) == "[8.000000, 4.000000]"
    assert str(v1 * v2) == "[3.000000, -2.000000]"
    assert str(v2 / v1) == "[3.000000, -0.500000]"

    v1 += 2 * v2
    assert str(v1) == "[7.000000, 0.000000]"
    v1 -= v2
    assert str(v1) == "[4.000000, 1.000000]"
    v1 *= 2
    assert str(v1) == "[8.000000, 2.000000]"
    v1 /= 16
    assert str(v1) == "[0.500000, 0.125000]"
    v1 *= v2
    assert str(v1) == "[1.500000, -0.125000]"
    v2 /= v1
    assert str(v2) == "[2.000000, 8.000000]"

    cstats = ConstructorStats.get(Vector2)
    assert cstats.alive() == 2
    del v1
    assert cstats.alive() == 1
    del v2
    assert cstats.alive() == 0
    assert cstats.values() == ['[1.000000, 2.000000]', '[3.000000, -1.000000]',
                               '[4.000000, 1.000000]', '[-2.000000, 3.000000]',
                               '[-7.000000, -6.000000]', '[9.000000, 10.000000]',
                               '[8.000000, 16.000000]', '[0.125000, 0.250000]',
                               '[7.000000, 6.000000]', '[9.000000, 10.000000]',
                               '[8.000000, 16.000000]', '[8.000000, 4.000000]',
                               '[3.000000, -2.000000]', '[3.000000, -0.500000]',
                               '[6.000000, -2.000000]']
    assert cstats.default_constructions == 0
    assert cstats.copy_constructions == 0
    assert cstats.move_constructions >= 10
    assert cstats.copy_assignments == 0
    assert cstats.move_assignments == 0
Exemplo n.º 44
0
def test_move_only_holder_with_addressof_operator():
    a = m.TypeForMoveOnlyHolderWithAddressOf.make()
    a.print_object()

    stats = ConstructorStats.get(m.TypeForMoveOnlyHolderWithAddressOf)
    assert stats.alive() == 1

    a.value = 42
    assert a.value == 42

    del a
    assert stats.alive() == 0
def test_sequence():
    cstats = ConstructorStats.get(m.Sequence)

    s = m.Sequence(5)
    assert cstats.values() == ["of size", "5"]

    assert "Sequence" in repr(s)
    assert len(s) == 5
    assert s[0] == 0 and s[3] == 0
    assert 12.34 not in s
    s[0], s[3] = 12.34, 56.78
    assert 12.34 in s
    assert s[0] == approx(12.34, rel=1e-05)
    assert s[3] == approx(56.78, rel=1e-05)

    rev = reversed(s)
    assert cstats.values() == ["of size", "5"]

    rev2 = s[::-1]
    assert cstats.values() == ["of size", "5"]

    it = iter(m.Sequence(0))
    for _ in range(3):  # __next__ must continue to raise StopIteration
        with pytest.raises(StopIteration):
            next(it)
    assert cstats.values() == ["of size", "0"]

    expected = [0, 56.78, 0, 0, 12.34]
    assert rev == approx(expected, rel=1e-05)
    assert rev2 == approx(expected, rel=1e-05)
    assert rev == rev2

    rev[0::2] = m.Sequence([2.0, 2.0, 2.0])
    assert cstats.values() == ["of size", "3", "from std::vector"]

    assert rev == approx([2, 56.78, 2, 0, 2], rel=1e-05)

    assert cstats.alive() == 4
    del it
    assert cstats.alive() == 3
    del s
    assert cstats.alive() == 2
    del rev
    assert cstats.alive() == 1
    del rev2
    assert cstats.alive() == 0

    assert cstats.values() == []
    assert cstats.default_constructions == 0
    assert cstats.copy_constructions == 0
    assert cstats.move_constructions >= 1
    assert cstats.copy_assignments == 0
    assert cstats.move_assignments == 0
Exemplo n.º 46
0
def test_shared_from_this_copy():
    s = m.SharedFromThisRef()
    stats = ConstructorStats.get(m.B)
    assert stats.alive() == 2

    copy = s.copy  # init_holder_helper(holder_ptr=false, owned=true, bad_wp=false)
    # RuntimeError: Invalid return_value_policy for shared_ptr.
    assert stats.alive() == 3
    assert s.set_ref(copy)
    assert s.set_holder(copy)
    del copy, s
    assert stats.alive() == 0
Exemplo n.º 47
0
def test_override(capture, msg):
    from pybind11_tests import (ExampleVirt, runExampleVirt,
                                runExampleVirtVirtual, runExampleVirtBool)

    class ExtendedExampleVirt(ExampleVirt):
        def __init__(self, state):
            super(ExtendedExampleVirt, self).__init__(state + 1)
            self.data = "Hello world"

        def run(self, value):
            print('ExtendedExampleVirt::run(%i), calling parent..' % value)
            return super(ExtendedExampleVirt, self).run(value + 1)

        def run_bool(self):
            print('ExtendedExampleVirt::run_bool()')
            return False

        def pure_virtual(self):
            print('ExtendedExampleVirt::pure_virtual(): %s' % self.data)

    ex12 = ExampleVirt(10)
    with capture:
        assert runExampleVirt(ex12, 20) == 30
    assert capture == "Original implementation of ExampleVirt::run(state=10, value=20)"

    with pytest.raises(RuntimeError) as excinfo:
        runExampleVirtVirtual(ex12)
    assert msg(
        excinfo.value
    ) == 'Tried to call pure virtual function "ExampleVirt::pure_virtual"'

    ex12p = ExtendedExampleVirt(10)
    with capture:
        assert runExampleVirt(ex12p, 20) == 32
    assert capture == """
        ExtendedExampleVirt::run(20), calling parent..
        Original implementation of ExampleVirt::run(state=11, value=21)
    """
    with capture:
        assert runExampleVirtBool(ex12p) is False
    assert capture == "ExtendedExampleVirt::run_bool()"
    with capture:
        runExampleVirtVirtual(ex12p)
    assert capture == "ExtendedExampleVirt::pure_virtual(): Hello world"

    cstats = ConstructorStats.get(ExampleVirt)
    assert cstats.alive() == 2
    del ex12, ex12p
    assert cstats.alive() == 0
    assert cstats.values() == ['10', '11']
    assert cstats.copy_constructions == 0
    assert cstats.move_constructions >= 0
Exemplo n.º 48
0
def test_shared_from_this_ref():
    s = m.SharedFromThisRef()
    stats = ConstructorStats.get(m.B)
    assert stats.alive() == 2

    ref = s.ref  # init_holder_helper(holder_ptr=false, owned=false, bad_wp=false)
    assert stats.alive() == 2
    assert s.set_ref(ref)
    assert s.set_holder(
        ref
    )  # std::enable_shared_from_this can create a holder from a reference
    del ref, s
    assert stats.alive() == 0
Exemplo n.º 49
0
def test_shared_from_this_bad_wp():
    s = m.SharedFromThisRef()
    stats = ConstructorStats.get(m.B)
    assert stats.alive() == 2

    bad_wp = s.bad_wp  # init_holder_helper(holder_ptr=false, owned=false, bad_wp=true)
    assert stats.alive() == 2
    assert s.set_ref(bad_wp)
    with pytest.raises(RuntimeError) as excinfo:
        assert s.set_holder(bad_wp)
    assert str(excinfo.value) == "Non-owning holder (loaded_as_shared_ptr)."
    del bad_wp, s
    assert stats.alive() == 0
Exemplo n.º 50
0
def assert_keeps_alive(cl, method, *args):
    cstats = ConstructorStats.get(cl)
    start_with = cstats.alive()
    a = cl()
    assert cstats.alive() == start_with + 1
    z = method(a, *args)
    assert cstats.alive() == start_with + 1
    del a
    # Here's the keep alive in action:
    assert cstats.alive() == start_with + 1
    del z
    # Keep alive should have expired:
    assert cstats.alive() == start_with
Exemplo n.º 51
0
def assert_keeps_alive(cl, method, *args):
    cstats = ConstructorStats.get(cl)
    start_with = cstats.alive()
    a = cl()
    assert cstats.alive() == start_with + 1
    z = method(a, *args)
    assert cstats.alive() == start_with + 1
    del a
    # Here's the keep alive in action:
    assert cstats.alive() == start_with + 1
    del z
    # Keep alive should have expired:
    assert cstats.alive() == start_with
Exemplo n.º 52
0
def test_pointers(msg):
    living_before = ConstructorStats.get(UserType).alive()
    assert m.get_void_ptr_value(m.return_void_ptr()) == 0x1234
    assert m.get_void_ptr_value(
        UserType())  # Should also work for other C++ types
    assert ConstructorStats.get(UserType).alive() == living_before

    with pytest.raises(TypeError) as excinfo:
        m.get_void_ptr_value([1, 2, 3])  # This should not work
    assert msg(excinfo.value) == """
        get_void_ptr_value(): incompatible function arguments. The following argument types are supported:
            1. (arg0: capsule) -> int

        Invoked with: [1, 2, 3]
    """  # noqa: E501 line too long

    assert m.return_null_str() is None
    assert m.get_null_str_value(m.return_null_str()) is not None

    ptr = m.return_unique_ptr()
    assert "StringList" in repr(ptr)
    assert m.print_opaque_list(ptr) == "Opaque list: [some value]"
Exemplo n.º 53
0
def test_shared_from_this_holder_ref():
    s = m.SharedFromThisRef()
    stats = ConstructorStats.get(m.B)
    assert stats.alive() == 2

    holder_ref = (
        s.holder_ref
    )  # init_holder_helper(holder_ptr=true, owned=false, bad_wp=false)
    assert stats.alive() == 2
    assert s.set_ref(holder_ref)
    assert s.set_holder(holder_ref)
    del holder_ref, s
    assert stats.alive() == 0
Exemplo n.º 54
0
def test_mi_unaligned_base():
    """Returning an offset (non-first MI) base class pointer should recognize the instance"""

    n_inst = ConstructorStats.detail_reg_inst()

    c = m.I801C()
    d = m.I801D()
    # + 4 below because we have the two instances, and each instance has offset base I801B2
    assert ConstructorStats.detail_reg_inst() == n_inst + 4
    b1c = m.i801b1_c(c)
    assert b1c is c
    b2c = m.i801b2_c(c)
    assert b2c is c
    b1d = m.i801b1_d(d)
    assert b1d is d
    b2d = m.i801b2_d(d)
    assert b2d is d

    assert ConstructorStats.detail_reg_inst() == n_inst + 4  # no extra instances
    del c, b1c, b2c
    assert ConstructorStats.detail_reg_inst() == n_inst + 2
    del d, b1d, b2d
    assert ConstructorStats.detail_reg_inst() == n_inst
Exemplo n.º 55
0
def test_mi_unaligned_base():
    """Returning an offset (non-first MI) base class pointer should recognize the instance"""

    n_inst = ConstructorStats.detail_reg_inst()

    c = m.I801C()
    d = m.I801D()
    # + 4 below because we have the two instances, and each instance has offset base I801B2
    assert ConstructorStats.detail_reg_inst() == n_inst + 4
    b1c = m.i801b1_c(c)
    assert b1c is c
    b2c = m.i801b2_c(c)
    assert b2c is c
    b1d = m.i801b1_d(d)
    assert b1d is d
    b2d = m.i801b2_d(d)
    assert b2d is d

    assert ConstructorStats.detail_reg_inst() == n_inst + 4  # no extra instances
    del c, b1c, b2c
    assert ConstructorStats.detail_reg_inst() == n_inst + 2
    del d, b1d, b2d
    assert ConstructorStats.detail_reg_inst() == n_inst
Exemplo n.º 56
0
def test_shared_ptr_from_this_and_references():
    s = m.SharedFromThisRef()
    stats = ConstructorStats.get(m.B)
    assert stats.alive() == 2

    ref = (s.ref
           )  # init_holder_helper(holder_ptr=false, owned=false, bad_wp=false)
    assert stats.alive() == 2
    assert s.set_ref(ref)
    assert s.set_holder(
        ref
    )  # std::enable_shared_from_this can create a holder from a reference

    bad_wp = (
        s.bad_wp
    )  # init_holder_helper(holder_ptr=false, owned=false, bad_wp=true)
    assert stats.alive() == 2
    assert s.set_ref(bad_wp)
    with pytest.raises(RuntimeError) as excinfo:
        assert s.set_holder(bad_wp)
    assert "Unable to cast from non-held to held instance" in str(
        excinfo.value)

    copy = (s.copy
            )  # init_holder_helper(holder_ptr=false, owned=true, bad_wp=false)
    assert stats.alive() == 3
    assert s.set_ref(copy)
    assert s.set_holder(copy)

    holder_ref = (
        s.holder_ref
    )  # init_holder_helper(holder_ptr=true, owned=false, bad_wp=false)
    assert stats.alive() == 3
    assert s.set_ref(holder_ref)
    assert s.set_holder(holder_ref)

    holder_copy = (
        s.holder_copy
    )  # init_holder_helper(holder_ptr=true, owned=true, bad_wp=false)
    assert stats.alive() == 3
    assert s.set_ref(holder_copy)
    assert s.set_holder(holder_copy)

    del ref, bad_wp, copy, holder_ref, holder_copy, s
    assert stats.alive() == 0

    z = m.SharedFromThisVirt.get()
    y = m.SharedFromThisVirt.get()
    assert y is z
Exemplo n.º 57
0
def test_keep_alive_return_value(capture):
    n_inst = ConstructorStats.detail_reg_inst()
    with capture:
        p = m.Parent()
    assert capture == "Allocating parent."
    with capture:
        p.returnChild()
        assert ConstructorStats.detail_reg_inst() == n_inst + 1
    assert (capture == """
        Allocating child.
        Releasing child.
    """)
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == "Releasing parent."

    with capture:
        p = m.Parent()
    assert capture == "Allocating parent."
    with capture:
        p.returnChildKeepAlive()
        assert ConstructorStats.detail_reg_inst() == n_inst + 2
    assert capture == "Allocating child."
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert (capture == """
        Releasing parent.
        Releasing child.
    """)

    p = m.Parent()
    assert ConstructorStats.detail_reg_inst() == n_inst + 1
    with capture:
        m.Parent.staticFunction(p)
        assert ConstructorStats.detail_reg_inst() == n_inst + 2
    assert capture == "Allocating child."
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert (capture == """
        Releasing parent.
        Releasing child.
    """)
Exemplo n.º 58
0
def test_keep_alive_argument(capture):
    n_inst = ConstructorStats.detail_reg_inst()
    with capture:
        p = m.Parent()
    assert capture == "Allocating parent."
    with capture:
        p.addChild(m.Child())
        assert ConstructorStats.detail_reg_inst() == n_inst + 1
    assert (capture == """
        Allocating child.
        Releasing child.
    """)
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert capture == "Releasing parent."

    with capture:
        p = m.Parent()
    assert capture == "Allocating parent."
    with capture:
        p.addChildKeepAlive(m.Child())
        assert ConstructorStats.detail_reg_inst() == n_inst + 2
    assert capture == "Allocating child."
    with capture:
        del p
        assert ConstructorStats.detail_reg_inst() == n_inst
    assert (capture == """
        Releasing parent.
        Releasing child.
    """)

    p = m.Parent()
    c = m.Child()
    assert ConstructorStats.detail_reg_inst() == n_inst + 2
    m.free_function(p, c)
    del c
    assert ConstructorStats.detail_reg_inst() == n_inst + 2
    del p
    assert ConstructorStats.detail_reg_inst() == n_inst

    with pytest.raises(RuntimeError) as excinfo:
        m.invalid_arg_index()
    assert str(excinfo.value) == "Could not activate keep_alive!"
Exemplo n.º 59
0
def test_sequence():
    from pybind11_tests import Sequence, ConstructorStats

    cstats = ConstructorStats.get(Sequence)

    s = Sequence(5)
    assert cstats.values() == ['of size', '5']

    assert "Sequence" in repr(s)
    assert len(s) == 5
    assert s[0] == 0 and s[3] == 0
    assert 12.34 not in s
    s[0], s[3] = 12.34, 56.78
    assert 12.34 in s
    assert isclose(s[0], 12.34) and isclose(s[3], 56.78)

    rev = reversed(s)
    assert cstats.values() == ['of size', '5']

    rev2 = s[::-1]
    assert cstats.values() == ['of size', '5']

    expected = [0, 56.78, 0, 0, 12.34]
    assert allclose(rev, expected)
    assert allclose(rev2, expected)
    assert rev == rev2

    rev[0::2] = Sequence([2.0, 2.0, 2.0])
    assert cstats.values() == ['of size', '3', 'from std::vector']

    assert allclose(rev, [2, 56.78, 2, 0, 2])

    assert cstats.alive() == 3
    del s
    assert cstats.alive() == 2
    del rev
    assert cstats.alive() == 1
    del rev2
    assert cstats.alive() == 0

    assert cstats.values() == []
    assert cstats.default_constructions == 0
    assert cstats.copy_constructions == 0
    assert cstats.move_constructions >= 1
    assert cstats.copy_assignments == 0
    assert cstats.move_assignments == 0