Hey all,

I'm running into a strange problem with root proxies in 10.5. I have been tracking down memory leaks in my app, and it seems that +rootProxyForConnectionWithRegisteredName:host: has been changed in 10.5 to return the root proxy retained rather than autoreleased. I haven't seen anything in the docs to reflect this, but testing seems to prove it. I did run across this curious mention in the Foundation release notes, though it doesn't really state things one way or the other:

Leaks in Distributed Objects plugged

Some leaks, and places where objects could leak if the timing was right, in Distributed Objects have been fixed in 10.5. This may mean that you may no longer get away with something you used to get away with due to the leak. Not retaining the root proxy you get from the connection, if you're going to hold onto it, seems to be a common pitfall.


Can anyone confirm this, or see anything wrong with the code below that might lead to this?

Here's a simplified version of the code I'm actually using (not the entire class, just basic portions of it):


- (id)init
{
   if ( (self = [super init]) ) {
       NSUInteger numTries = 0;
       struct timespec tv = { 0, 250000000 }; /* .25 of a second */

[NSThread detachNewThreadSelector:@selector(backgroundThread:) toTarget:self withObject:nil];

       while ( (threadPortName == nil) && (numTries < 20) ) {
           nanosleep( &tv, NULL );
           numTries += 1;
       }

       /* threadPortName and threadProxy are class ivars */

       if ( threadPortName != nil ) {
threadProxy = [NSConnection rootProxyForConnectionWithRegisteredName:threadPortName host:nil];
           /* Causes threadProxy to never be released under 10.5
              when uncommented; crash under 10.4 when commented
           */
           //[threadProxy retain];
       }

       if ( threadProxy == nil ) {
            [self autorelease];
           return nil;
       }
   }

   return self;
}

/* Always called when the class's task is done */
- (void)releaseBackgroundThread
{
   if ( threadProxy != nil ) {
       [threadProxy stopThread];
       [threadProxy autorelease];
       threadProxy = nil;
   }
}

/* Called on thread */
- (void)stopThread
{
   stopThread = YES;
}

- (void)backgroundThread:(id)sender
{
   NSAutoreleasePool *threadPool = [[NSAutoreleasePool alloc] init];
   CFUUIDRef uuid = CFUUIDCreate( NULL );
   NSString *threadName = (NSString *)CFUUIDCreateString( NULL, uuid );
   NSConnection *myCon = [[NSConnection defaultConnection] retain];
   NSRunLoop *current = [NSRunLoop currentRunLoop];

   CFRelease( uuid );

   [myCon setRootObject:self];

   if ( ![myCon registerName:threadName] ) {
       [threadName release];
       [threadPool release];
       return;
   }

   threadPortName = threadName;

   while ( !stopThread ) {
       NSAutoreleasePool *runPool = [[NSAutoreleasePool alloc] init];
       [current runUntilDate:[NSDate dateWithTimeIntervalSinceNow:2.]];
       [runPool release];
   }

   [myCon invalidate];
   [myCon release];
   [threadPool release];
}


--------------------------------------
Darkshadow
(aka Michael Nickerson)
http://www.nightproductions.net

_______________________________________________

Cocoa-dev mailing list (Cocoa-dev@lists.apple.com)

Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com

Help/Unsubscribe/Update your Subscription:
http://lists.apple.com/mailman/options/cocoa-dev/archive%40mail-archive.com

This email sent to [EMAIL PROTECTED]

Reply via email to