Я считаю, что NSDistributedNotificationCenter должен работать для этого. Обратите внимание, что использование NSDistributedNotificationCenter для взаимодействия между процессами в разных учетных записях пользователей само по себе не требует привилегий root.
Чтобы помочь в координации между учетными записями пользователей, может помочь определить, какие экземпляры приложения с графическим интерфейсом и демон в настоящее время активны и находятся под контролем, а какие - пассивны. Вы можете использовать уведомления NSWorkspace (NSWorkspaceSessionDidBecomeActiveNotification, NSWorkspaceSessionDidResignActiveNotification), чтобы определить, когда пользователь переключается между учетными записями пользователей и т. Д., И чтобы ваши экземпляры устанавливали себя соответствующим образом.
Допустим, у вашего GUI-приложения и демона есть экземпляры, запущенные в 3 разных учетных записях пользователей. Если в активной учетной записи пользователя вы хотите начать процесс обновления, вы можете использовать NSDistributedNotificationCenter, чтобы, например, легко сказать всем остальным экземплярам о немедленном завершении работы. Для этого вы должны определить что-то вроде следующего.
В файле .h объявите имена ваших различных уведомлений:
extern NSString * const MDShouldTerminateImmediatelyNotification;
в (реализации) файле реализации, создайте имена и настройте класс так, чтобы он интересовался распределенным уведомлением с этим именем и т. Д.: * 10101 *
NSString * const MDShouldTerminateImmediatelyNotification = @"MDShouldTerminateImmediately";
- (id)init {
if (self = [super init]) {
[[NSDistributedNotificationCenter defaultCenter]
addObserver:self
selector:@selector(shouldTerminateImmediately:)
name:MDShouldTerminateImmediatelyNotification
object:nil];
}
return self;
}
- (void)dealloc {
[[NSDistributedNotificationCenter defaultCenter] removeObserver:self];
[super dealloc];
}
- (void)shouldTerminateImmediately:(NSNotification *)notification {
if (ourInstanceIsInControl == NO) {
[NSApp terminate:nil];
}
}
В классе, который будет инициировать процесс обновления, вы должны сделать что-то вроде этого, чтобы отправить уведомление:
- (void)beginUpdate {
[[NSDistributedNotificationCenter defaultCenter]
postNotificationName:MDShouldTerminateImmediatelyNotification
object:[self description] // or just nil
userInfo:nil
options:NSNotificationDeliverImmediately | NSNotificationPostToAllSessions];
// continue
}
Это должно быть, по крайней мере, начало работы, я думаю ....
На самом деле, если вы говорите об одном экземпляре демона, работающем от имени пользователя root, который выполняет все функции во всех учетных записях пользователей, вам может потребоваться включить эту часть в процесс типа агента Launchd (фоновый процесс, запускаемый на уровне пользователя, каждая учетная запись пользователя будет иметь свой собственный экземпляр).
Для получения дополнительной информации:
Техническое примечание TN2083 Демоны и агенты
Сеансы рутирования и входа в систему
Создание запускаемых демонов и агентов