• Open Menu Close Menu
  • Apple
  • Shopping Bag
  • Apple
  • Mac
  • iPad
  • iPhone
  • Watch
  • TV
  • Music
  • Support
  • Search apple.com
  • Shopping Bag

Lists

Open Menu Close Menu
  • Terms and Conditions
  • Lists hosted on this site
  • Email the Postmaster
  • Tips for posting to public mailing lists
Re: Stopping an NSRunLoop OR getting NSDistributedNotificationCenter notifications
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Stopping an NSRunLoop OR getting NSDistributedNotificationCenter notifications


  • Subject: Re: Stopping an NSRunLoop OR getting NSDistributedNotificationCenter notifications
  • From: Chris Kane <email@hidden>
  • Date: Mon, 19 Jun 2006 09:36:18 -0700

Yes, NSDistributedNotifications are only delivered to the main thread.

With your lock, btw, it's unclear if you are locking it in one thread and unlocking it in another, but if that's what you're doing, don't do that, the results are undefined -- POSIX allows that not to "work" completely at the pthreads layer. Even if you just want to change the condition, always -lock first, then -unlockWithCondition:, so that you've always locked the lock you're unlocking on that thread.

There's no need to poll every second, and when you see code looping and running the run loop, it isn't necessarily a polling loop. You have to look carefully at which method is being used.

What you're supposed to do in your situation (per the original designers, more or less), is use

- (BOOL)runBeforeDate:(NSDate *)limitDate;

and loop, using [NSDate distantFuture] for the parameter. You'd use an NSPort which you'd registered with the run loop on the main thread, and NSPortMessage, to send a message to the main thread when the background thread wants it to terminate. The port's delegate handles the message, and the handling can be pretty trivial (like setting a flag). The Before variant methods return after processing approximately one input source; really, it's more like after one cycling of the run loop which has serviced a port. Of course, once you've switched to runBeforeDate: and a loop on the main thread, the need for the background thread may disappear and you could save yourself the trouble with the NSPort/NSPortMessage.

However, if you just want the process to die, just call exit() from the background thread. You need not futz with the main thread (except you need to change it to run the run loop to pick up distributed notifications).


Chris Kane Cocoa Frameworks, Apple


On Jun 18, 2006, at 5:48 PM, James Bucanek wrote:

Greetings,

I've got a background daemon (Foundation command-line tool) that performs user-defined tasks at specific times.

I've never figured out how to get an NSRunLoop to exit in a timely fashion. All of the examples show how to "poll" the run loop, but I just found it offensive that a process that could be doing absolutely nothing for days is required to check if it should quit every second[1].

I thought I'd come up with an elegant solution, but now I think it's biting me. My main() starts a new thread that runs the application in a separate run loop. main() then suspends on an NSConditionalLock. When the daemon wants to quit, it simply changes the state of the lock and main() returns, instantly terminating the process.

Everything (NSConnections, notifications, timers, etc.) have been working gloriously -- except that I'm not getting any NSDistributedNotificationCenter notifications. I'm now pretty sure this is because NSDistributedNotificationCenter fires all notifications on the "main" run loop, which would be the run loop associated with the original thread, which is main(), which is permanently suspended on its NSConditionalLock.

So I'm looking for suggestions on how to

- Get an NSRunLoop to exit on demand

- Receive NSDistributedNotificationCenter notifications on a thread other than the one running main()

- Find some other way of terminating my application. I do realize that I could simply call exit(0), but I was just trying to engineer something a little more structured than that.

Thanks,

James

[1] My daemon has an odd requirement: If a newer version of the daemon is started, it contacts the existing daemon and tells it to terminate immediately. The new daemon can't initialize until the old one has terminated, so I can't afford long delays between deciding to exit and actually exiting.
--
James Bucanek
_______________________________________________
Do not post admin requests to the list. They will be ignored.
Cocoa-dev mailing list (email@hidden)
Help/Unsubscribe/Update your Subscription:

This email sent to email@hidden

_______________________________________________ Do not post admin requests to the list. They will be ignored. Cocoa-dev mailing list (email@hidden) Help/Unsubscribe/Update your Subscription: This email sent to email@hidden
  • Follow-Ups:
    • Re: Stopping an NSRunLoop OR getting NSDistributedNotificationCenter notifications
      • From: James Bucanek <email@hidden>
References: 
 >Stopping an NSRunLoop OR getting NSDistributedNotificationCenter notifications (From: James Bucanek <email@hidden>)

  • Prev by Date: Re: NSException from [NSTextView setSelectedRange] ?
  • Next by Date: Re: Stopping an NSRunLoop OR getting NSDistributedNotificationCenter notifications
  • Previous by thread: Stopping an NSRunLoop OR getting NSDistributedNotificationCenter notifications
  • Next by thread: Re: Stopping an NSRunLoop OR getting NSDistributedNotificationCenter notifications
  • Index(es):
    • Date
    • Thread