2012-12-06 11 views
7

Próbuję uruchomić prosty skrypt bash za pomocą NSTask i skierować wyjście do widoku tekstowego. Po wykonaniu zadania użycie procesora w mojej aplikacji wynosi 100%, mimo że jest to proste echo (na razie).Używanie NSTask i NSPipe powoduje 100% użycie procesora.

stworzyłem całkowicie świeży projekt, aby wyizolować problem:

@interface AppDelegate() 
@property (nonatomic) NSTask *task; 
@property (nonatomic) NSPipe *pipe; 
@end 

@implementation AppDelegate 
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification 
{ 
    self.pipe = [NSPipe pipe]; 
    self.pipe.fileHandleForReading.readabilityHandler = ^(NSFileHandle *h) { 
     NSLog(@"Read: %@", [h readDataToEndOfFile]); 
    }; 

    self.task = [[NSTask alloc] init]; 
    self.task.launchPath = @"/bin/bash"; 
    self.task.arguments = @[@"-c", @"echo test"]; 
    self.task.standardOutput = self.pipe; 
    [self.task launch]; 
} 
@end 

To jest prawidłowo wykonane i wyjście (jako NSData) jest rejestrowane z NSLog:

PipeTest[3933:2623] Read: <74657374 0a> 

Jednak użycie procesora pozostaje na poziomie 100%, dopóki nie zakończę mojej aplikacji.

EDIT:

testu Czas Profiler zwraca listę poniżej, ale nie jestem pewien, jak to zinterpretować.

enter image description here

Odpowiedz

9

uchwyt pliku otwarte?

@interface AppDelegate() 
@property (nonatomic) NSTask *task; 
@property (nonatomic) NSPipe *pipe; 
@end 

@implementation AppDelegate 
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification 
{ 
    self.pipe = [NSPipe pipe]; 
    self.pipe.fileHandleForReading.readabilityHandler = ^(NSFileHandle *h) { 
     NSLog(@"Read: %@", [h readDataToEndOfFile]); 
     [h closeFile]; 
    }; 

    self.task = [[NSTask alloc] init]; 
    self.task.launchPath = @"/bin/bash"; 
    self.task.arguments = @[@"-c", @"echo test"]; 
    self.task.standardOutput = self.pipe; 
    [self.task launch]; 
} 

Zamknięcie plik na NSFileHandleh wydaje się przywrócić do normalnego użycia procesora.

+1

To świetnie, dzięki! Czy możesz również wyjaśnić, dlaczego procesor tak reaguje na lewe otwarte uchwyty plików? –

2

Sugerowany kod nie zadziałałby, gdyby aplikacja zapisywała więcej niż bufor implementacji NSFileHandle (4K w mojej obserwacji na El Capitan). [h readDataToEndOfFile] ma tendencję do czytania 4K na raz, więc ten przykład może przedwcześnie zamknąć bufor. Bardziej niezawodne i równie nieudokumentowane podejście do obsługi jest następujące:

NSData *data = [h readDataToEndOfFile]; 
if (data.length) { 
    NSLog(@"Read: %@", data); 
} else { 
    [h closeFile]; 
} 
Powiązane problemy