Autorização binária para o Borg

Este conteúdo foi atualizado pela última vez em maio de 2024 e representa o status quo no momento em que foi escrito. As políticas e os sistemas de segurança da Google podem mudar no futuro, à medida que melhoramos continuamente a proteção dos nossos clientes.

Este documento descreve como utilizamos revisões de código, infraestrutura de segurança e uma verificação de aplicação denominada autorização binária para o Borg (BAB) para ajudar a proteger a cadeia de fornecimento de software da Google contra o risco interno. A BAB ajuda a reduzir o risco interno porque garante que o software de produção é revisto e aprovado antes de ser implementado, especialmente quando o nosso código pode aceder a dados confidenciais. A BAB aplica-se a todos os serviços que estão a ser executados no Borg. Desde a publicação original deste documento, incluímos conceitos-chave da BAB numa especificação aberta denominada Níveis da cadeia de fornecimento para artefactos de software (SLSA).

Este documento faz parte de uma série de documentos técnicos que descrevem alguns projetos que a equipa de segurança da Google desenvolveu para ajudar a melhorar a segurança, incluindo o BeyondCorp e o BeyondProd. Para uma vista geral da segurança da nossa infraestrutura, consulte a vista geral da conceção de segurança da infraestrutura da Google.

Introdução

O risco interno representa uma ameaça à segurança dos dados do utilizador, que podem incluir dados de emprego, dados financeiros ou outros dados proprietários ou empresariais. O risco interno é a potencialidade de um funcionário usar os seus conhecimentos organizacionais ou acesso para realizar atos maliciosos, ou de um atacante externo usar as credenciais comprometidas de um funcionário para fazer o mesmo.

Para minimizar o risco interno na nossa cadeia de abastecimento de software, usamos o BAB. BAB é uma verificação de aplicação interna que ocorre quando o software é implementado. O BAB garante que as implementações de código e configuração cumprem determinadas normas mínimas e suportam a uniformidade nos nossos sistemas de produção.

Ajudamos a proteger os dados do utilizador nos nossos sistemas de produção limitando o acesso unilateral pelos nossos funcionários. A BAB ajuda a garantir que os funcionários, enquanto atuam sozinhos, não podem aceder direta ou indiretamente nem afetar de outra forma os dados do utilizador sem a autorização e a justificação adequadas. A BAB e os respetivos controlos ajudam-nos a aplicar o princípio do menor privilégio, o que melhora a nossa postura de segurança independentemente de um ator de ameaças específico. Por outras palavras, o BAB limita o acesso unilateral, independentemente de o ator ter intenções maliciosas, de a respetiva conta ter sido comprometida ou de lhe ter sido concedido acesso involuntariamente.

Vantagens do BAB

A adoção do BAB e de um modelo de implementação em contentores oferece muitas vantagens de segurança à infraestrutura da Google. As vantagens incluem o seguinte:

  • A BAB ajuda a reduzir o risco interno geral: a BAB requer que o código cumpra determinados padrões e práticas de gestão de alterações antes de poder aceder aos dados do utilizador. Este requisito reduz o potencial de um funcionário a agir sozinho (ou uma conta de funcionário comprometida) para aceder aos dados do utilizador por programação.
  • O BAB suporta a uniformidade dos sistemas de produção: através da utilização de sistemas contentorizados e da verificação dos respetivos requisitos do BAB antes da implementação, os nossos sistemas tornam-se mais fáceis de depurar, mais fiáveis e têm processos de gestão de alterações bem definidos. Os requisitos da BAB fornecem uma linguagem comum para os requisitos do sistema de produção.
  • A BAB dita uma linguagem comum para a proteção de dados: a BAB monitoriza a conformidade nos sistemas Google. Os dados sobre esta conformidade são publicados internamente e estão disponíveis para outras equipas. A publicação de dados de BAB permite que as equipas usem termos comuns quando comunicam entre si acerca da respetiva proteção de acesso aos dados. Esta linguagem comum reduz o trabalho de troca de informações necessário quando trabalha com dados entre equipas.
  • A BAB permite a monitorização programática dos requisitos de conformidade: a BAB simplifica as tarefas de conformidade que eram anteriormente manuais. Determinados processos na Google requerem controlos mais rigorosos sobre a forma como lidamos com os dados. Por exemplo, os nossos sistemas de relatórios financeiros têm de estar em conformidade com a Lei Sarbanes-Oxley (SOX). Antes da BAB, tínhamos um sistema que nos ajudava a fazer manualmente validações para garantir a nossa conformidade. Com a introdução da BAB, muitas destas verificações foram automatizadas com base nas políticas da BAB para os serviços. A automatização destas verificações permitiu à equipa de conformidade aumentar o âmbito dos serviços abrangidos e a adoção de controlos adequados nestes serviços.

