Se eu tiver um comando
$ ./script >> file.log
que é chamado duas vezes, com a segunda chamada antes que a primeira termine, o que acontece?
A primeira chamada recebe um bloqueio exclusivo no arquivo de saída? Nesse caso, o segundo script falha ao tentar gravar ou o shell aceita a saída (permitindo que o script termine) e gera um erro?
Ou o arquivo de log é gravado duas vezes?
Respostas:
Como você está usando
>>
, o que significa anexar, cada linha de saída de cada instância será anexada na ordem em que ocorreu.Se a sua saída de script impressões
1\n
através5\n
com um segundo de atraso entre cada e exemplo dois é iniciado 2,5 segundos mais tarde você vai ter isso:Então, para responder à sua pergunta: Não.
fonte
Os sistemas Unix geralmente evitam bloqueios obrigatórios. Existem alguns casos em que o kernel bloqueia um arquivo contra modificações feitas por programas do usuário, mas não se estiver apenas sendo gravado por outro programa. Nenhum sistema unix bloqueará um arquivo porque um programa está gravando nele.
Se você deseja que instâncias simultâneas do seu script não pisem nos dedos um do outro, é necessário usar um mecanismo de bloqueio explícito, como .
flock
lockfile
Quando você abre um arquivo para anexar, o que
>>
acontece, é garantido que cada programa sempre grave no final do arquivo. Portanto, a saída das várias instâncias nunca se substituirá e, se elas revezarem na gravação, a saída será na mesma ordem que as gravações.O ruim que poderia acontecer é se uma das instâncias gravar vários blocos de saída e esperar que eles saiam juntos. Entre gravações consecutivas por uma instância, outras instâncias podem executar suas próprias gravações. Por exemplo, se a instância 1 gravar
foo
, a instância 2 gravarhello
e somente a instância 2 gravarbar
, o arquivo conteráfoohellobar
.Um processo efetivamente grava no arquivo quando chama a
write
chamada do sistema. Uma chamada parawrite
é atômica: cada chamadawrite
grava uma sequência de bytes que não será interrompida por outros programas. Geralmente, há um limite para a quantidade de dados que uma única chamadawrite
gravará efetivamente: para tamanhos maiores, apenas o início dos dados é gravado e o aplicativo deve chamarwrite
novamente. Além disso, muitos programas executam buffering: eles acumulam dados em uma área de memória e gravam esses dados em um único bloco. Alguns programas liberam o buffer de saída após uma linha completa ou outra separação significativa. Com esses programas, você pode esperar que linhas inteiras sejam ininterruptas, desde que não sejam muito longas (até alguns kilobytes; isso depende do sistema operacional). Se o programa não descarregar em pontos significativos, mas apenas com base no tamanho do buffer, você poderá ver algo como 4kB de uma instância, depois 4kB de outra instância e novamente 4kB da primeira instância e assim por diante.fonte