示例#1
0
 def analyze(self, func, sig, func_to_analyze=None, backendopt=False):
     if func_to_analyze is None:
         func_to_analyze = func
     t = TranslationContext()
     t.buildannotator().build_types(func, sig)
     t.buildrtyper().specialize()
     if backendopt:
         backend_optimizations(t)
     if option.view:
         t.view()
     a = FinalizerAnalyzer(t)
     fgraph = graphof(t, func_to_analyze)
     result = a.analyze_light_finalizer(fgraph)
     return result
示例#2
0
 def analyze(self, func, sig, func_to_analyze=None, backendopt=False):
     if func_to_analyze is None:
         func_to_analyze = func
     t = TranslationContext()
     t.buildannotator().build_types(func, sig)
     t.buildrtyper().specialize()
     if backendopt:
         backend_optimizations(t)
     if option.view:
         t.view()
     a = FinalizerAnalyzer(t)
     fgraph = graphof(t, func_to_analyze)
     result = a.analyze_light_finalizer(fgraph)
     return result
示例#3
0
def test_various_ops():
    from rpython.flowspace.model import SpaceOperation, Constant

    X = lltype.Ptr(lltype.GcStruct('X'))
    Z = lltype.Ptr(lltype.Struct('Z'))
    S = lltype.GcStruct('S', ('x', lltype.Signed),
                        ('y', X),
                        ('z', Z))
    v1 = varoftype(lltype.Bool)
    v2 = varoftype(lltype.Signed)
    f = FinalizerAnalyzer(None)
    r = f.analyze(SpaceOperation('cast_int_to_bool', [v2],
                                                       v1))
    assert not r
    v1 = varoftype(lltype.Ptr(S))
    v2 = varoftype(lltype.Signed)
    v3 = varoftype(X)
    v4 = varoftype(Z)
    assert not f.analyze(SpaceOperation('bare_setfield', [v1, Constant('x'),
                                                          v2], None))
    assert     f.analyze(SpaceOperation('bare_setfield', [v1, Constant('y'),
                                                          v3], None))
    assert not f.analyze(SpaceOperation('bare_setfield', [v1, Constant('z'),
                                                          v4], None))
示例#4
0
    def make_finalizer_funcptr_for_type(self, TYPE):
        from rpython.memory.gctransform.support import get_rtti
        rtti = get_rtti(TYPE)
        if rtti is not None and hasattr(rtti._obj, 'destructor_funcptr'):
            destrptr = rtti._obj.destructor_funcptr
            DESTR_ARG = lltype.typeOf(destrptr).TO.ARGS[0]
            destrgraph = destrptr._obj.graph
        else:
            return None, False

        t = self.llinterp.typer.annotator.translator
        light = not FinalizerAnalyzer(t).analyze_light_finalizer(destrgraph)
        def ll_finalizer(addr):
            try:
                v = llmemory.cast_adr_to_ptr(addr, DESTR_ARG)
                self.llinterp.eval_graph(destrgraph, [v], recursive=True)
            except llinterp.LLException:
                raise RuntimeError(
                    "a finalizer raised an exception, shouldn't happen")
        return llhelper(gctypelayout.GCData.FINALIZER, ll_finalizer), light
示例#5
0
def test_various_ops():
    from rpython.flowspace.model import SpaceOperation, Constant

    X = lltype.Ptr(lltype.GcStruct('X'))
    Z = lltype.Ptr(lltype.Struct('Z'))
    S = lltype.GcStruct('S', ('x', lltype.Signed), ('y', X), ('z', Z))
    v1 = varoftype(lltype.Bool)
    v2 = varoftype(lltype.Signed)
    f = FinalizerAnalyzer(None)
    r = f.analyze(SpaceOperation('cast_int_to_bool', [v2], v1))
    assert not r
    v1 = varoftype(lltype.Ptr(S))
    v2 = varoftype(lltype.Signed)
    v3 = varoftype(X)
    v4 = varoftype(Z)
    assert not f.analyze(
        SpaceOperation('bare_setfield', [v1, Constant('x'), v2], None))
    assert f.analyze(
        SpaceOperation('bare_setfield', [v1, Constant('y'), v3], None))
    assert not f.analyze(
        SpaceOperation('bare_setfield', [v1, Constant('z'), v4], None))
