O “bug nível 256” no jogo do Pacman pode ser considerado um segfault sem tratamento?

51

Eu estou tentando explicar falhas de segmentação para alguém, e eu estava pensando sobre o nível 256 kill-screen no Pacman, e como ele é acionado por estouro de inteiro, e quão similar o comportamento é ao "estado desconhecido" do descrito em uma falha de segmentação.

Eu quero dizer que este é um bom exemplo do que eu chamo de "segfault sem manuseio", mas eu prefiro obter uma segunda opinião antes de potencialmente espalhar desinformação.

Eu tentei pesquisar, mas tudo o que estou recebendo são documentos sobre o bug em si, assim como a colaboração entre a Hipster Whale e a Namco.

Então, você consideraria o comportamento no nível 256 do Pacman como um exemplo de violação de segmentação não tratada?

    
por Braden Best 25.01.2016 / 11:33
fonte

5 respostas

113

Definitivamente não.

Acessar um endereço de memória que você não alocou é sempre um erro de programação. E agir de acordo com as informações que você obtém produz um comportamento indefinido, isso é preciso. Eu não tenho ideia de para qual plataforma o Pac-man original foi escrito, mas tenho certeza que ele exibiu esse comportamento como qualquer outra máquina de von Neumann.

No entanto, "falha de segmentação" é um termo técnico para uma condição muito mais específica. Isso acontece quando o computador detecta automaticamente que isso aconteceu e encerra o processo, em vez de permitir que um comportamento indefinido ocorra. Isso requer um modelo de memória específico (segmentado) com marcação de propriedade sofisticada. Eu não acho que os jogos de arcada de 1980 tinham isso, e na verdade o comportamento do jogo sugere que o erro não foi detectado, e o comportamento indefinido ocorreu. p>     

por 25.01.2016 / 11:39
fonte
38

Parece que você está confundindo "comportamento indefinido" e "falha de segmentação".

Não existe um segfault não manipulado. Uma falha de segmentação é tratamento de erros, por definição.

Se você não tiver um sistema operacional que detecte o acesso a memória ruim e encerre o processo por segurança, você não terá uma falha de segmentação.

Se qualquer coisa, então, este é um bom exemplo de como o UB não sempre resulta em um segfault.

    
por 25.01.2016 / 11:47
fonte
24

Nenhum desses termos é apropriado para um bug em um jogo de arcade que foi programado em linguagem assembly e é executado sem o benefício de hardware ou sistema operacional de proteção de memória.

"Comportamento indefinido" é um termo de arte em C e idiomas relacionados, cunhado pelo comitê de padrões C em 1989. O código tem comportamento indefinido quando a especificação de linguagem não define o que vai fazer. Não existe tal coisa na linguagem assembly Z80: o efeito de cada opcode com todas as entradas possíveis é bem definido. O significado convencional em inglês de "comportamento indefinido" pode ser lido para ser aplicado - a tela de morte é um comportamento não definido pelas pessoas que escreveram o jogo - mas eu não o usaria neste contexto porque é muito provável que ele dê o erro impressão.

"Falha de segmentação" é um termo de arte em POSIX, derivado em última análise do jargão de programação do sistema PDP. Falhas de segmentação acontecem quando um programa tenta acessar um endereço de memória que não está "mapeado" para nada: o hardware e o sistema operacional detectam isso e desligam o programa com defeito, de uma maneira cuidadosamente definida que permite ao programa recuperar . Algo como isso poderia ter acontecido como resultado de um bug no programa de jogo Pac-Man, porque a placa de circuito Pac-Man preenche apenas um pouco menos da metade do espaço de endereço de 64kB do Z80 com ROM, RAM e periféricos, mas não consegui descobrir o que o hardware real faria se o software tentasse acessar a memória não mapeada. Seja o que for que isso faria, seria inapropriado descrever como uma "falha de segmentação", porque o "sistema operacional" para o Pac-Man (na medida em que ele tem um) é não uma implementação do Unix e, novamente, daria a impressão errada.

O bug do nível 256, entretanto, não não acessa a memória não mapeada, então é discutível.

É correto dizer que o jogo tem um bug que se manifesta ao avançar para o nível 256. Também é correto dizer que a causa raiz do bug é um estouro de número inteiro , e que suas conseqüências são corrupção de memória (ou, equivalentemente, violações de memória e segurança de tipo ). Estes são todos os termos CS de propósito geral definidos sem referência a qualquer idioma ou sistema operacional em particular.

Também é preciso observar que os efeitos do bug são similares aos efeitos, dentro de um ambiente moderno, de bugs de corrupção de memória que não provocam segmentação falhas, panes. Se você ler qualquer um dos Project Zero , você verá uma notável semelhança com A análise da tela de morte do Pac-Man de Don Hodges.

Observe que um emulador que não reproduz fielmente a tela de eliminação quando alimentado com as ROMs do Pac-Man não está emulando o hardware do jogo corretamente.

    
por 25.01.2016 / 19:03
fonte
8

O erro de nível 256 no Pac Man resulta no programa lendo dados que está além do final da tabela pretendida, mas ainda é armazenamento legível , e escrevendo para partes da tela que estão além daquelas que o programa pretende escrever, mas ainda estão bem dentro das áreas da tela que o programa pode gravar . Nenhuma outra área de memória é afetada.

A razão pela qual o bug torna o jogo impossível de ser reproduzido é que a máquina determina quando um jogador está comendo pontos examinando o que está na tela e decide que um nível está completo quando o jogador comeu 244 pontos. Ao sobrescrever parte da tela, o bug torna impossível para o jogador comer 244 pontos; consequentemente, o jogo nunca creditará o jogador a completar o nível e recarregar a tela com pontos.

    
por 25.01.2016 / 21:57
fonte
1

Como dito antes, não é uma falha seg. Vou adicionar por que o problema ocorre: é um estouro .

O número do nível é armazenado em um byte, portanto, o intervalo é de 0 a 255. Cada vez que você completa um nível, o contador é incrementado. No nível 256, o contador é de fato 0 devido ao estouro.

No entanto, o jogo tenta exibir algumas frutas na parte inferior do nível. O número / tipo de fruta depende do nível. A fórmula exibe uma fruta por nível terminado no nível 8. De acordo com o contador, você está no nível 0 e abaixo de 8. O teste é verdadeiro e você deve imprimir 255 frutos (o valor do nível antigo). O que é impossível e dá essa tela com falha.

    
por 27.01.2016 / 14:20
fonte

Tags