Mistério dos arquivos binários

Mistério dos arquivos binários

Trata-se de arquivos direto do compilador, digamos g++, e do -osinalizador (outfile).

Se eles são binários, não deveriam ser apenas um monte de 0 e 1?

Ao catá-los, você obtém resultados ininteligíveis, mas também palavras intactas.

Se você arquivá-los, obterá a resposta imediatamente - parece não haver cálculo. Os arquivos binários de fato possuem cabeçalhos com esse tipo de informação?

Achei que um executável binário fosse apenas o programa recém-compilado, apenas na forma de instruções de máquina que sua CPU pudesse entender de forma instantânea e inequívoca. Se sim, esse conjunto de instruções não é apenas padrões de bits? Mas então, quais são todas as outras coisas nos binários? Como você exibe os bits?

Além disso, se você de alguma forma obtiver o manual do seu processador, poderá escrever um binário manualmente, uma instrução de máquina por vez? Isso seria terrivelmente ineficaz, masmuitofascinante se você conseguir que funcione mesmo para um "Olá, mundo!" demonstração.

Responder1

Esta pergunta do superusuário:Por que você não vê o código binário quando abre um arquivo binário com um editor de texto?aborda muito bem o seu primeiro ponto.

Os dados binários e de texto não são separados: são simplesmente dados. Depende da interpretação que os torna um ou outro. Se você abrir dados binários (como um arquivo de imagem) em um editor de texto, grande parte deles não fará sentido, porque não se ajusta à interpretação escolhida (como texto).

Os arquivos são armazenados como zeros e uns (por exemplo, tensão/sem tensão na memória, magnetização/sem magnetização no disco rígido). Você não vê zeros e uns ao catexecutar os arquivos porque as sequências 0/1 não serão de muita utilidade para um ser humano; caracteres fazem mais sentido e um hexdump é melhor para a maioria dos propósitos (experimente hexdumpum arquivo).

Arquivos executáveistenho um cabeçalhoque descreve parâmetros como a arquitetura para a qual o programa foi construído e quais seções do arquivo são código e dados. É isso que fileutiliza para identificar as características do seu arquivo binário.

Finalmente: sim, você pode escrever programas em linguagem assembly usando opcodes da CPU diretamente. Dê uma olhadaIntrodução à programação assembly UNIXe aDocumentação Intel x86para um ponto de partida.

Responder2

Todos os arquivos são armazenados como 1 e 0, cat apenas tenta interpretar cada BYTE (8 bits) como um caractere, é por isso que você vê os caracteres ininteligíveis.

Responder3

Todos os arquivos são binários: eles são armazenados como uma sequência depedaços.

Os pedaços de arquivos são realmente agrupados embytes. Cada arquivo consiste em um número inteiro de bytes. Todos os sistemas Unix, e na verdade quase todos os computadores, possuem bytes compostos de 8 bits (conhecidos comooctetosna terminologia de rede). Existe uma maneira natural de interpretar bytes como números de 8 bits, ou seja, números entre 0 e 2 8 -1 = 255.

Para vê-los como binários, você precisa de uma ferramenta que os escreva em notação binária. Os humanos não são adequados para a notação binária: leva muito tempo para escrever qualquer coisa. É mais comum usarhexadecimalnotação, com 16 dígitos diferentes. Por exemplo, 41(sessenta e cinco em hexadecimal) é mais confortável de ler do que 01000001(sessenta e cinco em binário). Você pode usar um comando comood(“octal dump”) ou hexdumpou hdpara listar um arquivo com notação octal ou hexadecimal para cada byte ( od -t x1muda para hexadecimal).

Bytes podem representar caracteres. Existem várioscodificações de caracteresusado no mundo unix. Eles são todos baseados emASCII, que define a interpretação de bytes entre 0 e 127. Observe que isso define apenas um significado para metade dos valores de bytes possíveis. Por exemplo, 65 representa a letra maiúscula A, 97 representa a letra minúscula a, 30 representa o dígito 0e assim por diante. Algumas codificações de caracteres representam cada caractere por um byte; por exemplo, nolatim-1codificação, 163 representa £, 241 representa ñe assim por diante. O número máximo de caracteres que se pode representar desta forma é 256, o que não é muito; portanto, existem outras codificações que utilizam mais de um byte por caractere. A codificação padrão de fato no mundo unix hoje em dia éUTF-8, que é uma codificação de comprimento variável (caracteres diferentes ocupam diferentes números de bytes) para oConjunto de caracteres Unicode.

Um arquivo de texto é um arquivo binário que contém texto inteligível. Na verdade, para programas Unix, um arquivo é um arquivo de texto, desde que respeite duas condições:

  • Um arquivo de texto não pode conter nenhum byte nulo (um byte com valor numérico 0). Este byte não representa nenhum caractere e é usado internamente como marcador especial em muitos programas de manipulação de texto.
  • Um arquivo de texto consiste em uma sequência de linhas e cada linha é terminada por umnova linhacaractere (que tem o valor numérico 10).

Executáveis ​​de máquina são um tipo específico de arquivo binário. Se você executar o catcomando neles, verá lixo com trechos ocasionais de texto. Esses arquivos também podem conter comandos para o seu terminal. Você pode usar o programa stringspara ver todos os fragmentos de texto em um arquivo binário, deixando de fora os caracteres não imprimíveis.

Executáveis ​​de máquina não são exatamente uma sequência de instruções de máquina: eles também contêm algumas informações extras que informam ao sistema operacional como carregar o arquivo na memória, geralmente também alguns dados usados ​​pelo programa e, opcionalmente, informações de depuração. A maioria dos sistemas Unix usa oDUENDEformato para executáveis ​​de máquina. Este formato especifica como um arquivo contendo código de máquina é dividido em seções, e essa parte é independente da arquitetura da máquina; algumas seções contêm código, e o significado desse código é específico para uma arquitetura de máquina específica.

Você pode usar o comando objdump -D /path/to/machine-executablepara exibir uma listagem do executável em um formato legível:linguagem assembly. Bem, de qualquer maneira, legível por um humano treinado. A linguagem assembly é específica para uma arquitetura de processador e mapeia diretamente para instruções de máquina.

É possível escrever um programa completo em linguagem assembly, mas isso raramente é feito para programas não triviais, porque leva muito tempo. Se você for realmente louco, poderá escrever seu programa diretamente em binário. Algumas pessoas tentaram inventar oprograma mais curto possível que imprimeHello world; Ryan Henszey explica como escrever umExecutável ELF de 142 bytes para processadores de PC; Brian Raiteranalisou o formato ELF e criou um programa de 45 bytesque o Linux está disposto a executar (esse programa não imprime nada).

Existem também executáveis ​​que não são arquivos binários; eles são conhecidos comoroteiros. E, inversamente, existem muitos arquivos binários que não são executáveis: imagens, vídeos, arquivos compactados, documentos de processador de texto, bibliotecas de código semponto de entrada, executáveis ​​para outras arquiteturas de processador,…

informação relacionada