2009-03-31 8 views
7

Ho un NSTimer in esecuzione nella mia applicazione che raccoglie alcuni dati e li invia periodicamente a un server. In produzione il timer scatterà ogni poche ore.Il codice in NSTimer impedisce la sospensione automatica

Sono preoccupato di interferire con il sonno automatico. In fase di test, alcune combinazioni di timer e sleep time prevengono completamente il sonno automatico: lo schermo si dorme, il sistema continua a funzionare. Impostando il mio NSTimer su un minuto si arresta sempre.

Alcune applicazioni Mac sono famose per interferire con il sonno automatico durante l'esecuzione (o in qualsiasi momento, se installano un daemon). Quali azioni impediscono al sistema di dormire e come posso eseguire le attività periodiche in modo sicuro?

+0

Le applicazioni non interferiscono mai con il sonno se sono installate ma non in esecuzione. Il codice deve essere in esecuzione per fare qualsiasi cosa. –

+0

Un'applicazione che ha un'esecuzione di supporto all'accesso, all'avvio o su richiesta da launchd può essere considerata installata. Un'applicazione in esecuzione (in questo contesto) ha una presenza nella sessione dell'utente corrente. Avrei dovuto essere più specifico – s4y

risposta

2

L'accesso al disco impedisce al computer di dormire, in base all'articolo "Mac OS X: Why your Mac might not sleep or stay in sleep mode" di Apple.

Inoltre, i miei test hanno dimostrato che la priorità di un thread ha anche un impatto sul fatto che un computer possa o meno dormire. Il seguente codice con un timer consentirà il sonno di un computer.

@implementation AppController 

-(void)timerFired:(NSTimer *)aTimer 
{ 

} 

-(void)spawnThread 
{ 
    NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; 
    [NSThread setThreadPriority:0.0]; 

    [NSTimer scheduledTimerWithTimeInterval:20 target:self selector:@selector(timerFired:) userInfo:nil repeats:YES]; 

    while(1) //Run forever! 
    { 
     [[NSRunLoop currentRunLoop] runUntilDate:[NSDate dateWithTimeIntervalSinceNow:300]]; 
    } 

    [pool drain]; 
} 

-(void)awakeFromNib 
{ 
    [NSThread detachNewThreadSelector:@selector(spawnThread) toTarget:self withObject:nil]; 
} 

@end 

La rimozione della chiamata setThreadPriority impedisce al computer di dormire.

0

Hai guardato in launchd? http://developer.apple.com/MacOsX/launchd.html

È ciò che il sistema operativo utilizza per i propri servizi, quindi sono sicuro che il sonno è stato preso in considerazione.

+0

Ho davvero guardato al launchd, ma il mio processo sarà già in esecuzione e non voglio installare un lavoro launchd - o il fattore periodico periodico in un eseguibile separato, del resto. – s4y

1

Sono un po 'confuso, sopporta me. =)

L'attività eseguita dall'applicazione ripristinerà il timer di spegnimento della macchina, quindi, a meno che il ritardo tra le trasmissioni sia maggiore del periodo di inattività, la macchina non andrà in stop. Non sono completamente sicuro di cosa si intenda per "attività" su OS X, ma se è qualcosa come Linux, mi aspetto che la rete o l'I/O del disco vadano conteggiati come i processi nello stato di esecuzione, vale a dire scricchiolare i numeri o mescolare i dati in giro nella RAM.

Inoltre, nel caso in cui il sistema è andato in stop, ci si aspetta che la macchina si riattivi in ​​modo che l'app possa comunicare con l'host remoto?

+0

Nessun problema. Non so nemmeno quale Mac OS X consideri un'attività di prevenzione del sonno, e questa è metà della mia domanda. Voglio poter accedere al disco e alla rete * senza * impedendo il sonno automatico. Non mi aspetto o voglio riattivare la macchina, la mia app è felice di aspettare che l'utente lo faccia. – s4y

2

NSLog(), almeno quando si registra su /var/log/system.log, può impedire la sospensione del periodo di inattività. Ho provato con un demone launchd che chiamava NSLog(@"test") ogni minuto e con un sistema inattivo di 1 minuto e il sistema non è mai andato in stop. Commentando la linea NSLog, il sistema è andato in stop dopo 1 minuto.

Ecco lo only reference che ho trovato a qualcun altro che ha riscontrato questo problema.

Problemi correlati