O BAB faz parte da estrutura mais ampla BeyondProd que usamos para mitigar o risco interno.

O nosso processo de desenvolvimento e produção

Por predefinição, o processo de desenvolvimento e produção da Google inclui quatro passos obrigatórios: revisão do código, compilações verificáveis, implementação em contentores e identidade baseada em serviços. As secções seguintes descrevem estes passos com mais detalhe.

Passo 1: revisão do código

A maior parte do nosso código-fonte está armazenada num repositório monolítico central, e requer revisão e aprovação de, pelo menos, um engenheiro que não seja o autor. Uma base de código monolítica permite a aplicação de um único ponto de restrição para revisões de código.

No mínimo, o nosso processo de revisão de código requer que os proprietários de um sistema aprovem as modificações de código desse sistema.

Quando importa alterações de terceiros ou código open source, verificamos se a alteração é adequada (por exemplo, a versão mais recente). No entanto, muitas vezes, não temos os mesmos controlos de revisão em vigor para todas as alterações feitas por programadores externos ao código open source ou de terceiros que usamos.

Passo 2: compilações validáveis

O nosso sistema de compilação é semelhante ao Bazel, que compila código fonte para criar um ficheiro binário para implementação. O nosso sistema de compilação é executado num ambiente isolado e bloqueado que está separado dos funcionários que realizam as compilações. Para cada compilação, o sistema produz uma proveniência gerada por compilações validáveis . Esta proveniência é um certificado assinado que descreve as origens e as dependências que foram usadas na compilação, os hashes criptográficos de todos os ficheiros binários ou outros artefactos de compilação e os parâmetros de compilação completos. Esta proveniência permite o seguinte:

  • A capacidade de rastrear um ficheiro binário até ao código-fonte que foi usado na sua criação. Por extensão, a proveniência também pode rastrear o processo em torno da criação e do envio do código fonte que descreve.
  • A capacidade de verificar se o ficheiro binário não foi modificado, uma vez que quaisquer alterações ao ficheiro invalidariam automaticamente a respetiva assinatura.

Uma vez que as ações de compilação podem ser código arbitrário, o nosso sistema de compilação foi reforçado para multi-tenancy. Por outras palavras, o nosso sistema de compilação foi concebido para impedir que uma compilação influencie outras compilações. O sistema impede que as compilações façam alterações que possam comprometer a integridade da proveniência da compilação ou do próprio sistema. Após a conclusão da compilação, a alteração é implementada através do Borg.

Passo 3: implementação em contentores

Depois de o sistema de compilação criar o ficheiro binário, este é incluído num contentor de imagem e implementado como uma tarefa do Borg no nosso sistema de orquestração de clusters, Borg. Executamos centenas de milhares de tarefas a partir de muitas aplicações diferentes, em vários clusters, cada um com até dezenas de milhares de máquinas. Apesar desta escala, o nosso ambiente de produção é bastante homogéneo. Como resultado, os pontos de contacto para acesso aos dados do utilizador podem ser controlados e auditados mais facilmente.

Os contentores oferecem vantagens de segurança notáveis. Os contentores destinam-se a ser imutáveis, com reimplementações frequentes a partir de uma recriação completa da imagem. A contentorização permite-nos rever uma alteração de código no contexto e fornece um único ponto de estrangulamento para as alterações implementadas na nossa infraestrutura.

A configuração de uma tarefa do Borg especifica os requisitos para a implementação da tarefa: as imagens de contentores, os parâmetros de tempo de execução, os argumentos e os indicadores. O Borg agenda a tarefa, tendo em conta as restrições, a prioridade, a quota e quaisquer outros requisitos indicados na configuração. Após a implementação da tarefa, a tarefa do Borg pode interagir com outras tarefas em produção.

Passo 4: identidade baseada em serviços

Uma tarefa do Borg é executada como uma identidade de serviço. Esta identidade é usada para aceder a repositórios de dados ou a métodos de chamada de procedimento remoto (RPC) de outros serviços. Vários trabalhos podem ser executados como a mesma identidade. Apenas os funcionários responsáveis por executar o serviço (normalmente engenheiros de fiabilidade de sites [SREs]) podem implementar ou modificar tarefas com uma identidade específica.

Quando o Borg inicia uma tarefa, aprovisiona-a com credenciais criptográficas. A tarefa usa estas credenciais para comprovar a respetiva identidade quando faz pedidos a outros serviços através da segurança de transporte da camada de aplicação (ALTS). Para que um serviço aceda a determinados dados ou a outro serviço, a respetiva identidade tem de ter as autorizações necessárias.

As nossas políticas requerem a proteção BAB para identidades de serviços que tenham acesso a dados do utilizador e a quaisquer outras informações confidenciais. Os trabalhos de controlo de qualidade e desenvolvimento que não tenham acesso a dados confidenciais podem ser executados com menos controlos.

