[omniORB] ServantActivator never destroyed?

Adam Groszer adamg@mailbox.hu
Mon Mar 24 17:23:02 2003


This is a multi-part message in MIME format.

--Boundary_(ID_xmRLBklo/V0V/dQSvAP5og)
Content-type: text/plain; charset=iso-8859-1
Content-transfer-encoding: 8BIT

I modified the omniORBpy-2.1\examples\poa\servantactivator.py to model my
scripts fundamental behavior. See adiactivator.py, the output generated is
in out.txt. I have a dictionary of servants from which the servantactivator
looks up the necessary object.

My problem is that it looks like, ServantActivator of childPOA never gets
destroyed, so all objects kept in the objects dict also never get garbage
collected.

If I del the objects with
for i in objects.keys():
   del objects[i]
the objects get garbage collected, but the ServantActivator never.

What am I doing wrong?
Which is the correct way to setup and cleanup a ServantActivator
or -Locator?

please help

Adam Gröszer

--Boundary_(ID_xmRLBklo/V0V/dQSvAP5og)
Content-type: text/plain; name=adiactivator.py
Content-transfer-encoding: 7BIT
Content-disposition: attachment; filename=adiactivator.py

#!/usr/bin/env python

# Example of using a ServantActivator.
#
# This program behaves just like the echo server, except that the
# servant object is not activated until the first request on the
# object.
#
# If you run with a -l command line argument, the program will make a
# number of local calls to the object, showing that the activator runs
# in the local, as well as the remote, case.


import sys, time
from omniORB import CORBA, PortableServer, PortableServer__POA

import _GlobalIDL, _GlobalIDL__POA

import gc

class Echo_i (_GlobalIDL__POA.Echo):
    def __init__(self):
        print "Echo_i created.",self

    def __del__(self):
        print "Echo_i deleted.",self

    def echoString(self, mesg):
        print "echoString() called with message:", mesg
        return mesg
    
    def _incarnate_called(self):
        print '_incarnate_called',self
    
    def _ether_called(self):
        print '_ether_called',self

class ServantActivator_i (PortableServer__POA.ServantActivator):
    def __init__(self, collection):
        self.collection = collection
        
        print 'ServantActivator created',self
        
    def incarnate(self, oid, poa):
        print "incarnate(): oid:", oid, "poa:", poa._get_the_name()
        
        ei = self.collection[oid]
        print "object:", ei
        
        ei._incarnate_called()
        
        return ei

    def etherealize(self, oid, poa, servant, cleanup_in_progress,
                    remaining_activations):
        print "etherealize called"
        try:
            name = poa._get_the_name()
        except CORBA.OBJECT_NOT_EXIST, ex:
            name = "<dead poa>"
        print "etherealize(): oid:", oid, "poa:", name
        
        servant._ether_called()
    
    def __del__(self):
        print 'ServantActivator deleted',self

def newobj(objects, poa):
    childobj = Echo_i()
    
    oid = str(id(childobj))
    corbaId = CORBA.id(childobj.__class__)
    
    childobj._oid = oid
    childobj._objref = poa.create_reference_with_id(oid, corbaId)
    
    objects[oid] = childobj
    
    print 'oid:',oid


def main():
    # Initialise the ORB and activate the root POA.
    orb = CORBA.ORB_init(sys.argv, CORBA.ORB_ID)
    poa = orb.resolve_initial_references("RootPOA")
    poaManager = poa._get_the_POAManager()
    poaManager.activate()
    
    # Create a child POA with the right policies for a ServantActivator
    ps = [poa.create_id_assignment_policy(PortableServer.USER_ID),
          poa.create_servant_retention_policy(PortableServer.RETAIN),
          poa.create_request_processing_policy(PortableServer.USE_SERVANT_MANAGER)]
    
    #child = poa.create_POA("MyPOA", poaManager, ps)
    childPOA = poa.create_POA("MyPOA", poaManager, ps)
    
    objects = {}
    
    # Create the ServantActivator and set it as the child's ServantManager
    sai = ServantActivator_i(objects)
    sao = sai._this()
    childPOA.set_servant_manager(sao)
    
    # Create an object reference with no servant
    for i in range(10):
        newobj(objects, childPOA)
    
    # Run, or do some local calls...
    if not (len(sys.argv) > 1 and sys.argv[1] == "-l"):
        orb.run()
    
    time.sleep(1)
    
    print "Calling..."
    
    eo_obj = objects.items()[5][1]
    eo = eo_obj._objref
    
    # On this invocation, the servant will be activated
    print eo.echoString("Hello from same address space")
    time.sleep(1)
    
    # This invocation uses the local case optimisation, since the servant
    # is now active
    print eo.echoString("Hello again")
    time.sleep(1)
    
    # Deactivating the object causes a call to etherealize(), and the
    # servant is deleted.
    print "Deactivating the object..."
    childPOA.deactivate_object(eo_obj._oid)
    print "Deactivated."
    time.sleep(1)
    
    # This invocation activates the servant again
    print eo.echoString("Hello again again")
    time.sleep(1)
    
    # Destroying the child POA causes the servant to be etherealized again
    print "Destroying POA..."
    childPOA.destroy(1, 1)
    print "Destroyed."
    
    #for i in objects.keys():
    #    del objects[i]

print 'calling main()'

main()

print 'main() finished'

gc.collect()

--Boundary_(ID_xmRLBklo/V0V/dQSvAP5og)
Content-type: text/plain; name=out.txt
Content-transfer-encoding: 7BIT
Content-disposition: attachment; filename=out.txt

calling main()
ServantActivator created <__main__.ServantActivator_i instance at 0x00837A18>
Echo_i created. <__main__.Echo_i instance at 0x0083B778>
oid: 8632184
Echo_i created. <__main__.Echo_i instance at 0x0082CC18>
oid: 8571928
Echo_i created. <__main__.Echo_i instance at 0x0082CFB0>
oid: 8572848
Echo_i created. <__main__.Echo_i instance at 0x0082D3C8>
oid: 8573896
Echo_i created. <__main__.Echo_i instance at 0x0082D7E0>
oid: 8574944
Echo_i created. <__main__.Echo_i instance at 0x0082DBF8>
oid: 8575992
Echo_i created. <__main__.Echo_i instance at 0x0082E068>
oid: 8577128
Echo_i created. <__main__.Echo_i instance at 0x0082E530>
oid: 8578352
Echo_i created. <__main__.Echo_i instance at 0x0082E9F8>
oid: 8579576
Echo_i created. <__main__.Echo_i instance at 0x0082EEC0>
oid: 8580800
Calling...
incarnate(): oid: 8579576 poa: MyPOA
object: <__main__.Echo_i instance at 0x0082E9F8>
_incarnate_called <__main__.Echo_i instance at 0x0082E9F8>
echoString() called with message: Hello from same address space
Hello from same address space
echoString() called with message: Hello again
Hello again
Deactivating the object...
etherealize called
etherealize(): oid: 8579576 poa: MyPOA
_ether_called <__main__.Echo_i instance at 0x0082E9F8>
Deactivated.
incarnate(): oid: 8579576 poa: MyPOA
object: <__main__.Echo_i instance at 0x0082E9F8>
_incarnate_called <__main__.Echo_i instance at 0x0082E9F8>
echoString() called with message: Hello again again
Hello again again
Destroying POA...
etherealize called
etherealize(): oid: 8579576 poa: <dead poa>
_ether_called <__main__.Echo_i instance at 0x0082E9F8>
Destroyed.
main() finished

--Boundary_(ID_xmRLBklo/V0V/dQSvAP5og)--