aggregation.drawio

Suponha que você tenha um grande número de objetos que podem ser enviados pelos usuários, que todos (se válidos) precisam ser transmitidos para que possam ser descobertos e incluídos por algum nó construtor final. Suponha também que a condição de validade possa ser expressa em um STARK, e que estejamos em um ambiente pós-quântico onde SNARKs de curva elíptica não funcionarão.

Isso se aplica a pelo menos três casos de uso no Ethereum:

  • Agregação de assinaturas da camada de execução pós-quântica, especialmente se os usuários estiverem usando protocolos de privacidade
  • Agregação de assinaturas da camada de consenso pós-quântica, para lidar com um grande número de validadores
  • Transmitindo raízes de blob, em um modelo de construção de bloco distribuído onde assumimos que o número total de blobs é muito grande para um construtor fazer o download completo e, portanto, o construtor deve baixar raízes dos remetentes de blob e, em seguida, usar o DAS para verificar sua disponibilidade. O STARK verifica se a codificação de apagamento foi calculada corretamente

O problema: os STARKs são caros, ocupando 128 kB mesmo em implementações com tamanho altamente otimizado. Se cada objeto enviado por um usuário fosse transmitido para todos junto com os 128 kB completos de sobrecarga STARK, as necessidades de largura de banda (tanto para nós intermediários do mempool quanto para o construtor) seriam esmagadoras.

Veja como podemos resolver esse problema.

Quando um usuário envia um objeto para o mempool, ele pode enviar esse objeto junto com um direto prova de validade (por exemplo, uma ou mais assinaturas, dados de chamada EVM que passam em alguma função de validação) ou uma prova de validade STARK.

Os nós Mempool seguem o seguinte algoritmo:

  • Eles esperam passivamente e recebem objetos dos usuários. Quando veem um objeto, validam sua prova. Se a prova for válida, eles a aceitam.
  • A cada tick (por exemplo, 500 ms), eles geram um STARK recursivo provando a validade de todos os objetos ainda válidos que conhecem. Eles encaminham essa prova para seus pares, além de enviar a cada par quaisquer objetos (sem provas) que ainda não tenham enviado a esse par.

A lógica do STARK recursivo é a seguinte. A entrada pública é um campo de bits ou uma lista de hashes, representando o conjunto de objetos cuja validade a prova prova. A prova então espera:

  • 0 ou mais objetos, com suas provas de validade (sejam provas diretas ou STARKs)
  • 0 ou mais outros STARKs recursivos do mesmo tipo
  • Um campo de bits de lista hash de objetos a serem descartados (isso permite descartar objetos expirados)

A prova atesta a validade da união de todos os objetos e de todas as entradas públicas de starks recursivos alimentadas nela, menos os objetos que são descartados.

Em forma de diagrama (aqui, para o caso de uso de agregação de assinatura da camada de execução):

Neste exemplo, o primeiro nó do mempool vê Tx 1 e Tx 2 (com provas diretas) e cria um STARK recursivo provando que {Tx 1, Tx 2} são válidos. O segundo nó do mempool vê a mensagem do primeiro nó, que contém Tx 1 e Tx 2 (sem provas diretas) mais o STARK, e também vê Tx 3 (com uma prova direta), e cria um STARK recursivo provando que {Tx 1, Tx 2, Tx 3} são válidos. Ele envia isso para seus pares, dos quais um é construtor, que o recebe e inclui.

Se o construtor receber múltiplas mensagens contendo conjuntos de objetos não totalmente sobrepostos e o construtor desejar incluir ambos, o próprio construtor poderá fazer um STARK recursivo combinando-os. O construtor também pode descartar quaisquer objetos (aqui, transações) que eles vejam que não são mais válidos para inclusão.

A sobrecarga total deste esquema é:

  • Cada objeto, sem sua prova, é transmitido para cada nó (nota: no caso de agregação da camada de consenso, isso pode ser compactado para 1 bit por participante). Isto tem a mesma largura de banda que o status quo hoje, exceto que podemos retirar assinaturas.
  • Cada nó tem largura de banda extra de entrada e saída igual ao tamanho de um STARK por tick, multiplicado por seu número de peers (por exemplo, com 8 peers e ticks de 500 ms, isso é 128 kB * 8/0,5 = 2 MB/s). Isso é constante e não aumenta à medida que aumenta o número de objetos que os usuários enviam.

Fontesethresear

By victor

Deixe um comentário

O seu endereço de e-mail não será publicado. Campos obrigatórios são marcados com *