3 pontos por GN⁺ 2024-05-09 | 1 comentários | Compartilhar no WhatsApp
  • A falha da kill screen de NES Tetris não é apenas um fim de jogo: ela pode ser usada como ponto de entrada para executar novos comportamentos em hardware e cartucho não modificados
  • Depois do nível 155, se o cálculo da pontuação não terminar entre um quadro e outro, o fluxo de controle se quebra e o jogo pode acabar em execução arbitrária de código, lendo posições inesperadas da RAM como se fossem instruções
  • A RAM de entrada da porta de controle de expansão do Famicom se sobrepõe à posição da rotina de salto, permitindo manipular o endereço para onde o jogo vai após a falha por meio dos botões dos controles 3 e 4
  • A Displaced Gamers publicou um código de prova de conceito que envia o destino do salto para a tabela de recordes, fazendo o jogo ler dados de nomes e pontuações como opcodes da CPU do NES
  • A utilidade prática é limitada pelos caracteres e números que podem ser inseridos e pela falta de armazenamento, mas há possibilidade de expansão para patches que evitem a falha ou para controle total da RAM

Como a falha da kill screen vira execução de código

  • A falha em NES Tetris pode ocorrer quando o processador de pontuação demora demais para calcular a nova pontuação entre um quadro e outro
    • Essa situação pode aparecer depois do nível 155
    • Quando há atraso, parte do código de controle é interrompida pela rotina de escrita de um novo quadro
    • Depois disso, o jogo salta para uma posição inesperada da RAM em busca da próxima instrução
  • Em geral, esse salto inesperado faz o jogo ler dados lixo no início da RAM como se fossem código, levando a uma falha rápida
  • Um vídeo recente da Displaced Gamers revelou um procedimento para fazer NES Tetris ler a tabela de recordes como instruções de máquina
    • Glitches semelhantes de execução arbitrária de código já eram conhecidos em Super Mario World, Paper Mario e The Legend of Zelda: Ocarina of Time
    • O método básico para inserir código externo em NES Tetris já era teorizado publicamente desde pelo menos 2021, e diz-se que métodos de controle total da RAM já eram conhecidos havia muito tempo dentro da comunidade

Controle da posição do salto via processamento de entradas do Famicom

  • Esse hack depende não só da forma como Tetris falha, mas também da estrutura de entrada do Famicom
  • Diferente do NES americano, o Famicom japonês tinha dois controles conectados de forma fixa ao console, e controles de terceiros podiam ser conectados à porta de expansão frontal
  • O código de Tetris lê as entradas dessa porta de controles “extra”
    • Com um adaptador, é possível conectar mais dois controles padrão de NES
    • O Famicom tinha uma versão separada de Tetris da Bullet-Proof Software, mas essa característica de processamento de entradas funciona no código de NES Tetris
  • A área de RAM que processa as entradas dos controles adicionais se sobrepõe à posição de memória da rotina de salto usada durante a falha
    • Quando a rotina de salto é interrompida pela falha, essa RAM contém dados que representam os botões pressionados nos controles
    • O jogador pode usar esses valores para controlar com precisão para onde o código do jogo vai após a falha