Como funciona o BAB

O BAB integra-se com o Borg para garantir que apenas os trabalhos autorizados podem ser executados com a identidade de cada serviço. O BAB também cria uma trilha de auditoria do código e da configuração usados em tarefas ativadas pelo BAB para permitir a monitorização e a resposta a incidentes.

A BAB foi concebida para garantir que todo o software e configuração de produção são revistos, registados, criados de forma verificável e autorizados corretamente, especialmente quando esse código pode aceder aos dados do utilizador.

Política específica do serviço

Quando os proprietários de serviços incorporam o respetivo serviço no Borg, criam uma política de BAB que define os requisitos de segurança para o respetivo serviço. Esta política é denominada política específica de serviços. Definir ou modificar uma política é, em si, uma alteração ao código que tem de ser revista.

A política específica do serviço define que código e configuração podem ser executados como a identidade do serviço, bem como as propriedades necessárias desse código e configuração. Todas as tarefas executadas como identidade do serviço têm de cumprir a política específica do serviço.

Todos os serviços Borg no Google têm de configurar uma política específica do serviço.

Por predefinição, esta prática aplica os seguintes requisitos:

  • O código tem de ser auditável: podemos rastrear a imagem do contentor até às respetivas origens legíveis por humanos através da proveniência gerada por compilações validáveis. Uma política de retenção mantém as origens legíveis do código durante, pelo menos, 18 meses, mesmo que o código não seja enviado.
  • O código tem de ser enviado: O código é criado a partir de uma localização especificada e definida no nosso repositório de origem. Geralmente, o envio implica que o código foi sujeito a uma revisão do código.
  • As configurações têm de ser enviadas: Todas as configurações fornecidas durante a implementação passam pelo mesmo processo de revisão e envio que o código normal. Por conseguinte, não é possível modificar os valores, os argumentos e os parâmetros das flags da linha de comandos sem revisão.

Os serviços que não têm acesso a dados confidenciais ou, em circunstâncias raras, os serviços que têm uma exceção válida e aprovada, podem ter uma política mais permissiva, como uma que apenas exija a capacidade de auditoria do código ou até mesmo uma que desative completamente o BAB.

Os sistemas e os componentes que aplicam a BAB são rigorosamente controlados através de requisitos automatizados estritos e controlos manuais adicionais.

Modos de aplicação

A BAB usa dois modos de aplicação para garantir que os trabalhos estão em conformidade com a política específica do serviço:

  • Aplicação no momento da implementação, que impede a implementação de tarefas não conformes.
  • Validação contínua, que monitoriza e envia alertas sobre tarefas não conformes que foram implementadas.

Além disso, em caso de emergência, os procedimentos de resposta a emergências podem ignorar a aplicação no momento da implementação.

Modo de aplicação no momento da implementação

O Borg Prime é o controlador centralizado do Borg, que funciona como a autoridade de certificação para ALTS. Quando uma nova tarefa é enviada, o Borg Prime consulta o BAB para verificar se a tarefa cumpre os requisitos das políticas específicas do serviço antes de o Borg Prime conceder o certificado ALTS à tarefa. Esta verificação funciona como um controlador de admissão: o Borg só inicia a tarefa se satisfizer a política específica do serviço. Esta verificação ocorre mesmo quando o funcionário ou o serviço que faz o pedido de implementação está autorizado de outra forma.

Em casos raros, os serviços podem recusar a aplicação no momento da implementação com uma justificação adequada.

Modo de validação contínua

Após a implementação de uma tarefa, esta é validada continuamente durante a respetiva duração total, independentemente do modo de aplicação no momento da implementação. Um processo BAB é executado, pelo menos, uma vez por dia para verificar se os trabalhos iniciados (e que ainda podem estar em execução) estão em conformidade com as atualizações das respetivas políticas. Por exemplo, o modo de validação contínua verifica constantemente se existem trabalhos em execução com políticas desatualizadas ou que foram implementados através de procedimentos de resposta a emergências. Se for encontrado um trabalho que não cumpre a política mais recente, o BAB notifica os proprietários do serviço para que possam mitigar o risco.

Procedimentos de resposta a emergências

Quando ocorre um incidente ou uma indisponibilidade, a nossa primeira prioridade é restaurar o serviço afetado o mais rapidamente possível. Numa situação de emergência, pode ser necessário executar código que não tenha sido revisto nem criado de forma verificável. Como resultado, o modo de aplicação pode ser substituído através de uma flag de resposta de emergência. Os procedimentos de resposta de emergência também atuam como uma alternativa caso ocorra uma falha da BAB que, de outra forma, bloquearia uma implementação. Quando um programador implementa uma tarefa através do procedimento de resposta a emergências, tem de enviar uma justificação como parte do pedido.

