Eu li essa citação (abaixo) várias vezes, mais recentemente aqui , e estou constantemente intrigado com a forma como dd
pode ser usado para corrigir qualquer coisa e muito menos um compilador:
O sistema Unix que usei na escola, há 30 anos, era muito limitado em RAM e espaço em disco. Especialmente, o
/usr/tmp
sistema de arquivos era muito pequeno, o que causava problemas quando alguém tentava compilar um programa grande. Obviamente, os alunos não deveriam escrever "grandes programas" de qualquer maneira; programas grandes geralmente eram códigos-fonte copiados de "algum lugar". Muitos de nós copiados/usr/bin/cc
para/home/<myname>/cc
, e utilizadodd
para corrigir o binário para usar/tmp
em vez de/usr/tmp
, que era maior. Obviamente, isso apenas piorou o problema - o espaço em disco ocupado por essas cópias importava naqueles dias e agora era/tmp
preenchido regularmente, impedindo que outros usuários editassem seus arquivos. Depois que descobriram o que aconteceu, os administradores do sistema fizeram umachmod go-r /bin/* /usr/bin/*
que "corrigiu" o problema e excluiu todas as nossas cópias do compilador C.
(Ênfase minha)
A dd
página de manual não diz nada sobre correções e não acha que poderia ser re-proposto de qualquer maneira.
Os binários poderiam realmente ser corrigidos dd
? Existe algum significado histórico para isso?
od
um arquivo para os códigos hexadecimais bytes, encontrar o deslocamento que você precisa, decidir sobre a sua edição, ebs=$patchsize count=1 seek=$((offset/bs)) conv=notrunc
sua direita patch no no.Respostas:
Vamos tentar. Aqui está um programa C trivial:
Vamos incorporar isso em
test
:Se o rodarmos, ele imprimirá "/ usr / tmp".
Vamos descobrir onde "
/usr/tmp
" está no binário:-t d
imprime o deslocamento em decimal no arquivo de cada sequência encontrada.Agora vamos criar um arquivo temporário apenas com "
/tmp\0
":Portanto, agora temos o binário, sabemos onde está a cadeia que queremos alterar e temos um arquivo com a cadeia de substituição.
Agora podemos usar
dd
:Isso lê dados de
tmp
(nosso "/tmp\0
" arquivo), gravando-os em nosso binário, usando um tamanho de bloco de saída de 1 byte, pulando para o deslocamento que encontramos anteriormente antes de gravar qualquer coisa, e explicitamente não truncando o arquivo quando terminar.Podemos executar o executável corrigido:
A string literal impressa pelo programa foi alterada, portanto agora contém "
/tmp\0tmp\0
", mas as funções da string param assim que vêem o primeiro byte nulo. Esse patch permite apenas tornar a string mais curta ou com o mesmo comprimento, e não mais, mas é adequada para esses fins.Portanto, não apenas podemos consertar as coisas
dd
, como acabamos de fazê-lo.fonte
/usr/tmp
string, substitua-a por/tmp
, não esqueça o\0
byte à direita , salve o arquivo e cruze os dedos ". Ou, melhor ainda, um script de shell que verifica primeiro a sanidade e depois chamadd
. Infelizmente, a necessidade de coisas como essa surge com frequência quando um software antigo de um fornecedor agora extinto apenas precisa ser migrado para um novo sistema.sed
é melhor para esse tipo de coisa - você não pode limitar de forma explícita e precisa os buffers de leitura / gravação da maneira que você poderia com - o que é todo o motivo pelo qual ele foi usado para isso em primeiro lugar. Com você pode arbitrariamente colocar uma contagem arbitrária de bytes arbitrários. Isso também não pode ser dito . Se for usado como um bisturi aqui, você aplicaria como uma bola de demolição.sed
dd
dd
sed
dd
sed
Depende do que você quer dizer com "corrigir o binário".
Eu mudo binários usando
dd
às vezes. É claro que não existe esse recursodd
, mas ele pode abrir arquivos, ler e escrever coisas com desvios específicos; portanto, se você sabe o que escrever, onde está, seu patch está pronto.Por exemplo, eu tinha esse binário que continha alguns dados PNG. Use
binwalk
para encontrar o deslocamento,dd
para extraí-lo (geralmente o binwalk também extrai coisas, mas minha cópia estava com bugs), edite-o comgimp
, verifique se o arquivo editado é do mesmo tamanho ou menor que o original (alterar deslocamentos não é algo que você possa fazer facilmente) ) e usedd
para colocar a imagem alterada novamente no lugar.Às vezes, também desejo substituir cadeias de caracteres em binários (como nomes de caminho ou variável). Embora isso também possa ser feito
dd
, é mais simples fazê-losed
. Você só precisa garantir que a string substituída tenha o mesmo comprimento da string original para não alterar as compensações.ou para pegar o exemplo do @ MichaelHomer com um byte de 0 bytes adicionado em:
Claro que você precisa verificar se realmente funciona depois.
fonte
sed
que lida bem com arquivos binários, o que parece ser o caso do gnused
, mas não com muitos dossed
s mais antigos que funcionavam apenas em arquivos ascii, ficou confuso com qualquer outra coisa (especialmente\0
s na entrada), e tinha restrições no comprimento máximo da linha.sed
parece capaz de alterar bem os arquivos binários, mas não entende\x00
na cadeia de substituição a maneira como o GNUsed
. Requer testes, mas mesmo assim acho que vale a pena mencionar, pois é muito mais simples do quedd
- em alguns casos. Os binários de aplicação de patches são um negócio confuso, de qualquer maneira.