Lendo a tabela de recordes como código executável

  • O método de controle de salto da Displaced Gamers exige entradas específicas nos controles
    • Pressionar up no controle 3
    • Pressionar right, left e down no controle 4
    • Para inserir left e right ao mesmo tempo, é necessário modificar o controle
  • Essa entrada envia o código de salto para a área da RAM onde ficam armazenados os nomes e pontuações da lista de recordes do jogo
  • Ao colocar (G na posição-alvo da tabela de recordes do B-Type, o jogo salta novamente para outra área da tabela de recordes
  • Depois disso, o jogo lê nomes e pontuações em sequência e os processa como opcodes da CPU do NES, em um estilo que a Displaced Gamers chamou de código “bare metal”

Possibilidades e limites demonstrados pela prova de conceito

  • A área de entrada de nomes dos recordes permite usar apenas 43 símbolos, e as pontuações só podem conter 10 algarismos
    • Por causa dessa restrição, só é possível “programar” na tabela de recordes uma parte dos opcodes disponíveis no NES
  • Mesmo com entradas limitadas, foi possível criar um código de prova de conceito curto
    • Os dados de exemplo incluem o nome ))"-P) e a pontuação de 8.575 na 2ª posição do A-Type
    • Essa rotina zera os dois algarismos mais altos da pontuação do jogo
    • Isso reduz o tempo de processamento da pontuação e diminui a causa da falha, mas, se o jogador continuar jogando, a pontuação volta a atingir a “zona de risco” de falha
  • O NES Tetris original não tem armazenamento com backup por bateria, então é necessário recriar manualmente os recordes e nomes complexos exigidos a cada vez que o console é ligado
  • O espaço da tabela de recordes também é limitado, o que dificulta inserir programas complexos diretamente sobre o código real de Tetris
  • HydrantDude escreveu que existe uma forma de criar um bootstrapper com combinações específicas de nomes e números na tabela de recordes e, em seguida, criar outro bootstrapper para obter controle total da RAM

Possibilidade de reprogramação para além de evitar a falha

  • Se o controle total da RAM se tornar possível, jogadores de alto nível também poderiam recodificar o jogo para aplicar um patch no bug de falha de NES Tetris
  • Esse método pode ser especialmente útil para jogadores que tentam passar do nível 255
    • Depois do nível 255, o jogo volta para o Level 0
  • Expandindo o mesmo princípio, também seriam possíveis transformações como mudar Tetris para Flappy Bird, em um caso semelhante ao dos speedrunners de Super Mario World