Durante uma resposta de emergência, o BAB regista detalhes sobre a tarefa do Borg associada e envia uma notificação à equipa de segurança centralizada da Google e à equipa proprietária da identidade do serviço. A entrada de registo inclui uma referência a uma captura de ecrã do código implementado e a justificação fornecida pelo utilizador. Os procedimentos de resposta a emergências destinam-se apenas a ser usados como último recurso.

Extensão da BAB a outros ambientes

Inicialmente, o BAB só suportava a proteção de tarefas do Borg e exigia que o software fosse desenvolvido através do pipeline de controlo de origem, compilação e embalagem tradicionais da Google. Agora, a BAB adicionou suporte para proteger outros ambientes de implementação e entrega de software, bem como suporte para sistemas alternativos de controlo de origem, compilação e embalagem. Os detalhes de implementação destes vários ambientes diferem, mas as vantagens da BAB mantêm-se.

Existem alguns casos que não se adequam bem às revisões de código humano antes da implementação, nomeadamente o desenvolvimento iterativo de código de aprendizagem automática e a análise de dados de alta frequência. Nestes casos, temos controlos alternativos que compensam a revisão humana.

Adotar controlos semelhantes na sua organização

Esta secção descreve as práticas recomendadas que aprendemos à medida que implementámos a BAB, para que possa adotar controlos semelhantes na sua organização.

Crie uma pipeline de CI/CD homogénea e contentorizada

A adoção da BAB foi facilitada porque a maioria das equipas usava um único sistema de controlo de origem, processo de revisão de código, sistema de compilação e sistema de implementação. As revisões de código já faziam parte da nossa cultura, pelo que conseguimos fazer alterações sem muitas alterações significativas visíveis para o utilizador. Para adotar a BAB, focámo-nos em revisões de código, compilações verificáveis, implementações em contentores e identidades baseadas em serviços para o controlo de acesso. Esta abordagem simplificou a adoção de BAB e reforçou as garantias que uma solução como BAB pode oferecer.

A nossa utilização generalizada de microsserviços e identidades baseadas em serviços (como contas de serviço), em vez de identidades baseadas em anfitriões (como endereços IP), permite-nos criar um controlo detalhado sobre o software que tem autorização para executar cada serviço.

Se a sua organização não conseguir adotar uma identidade de serviço diretamente, pode tentar proteger os tokens de identidade através de outras medidas como passo provisório.

Determine os seus objetivos e defina as suas políticas com base nos seus requisitos

Crie o seu processo de lançamento orientado por políticas passo a passo. Pode ter de implementar determinadas alterações mais cedo do que outras no pipeline de CI/CD. Por exemplo, pode ter de começar a realizar revisões de código formais antes de as poder aplicar no momento da implementação.

A conformidade é um grande motivador para um processo de lançamento orientado por políticas. Se conseguir codificar, pelo menos, alguns dos seus requisitos de conformidade numa política, pode ajudar a automatizar os testes e garantir que estão em vigor de forma fiável. Comece com um conjunto base de requisitos e codifique requisitos mais avançados à medida que avança.

Aplique políticas no início do desenvolvimento

É difícil definir políticas abrangentes num software sem primeiro saber onde vai ser executado e a que dados vai aceder. Por conseguinte, a aplicação de políticas específicas do serviço é feita quando o código é implementado e quando acede aos dados, e não quando é criado. Uma política é definida em termos de uma identidade de tempo de execução, pelo que o mesmo código pode ser executado em diferentes ambientes e estar sujeito a diferentes políticas.

Usamos o BAB, além de outros mecanismos de acesso, para limitar o acesso aos dados do utilizador. Os proprietários de serviços podem garantir ainda mais que os dados só são acedidos por uma tarefa que cumpra requisitos BAB específicos.

Recrute agentes de mudança em várias equipas

Quando criámos um mandato ao nível da Google para a implementação da BAB, o que mais afetou a nossa taxa de êxito foi encontrar proprietários para impulsionar a alteração em cada grupo de produtos. Identificámos alguns proprietários de serviços que viram benefícios imediatos com a aplicação e estavam dispostos a dar feedback. Pedimos a estes proprietários que se voluntariassem antes de tornar obrigatórias quaisquer alterações. Depois de recebermos a ajuda da Google, configurámos uma equipa formal de gestão de alterações para acompanhar as alterações em curso. Em seguida, identificámos proprietários responsáveis em cada equipa de produto para implementar as alterações.

Determine como gerir o código de terceiros

Se tiver de gerir código de terceiros, considere como vai introduzir os seus requisitos de política na base de código de terceiros. Por exemplo, pode começar por manter um repositório de todo o código de terceiros usado. Recomendamos que valide regularmente esse código em função dos seus requisitos de segurança.

Para mais informações sobre a gestão de código de terceiros, consulte o artigo Sucesso partilhado na criação de uma comunidade de código aberto mais segura.

O que se segue?