Sempre deixe a decisão de como lidar EINTR
com o usuário e facilite a retomada da operação, conforme apropriado.
Geralmente, a melhor maneira de fazer isso é retornar da função de biblioteca para o chamador EINTR
, mas em alguns casos um retorno de chamada ou alguma outra implementação pode ser melhor - a melhor maneira depende de outros fatores, mas sempre permita que o controle do usuário tente novamente. currículo.
Isso significa que, se o código da sua biblioteca puder ser parcialmente bem-sucedido antes de obter um EINTR
, você deve pensar cuidadosamente no que o usuário precisa saber sobre esse êxito parcial ou se pode precisar retomar a operação de onde falhou. Pode ser necessário retornar informações adicionais ou fornecer uma interface para retomar a partir de qualquer local onde possa ser apropriado.
É por isso que as chamadas do sistema read
e write
hoje em dia retornam sucesso parcial - porque é muito frustrante para o usuário ser informado:
Você tentou escrever "foo"
e nós escrevemos com sucesso nada, ou "f"
, ou "fo"
, e você não sabe qual . Diverta-se! Espero que o seu sistema consiga reiniciar toda a gravação depois de qualquer uma dessas!
Obviamente, em alguns casos, devemos escrever sistemas para lidar com situações exatamente como essa - por exemplo, talvez após uma gravação parcial, você sempre recrie o arquivo, ou reabra a conexão de rede, ou use algum byte para significar "recomeçar" - portanto, depende de quais casos de uso sua biblioteca se destina.
Se uma função de biblioteca executa várias operações, e não há como saber em qual delas falhou, e essas operações não são todas seguras e eficientemente idempotentes, isso basicamente torna uma biblioteca inutilizável para código que precisa ser robusto.
Se todas as etapas de uma função de biblioteca são seguras e eficientemente idempotentes, ou a coisa toda é atômica - como a aquisição de um bloqueio -, basta informar o usuário que uma EINTR
ocorrência é suficiente.
Além disso, se tentarmos novamente EINTR
, poderemos interromper o tratamento do sinal . No nível baixo, os manipuladores de sinal podem usar com segurança apenas um conjunto limitado de recursos e, em muitos casos, um manipulador de sinal define apenas um booleano indicando que o sinal foi recebido e depois retorna, esperando que, quando o código for retomado, sair do que estava fazendo. Se obtivermos um EINTR
e tentarmos novamente, em vez de retornar o controle ao usuário, poderemos impedir que o código faça isso.
O que fazer depois de uma EINTR
é uma decisão completa do programa - a resposta certa não pode ser conhecida sem saber o que o programa está fazendo e como o programa deve responder a um sinal, e isso afeta o restante do programa.
Saber como ou se o usuário pode precisar continuar e ajudá-lo a fazê-lo, se necessário, é uma responsabilidade da biblioteca - a resposta certa não pode ser conhecida sem saber o que a biblioteca está fazendo.
EINTR
e relatando que ao chamador), mas pode depender de qual é a sua biblioteca fazendo ...