Pergunta

Aqui está uma versão simplificada do meu código:

- (IBAction)convert:(id)sender
{
    /* these two lines are ignored */
    [textbox setStringValue:@"converting"];
    [convertButton setEnabled:NO];

        pid_t pid;
        if((pid=fork())==-1)
        {
            [log setStringValue:@"couldn't fork a new process."];
            converting = 0;
        [convertButton setEnabled:YES];
            return;
        }else if (pid==0)
        {
            //this is the child
            sleep(2);
            exit(0);
        }else{
            int status;
            waitpid(pid,&status,0);
        }
    }
}

É uma chamada de garfo () bastante básica. O problema é que as duas linhas no topo (marcadas com um comentário) são ignoradas ... elas não parecem executar até depois A criança bifurcada sai. Por quê?

Editar: E o que posso fazer para consertar isso?

Foi útil?

Solução

Você realmente verdade verdade Não quero ligar fork() em uma aplicação de cacau. Existem cerca de um zilhão de gotchas diferentes ao fazê -lo, principalmente relacionados a vários recursos, como portas Mach e outras infraestruturas de ligação ao sistema sobrevive fork() fronteira. Os tópicos causam todo tipo de inferno também.

Usar NSTask em vez de. Enquanto efetivamente faz fork()/exec() Internamente, faz isso com um cuidado considerável para garantir que seja feito corretamente.

Outras dicas

Talvez porque seu código deva retornar ao loop do evento principal antes que a GUI possa mudar o estado? Ou uma pequena variação, porque o fio que executa a GUI está bloqueado enquanto seu código está fazendo uma espera no nível do kernel ()?

Bbum acertou exatamente isso. Aqui está o código que acabei usando:

- (IBAction)convert:(id)sender
{
    task = [[NSTask alloc] init];
    [task setLaunchPath: @"/usr/local/bin/lame"];

    NSArray *arguments;
    arguments = [NSArray arrayWithObjects: file,outputFile, nil];
    [task setArguments: arguments];

    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(taskFinished:) name:NSTaskDidTerminateNotification object:task];

    [task launch];  
}
- (void) taskFinished:(NSNotification *)note {
    // code here executes after process finishes    
}
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top