示例#6
0
def test_various_ops():
    from rpython.flowspace.model import SpaceOperation, Constant

    X = lltype.Ptr(lltype.GcStruct('X'))
    Z = lltype.Ptr(lltype.Struct('Z'))
    S = lltype.GcStruct('S', ('x', lltype.Signed),
                        ('y', X),
                        ('z', Z))
    v1 = varoftype(lltype.Bool)
    v2 = varoftype(lltype.Signed)
    f = FinalizerAnalyzer(None)
    r = f.analyze(SpaceOperation('cast_int_to_bool', [v2],
                                                       v1))
    assert not r
    v1 = varoftype(lltype.Ptr(S))
    v2 = varoftype(lltype.Signed)
    v3 = varoftype(X)
    v4 = varoftype(Z)
    assert not f.analyze(SpaceOperation('bare_setfield', [v1, Constant('x'),
                                                          v2], None))
    assert     f.analyze(SpaceOperation('bare_setfield', [v1, Constant('y'),
                                                          v3], None))
    assert not f.analyze(SpaceOperation('bare_setfield', [v1, Constant('z'),
                                                          v4], None))

    def test_malloc(self):
        S = lltype.GcStruct('S')

        def f():
            return lltype.malloc(S)

        r = self.analyze(f, [])
        assert r

    def test_raw_free_getfield(self):
        S = lltype.Struct('S')

        class A(object):
            def __init__(self):
                self.x = lltype.malloc(S, flavor='raw')

            def __del__(self):
                if self.x:
                    lltype.free(self.x, flavor='raw')
                    self.x = lltype.nullptr(S)

        def f():
            return A()

        r = self.analyze(f, [], A.__del__.im_func)
        assert not r

    def test_c_call(self):
        C = rffi.CArray(lltype.Signed)
        c = rffi.llexternal('x', [lltype.Ptr(C)], lltype.Signed)

        def g():
            p = lltype.malloc(C, 3, flavor='raw')
            f(p)

        def f(p):
            c(rffi.ptradd(p, 0))
            lltype.free(p, flavor='raw')

        r = self.analyze(g, [], f, backendopt=True)
        assert not r

    def test_chain(self):
        class B(object):
            def __init__(self):
                self.counter = 1

        class A(object):
            def __init__(self):
                self.x = B()

            def __del__(self):
                self.x.counter += 1

        def f():
            A()

        r = self.analyze(f, [], A.__del__.im_func)
        assert r

    def test_must_be_light_finalizer_decorator(self):
        S = lltype.GcStruct('S')

        @rgc.must_be_light_finalizer
        def f():
            lltype.malloc(S)
        @rgc.must_be_light_finalizer
        def g():
            pass
        self.analyze(g, []) # did not explode
        py.test.raises(FinalizerError, self.analyze, f, [])
示例#7
0
def test_various_ops():
    from rpython.flowspace.model import SpaceOperation, Constant

    X = lltype.Ptr(lltype.GcStruct('X'))
    Z = lltype.Ptr(lltype.Struct('Z'))
    S = lltype.GcStruct('S', ('x', lltype.Signed), ('y', X), ('z', Z))
    v1 = varoftype(lltype.Bool)
    v2 = varoftype(lltype.Signed)
    f = FinalizerAnalyzer(None)
    r = f.analyze(SpaceOperation('cast_int_to_bool', [v2], v1))
    assert not r
    v1 = varoftype(lltype.Ptr(S))
    v2 = varoftype(lltype.Signed)
    v3 = varoftype(X)
    v4 = varoftype(Z)
    assert not f.analyze(
        SpaceOperation('bare_setfield', [v1, Constant('x'), v2], None))
    assert f.analyze(
        SpaceOperation('bare_setfield', [v1, Constant('y'), v3], None))
    assert not f.analyze(
        SpaceOperation('bare_setfield', [v1, Constant('z'), v4], None))

    def test_malloc(self):
        S = lltype.GcStruct('S')

        def f():
            return lltype.malloc(S)

        r = self.analyze(f, [])
        assert r

    def test_raw_free_getfield(self):
        S = lltype.Struct('S')

        class A(object):
            def __init__(self):
                self.x = lltype.malloc(S, flavor='raw')

            def __del__(self):
                if self.x:
                    lltype.free(self.x, flavor='raw')
                    self.x = lltype.nullptr(S)

        def f():
            return A()

        r = self.analyze(f, [], A.__del__.im_func)
        assert not r

    def test_c_call(self):
        C = rffi.CArray(lltype.Signed)
        c = rffi.llexternal('x', [lltype.Ptr(C)], lltype.Signed)

        def g():
            p = lltype.malloc(C, 3, flavor='raw')
            f(p)

        def f(p):
            c(rffi.ptradd(p, 0))
            lltype.free(p, flavor='raw')

        r = self.analyze(g, [], f, backendopt=True)
        assert not r

    def test_chain(self):
        class B(object):
            def __init__(self):
                self.counter = 1

        class A(object):
            def __init__(self):
                self.x = B()

            def __del__(self):
                self.x.counter += 1

        def f():
            A()

        r = self.analyze(f, [], A.__del__.im_func)
        assert r

    def test_must_be_light_finalizer_decorator(self):
        S = lltype.GcStruct('S')

        @rgc.must_be_light_finalizer
        def f():
            lltype.malloc(S)

        @rgc.must_be_light_finalizer
        def g():
            pass

        self.analyze(g, [])  # did not explode
        py.test.raises(FinalizerError, self.analyze, f, [])