É tentador ler "segundos desde 1970" como uma contagem precisa dos segundos físicos que se passaram. Não é, e a razão são os segundos bissextos.
O que é um segundo bissexto
A rotação da Terra é levemente irregular e, em média, está desacelerando lentamente. Para manter o tempo do relógio () alinhado com a posição real do Sol, os responsáveis pela medição do tempo ocasionalmente inserem um segundo bissexto — um segundo :60 extra acrescentado ao último minuto de um dia, anunciado alguns meses antes. Desde 1972, mais de duas dúzias foram adicionados.
O tempo Unix desvia o olhar
Eis o fato-chave: o tempo não conta os segundos bissextos. O padrão (Interface Portátil de Sistema Operacional, do inglês Portable Operating System Interface) define um dia como exatamente 86.400 segundos, ponto final. Quando um segundo bissexto acontece, o tempo Unix não ganha um :60; em vez disso o mesmo valor de timestamp é efetivamente usado duas vezes (ou o relógio é ajustado), de modo que a meia-noite sempre cai em um múltiplo redondo de 86.400. O calendário fica arrumado ao custo da exatidão estrita.
A consequência é precisa e um pouco surpreendente: um timestamp Unix não é o número verdadeiro de segundos (Sistema Internacional de Unidades, do inglês International System of Units) decorridos desde a época. Ele está atrasado pelo número de segundos bissextos inseridos no meio do caminho — cerca de 27 segundos no fim da década de 2010. A escala de tempo atômico que de fato conta cada segundo, o (Tempo Atômico Internacional, do inglês International Atomic Time), se distanciou tanto à frente do UTC.
Por que essa é a escolha certa
Contar segundos bissextos faria todo timestamp Unix depender de uma tabela de inserções históricas que também teria de prever as futuras — transformando uma divisão trivial em uma consulta, e quebrando a propriedade limpa de que um dia tem sempre 86.400 segundos. Para a medição de tempo civil — logs, agendas, "quando isto aconteceu" — essa simplicidade vale muito mais do que a exatidão de sub-segundo. Sistemas que genuinamente precisam de cada segundo (física de alta precisão, alguns sistemas financeiros e de navegação) usam TAI ou tempo GPS e convertem deliberadamente.
Um alvo móvel, em breve congelado
Os segundos bissextos sempre foram um incômodo para a computação, e o mundo decidiu parar: uma resolução de 2022 vai aposentar o segundo bissexto até 2035, deixando o UTC e o tempo atômico se distanciarem lentamente em vez de sacudir os relógios. Até lá, a lição prática permanece — trate um timestamp Unix como tempo civil, exato ao segundo para propósitos cotidianos, mas não como a leitura de um cronômetro desde 1970.
30 de junho de 2012: a noite em que de fato quebrou
A teoria acima é elegante. O que aconteceu na prática, na última vez em que um segundo bissexto chegou sem a indústria estar pronta, é a parte de que um operador precisa.
No fim de 30 de junho de 2012 o segundo bissexto foi inserido, e máquinas com Linux começaram a consumir os processadores sem razão visível. O saiu do ar. Os sistemas de reservas da Qantas falharam e voos atrasaram. Aplicações Java prenderam um núcleo cada. As falhas não estavam nas aplicações: estavam numa linha faltando no núcleo.
O commit que corrigiu aquilo, de John Stultz, enuncia a falha com precisão. O código de temporização deixava de atualizar o subsistema de temporizadores de alta resolução depois de um segundo bissexto, de modo que temporizadores baseados no relógio de tempo real expiravam um segundo antes ou depois — e, decisivamente, a discrepância ficava para sempre a menos que outra coisa por acaso atualizasse aquelas estruturas. Um software que arma um temporizador, vê-o disparar de imediato e o arma de novo faz isso num loop muito apertado.
O contorno descoberto pelos operadores naquela noite é o detalhe que vale guardar, porque parece um absurdo e não é:
date -s "$(date)"
Ajuste o relógio para a hora que ele já marca. O valor não muda; o ato de ajustar chama a rotina que atualiza as estruturas de temporizador, e o loop para. Uma operação nula com efeito colateral, que é exatamente o tipo de conserto que só faz sentido depois de se saber o que está quebrado por baixo.
Suavização: a resposta que ficou
O problema mais fundo é que o Unix e o Linux nunca implementaram um sexagésimo primeiro segundo, então o segundo 59 simplesmente roda duas vezes. Software não espera que um instante ocorra duas vezes, e o que ele faz quando isso acontece é indefinido pela aplicação, não pela norma.
A resposta do Google, publicada em 2011 e adotada amplamente desde então, foi recusar a descontinuidade por completo: em vez de repetir um segundo, espalhar o segundo extra por muitas horas, fazendo os relógios andarem fracionalmente devagar. Nenhum instante se repete, nenhum relógio anda para trás, e nenhuma aplicação vê um valor impossível. O custo é que, durante a janela de suavização, a hora da máquina discorda deliberadamente do UTC em até meio segundo — o que é aceitável para quase tudo, e inaceitável para as aplicações que precisam de UTC verdadeiro ao milissegundo.
Os grandes provedores de nuvem hoje suavizam por padrão e publicam a janela que usam. Isso cria o risco prático para quem opera rede: dois equipamentos suavizando em horários diferentes, ou um suavizando e outro saltando, discordam entre si por horas. As fontes de tempo devem ser consistentes num parque, o que significa conferir o que os servidores de cima fazem em vez de supor.
Com os segundos bissextos a caminho da aposentadoria até 2035, este problema tem fim marcado. Até lá, a resposta correta para "o que nossos sistemas farão no próximo segundo bissexto" não é uma opinião; é um teste.
Fontes
- O commit do núcleo Linux que corrigiu, de John Stultz: o código de temporização deixa de atualizar o subsistema hrtimer depois de um segundo bissexto, então temporizadores baseados no CLOCK_REALTIME expiram um segundo antes ou depois, e a discrepância fica para sempre a menos que a atualização aconteça por outro meio; o contorno relatado provoca uma chamada a clock_was_set(), que atualiza as estruturas do hrtimer
- CBC, junho de 2015: o segundo bissexto de 30 de junho de 2012 fez falhar os sistemas de reserva de voos da Qantas, atrasando voos, e tirou o Reddit do ar quando seus servidores Linux não deram conta; outros sites foram afetados de forma semelhante
- Nota de suporte da IBM: Linux e Unix não implementaram um sexagésimo segundo, então o segundo 59 é executado duas vezes, e como os processos não esperam que um instante ocorra duas vezes, comportamento imprevisível pode ocorrer; alta utilização de CPU pode ser vista quando o segundo bissexto acontece
- Lista NANOG, janeiro de 2015: o Java teve problemas de 100% de uso de CPU quando o NTP estava rodando durante o segundo adicional em 2012, e o Google fez algo diferente para inserir o segundo extra, descrito em seu texto de 2011 sobre tempo, tecnologia e segundos bissextos
- AWS, maio de 2015: um segundo extra foi injetado no fim de 30 de junho de 2015, de modo que o último minuto do dia teve 61 segundos, marcando 23:59:60 em relógios sincronizados com o tempo civil padrão; relógios em sistemas de TI nem sempre seguem esse padrão e podem se comportar de muitas maneiras diferentes