1 comentários

 
GN⁺ 2024-05-09
Comentários do Hacker News
  • Exploits como esse sempre me lembram o estágio final definitivo de hacking em Accelerando, de Stross: “fazer um ataque de canal de temporização contra a superestrutura computacional do próprio espaço-tempo, tentando invadir algo por baixo dela”

    • Eu não gostaria de estar dentro do cone de luz de alguém que fizesse uma tentativa com qualquer mínima chance de sucesso
      Parece uma ótima maneira de provocar um decaimento do vácuo e fazer o universo dar tela azul
    • O livro pode ser baixado gratuitamente no blog do autor: https://www.antipope.org/charlie/blog-static/fiction/acceler...
    • Acabei de encontrar um erro de sincronização, então talvez seja um bom caso de borda para começar: https://www.science.org/content/article/quantum-paradox-poin...
    • Acho que isso normalmente se chama física
    • Espaço-tempo? Por que se limitar ao espaço? Meta-tempo é muito mais interessante
  • Gosto muito de pessoas assim
    Chega a me dar vergonha eu não ter essa mentalidade hacker de tentar coisas que provavelmente são inúteis só pela diversão

    • Será que a maioria desses hackers nasceu com um fundo fiduciário? Gente com o futuro garantido e nada além de tédio?
      O resto de nós está ocupado demais tentando sobreviver para ter tempo de fazer exploits assim, sem trocadilho intencional
  • Se você não quer ler o texto inteiro, mas está se perguntando “achei que cartuchos de NES rodassem a partir de ROM?”, é isso mesmo
    Só que esse exploit faz a CPU saltar para a RAM usada para armazenar a tabela de recordes. Muito bacana

  • O processo de chegar à execução arbitrária de código é sempre mais interessante do que o que se faz depois
    A obstinação de desmontar o jogo para descobrir quando e onde ele faz esse comportamento, e encontrar que parte precisa ser manipulada para inserir instruções, é admirável

  • Quanto tempo até alguém rodar Doom dentro de Tetris?

    • Talvez isso exija um cartucho de expansão de RAM
  • Tempo bem desperdiçado

    • O que você faz por diversão? Também considera isso perda de tempo?
      Pergunto de verdade. Eu costumava considerar até coisas divertidas como perda de tempo, mas, depois de pagar o preço de viver sob estresse alto por muito tempo, fui mudando de ideia com a idade
  • Quero tentar fazer isso com Factorio
    Criar um computador gigante feito de esteiras dentro de Factorio e provocar uma falha de segmentação para escapar para fora do jogo

  • Encontrar execução arbitrária de código em jogos antigos é realmente fascinante
    Quando vi algo assim em Super Mario World alguns anos atrás, fiquei obcecado por um tempo em entender como aquilo era possível
    Digo isso no bom sentido, como elogio, embora possa soar meio maldoso: adoro ver pessoas realmente inteligentes gastando tempo e esforço enormes em algo completamente inútil
    Existe algum motivo imediato para injetar código no NES Tetris? Provavelmente não. Mas o ponto não é esse; é descobrir o que é possível e até onde dá para forçar código antigo e computadores primitivos a fazerem coisas
    Talvez não seja “útil” no sentido clássico, mas o mesmo vale para Sudoku, palavras cruzadas ou até jogar NES Tetris em primeiro lugar

    • Escondido pelos detalhes técnicos, este exploit também tem um propósito prático
      Ele permite que jogadores de alto nível evitem um travamento que impede a partida depois de certo ponto e joguem por mais tempo
      Para o jogador médio, não há utilidade prática, mas, para quem quer competir por recordes, ele remove um limite e abre novas possibilidades de competição
    • Muitas descobertas científicas foram feitas por pessoas realmente inteligentes gastando tempo e esforço em coisas completamente inúteis
      Teoria dos números também era considerada inútil, mas hoje sustenta praticamente toda a criptografia de chave pública
    • Não é inútil. Eles gostam de fazer isso
      A utilidade que os outros obtêm de coisas que eu faço sem gostar é um subproduto feliz, ou algo que me beneficia indiretamente, como dinheiro ou reconhecimento
      Fazer algo por gostar é a forma mais direta de utilidade para a pessoa mais importante: você mesmo
    • O canal desse cara no YouTube é a essência disso: https://www.youtube.com/@tom7
  • Sinceramente, é surpreendente que Tetris tenha sido quebrado tão tarde
    Acho que isso vai abrir uma nova era de runs any%. O objetivo é acionar a cena final ou os créditos do jogo o mais rápido possível
    Meu exemplo favorito é Ocarina of Time, que já tinha exploits de ACE havia alguns anos
    O jogo é tão quebrado que, manipulando a memória do jogo e editando um warp de entrada específico, dá para “zerar” em poucos minutos
    O mais surpreendente é que as pessoas editam memória manualmente, usando só alguns botões e um joystick analógico
    Um caso em que os créditos aparecem em 3 minutos: https://www.speedrun.com/oot/runs/z1l1627m

    • Vi algo parecido em Super Mario
      Ao encontrar uma falha no túnel de warp, isso acionava uma leitura fora dos limites, e antes disso a pessoa usava manipulações do joystick para escrever, logo fora do buffer, os bytes que causariam o comportamento desejado
      Em um dos jogos de Pokemon, era preciso fazer um monte de transações de compra/venda para preparar a memória com precisão e então causar overflow na quantidade de itens para acionar o salto
      É algo realmente fantástico. Um dia, se alienígenas atacarem, essas brincadeiras vão nos salvar
    • Pelo que li no texto, isso parece improvável
      Este ACE parece depender primeiro de chegar à kill screen
      Imagine se o ACE de Ocarina of Time só fosse acionado depois dos créditos finais; como ele só aconteceria depois de uma conclusão bem-sucedida, não daria para reduzir o tempo
    • Você disse que é surpreendente que Tetris tenha sido quebrado tão tarde; sinceramente, fico curioso sobre o que antes fazia você pensar que a execução arbitrária seria possível
  • Gosto muito desse tipo de trabalho
    Isso me lembra quando programaram Flappy Bird dentro de Super Mario World usando uma falha. É insano
    https://www.youtube.com/watch?v=hB6eY73sLV0