34

Кто-нибудь знает способ подбора значений силы при определенном смещении в файле? Это 4 последовательных байта, которые должны быть грубо форсированы. Я знаю правильный SHA-1 поврежденного файла. Итак, я хотел бы сравнить полный файл SHA-1, каждый раз, когда он меняет значение байта.

Я знаю точные 4 байта, которые были изменены, потому что файл был предоставлен мне экспертом по восстановлению данных, как задача восстановления. Для тех, кто интересуется знанием, файл rar имеет 4 байта, которые были намеренно изменены. Мне сказали смещения измененных 4 байтов и оригинального SHA-1. Человек сказал, что НЕВОЗМОЖНО восстановить точный файл в архиве после того, как 4 байта были изменены. Даже если бы было всего несколько байтов, и вы точно знали, где была обнаружена коррупция. Так как у него нет записи восстановления. Я пытаюсь увидеть, есть ли способ, чтобы эти 4 байта были правильно заполнены, чтобы файл распаковывался без ошибок. Размер файла составляет около 5 МБ.

Пример:

Я загрузил фотографии, чтобы они более четко определяли, что именно я хочу сделать. Я считаю, что кто-то может опубликовать их здесь для меня с большим количеством представителей.

Скриншот первый

Скриншот два

Пример смещения, на котором я акцентирую внимание: 0x78 где на первом рисунке показано значение CA Я хочу, чтобы скрипт принял значение на 1, чтобы оно стало CB как показано на втором рисунке. Я хочу, чтобы он продолжал увеличивать значение на 1 а затем сравнивать весь файл SHA-1 каждый раз. Вносить изменения только в эти 4 байта с указанным смещением.

Он попробует CAC5C58A и сравнит SHA-1. Если не совпадает, то он будет пытаться CBC5C58A Затем, как только первое значение достигнет FF он перейдет к 00C6C58A и так далее. По сути, я бы хотел, чтобы он мог переходить от 00000000-FFFFFFFF но также имел возможность выбрать, где вы хотите, чтобы он начинался и заканчивался. Я знаю, что это может занять некоторое время, но я все еще хотел бы попробовать это. Имейте в виду, я знаю точное смещение байтов, которые повреждены. Мне просто нужны правильные значения.

Если вы ищете в Google: "Как исправить поврежденный файл с помощью грубой силы", то есть человек, который написал программу для Linux. Тем не менее, он работает только против файлов, включенных в программу. Я ищу способ использовать тот же процесс с моим файлом.

2 ответа2

27

Вот небольшая программа на Python, которая делает то, что вы, кажется, описываете.

#!/usr/bin/env python3
from hashlib import sha1

with open('binaryfile', 'rb') as bin:
    binary = bin.read()

base = 0x0078
# ... is not valid Python; add more sequences, or take it out (or see below)
for seq in [[0xCA, 0xC5, 0xC5, 0x8A], [0xCB, 0xC5, 0xC5, 0x8A], ...]:
    copy = binary[0:base]
    copy += bytes(seq)
    copy += binary[base+len(seq):]
    if sha1(copy).hexdigest() == '9968733ce3ff0893bbb0a19e75faaf2fb0000e19':
        print('success with bytes {0}'.format(seq))
        break
else:
    print('no success')

ООН Только кратко проверено; пожалуйста, пингуйте меня, если найдете опечатки.

base указывает, где пытаться применить четыре байта, а длинная строка '996873 ... является шестнадцатеричным представлением ожидаемого SHA1. Строка for seq in ... определяет байты, которые нужно попробовать; и, конечно, замените 'binaryfile' на путь к файлу, который вы хотите попытаться спасти.

Вы можете заменить буквальный список [[0xCA, 0xC5, ... ]] чем-то, что фактически зацикливает все возможные значения, но это в основном просто заполнитель для чего-то более полезного, потому что я не совсем уверен, чего именно вы там хотите.

Нечто подобное for seq in itertools.product(range(256), repeat=4)): перебирает все возможные значения от 0 до 2 32 -1. (Вам нужно будет добавить import itertools вверху.) Или, возможно, вы могли бы просто добавить смещение; обновите скрипт, чтобы заменить текущий for seq in на следующий (где снова import должен идти перед основной программой);

import struct

for n in range(2**32):
    val=(n+0x8AC5C5CA) % 2**32  # notice reverse order
    seq=list(reversed(struct.pack(">I", val)))
    copy = ...

Я перевернул порядок байтов, так что он, естественно, увеличивается с 0x8AC5C5CA до 0x8AC5C5CB, но затем следующим шагом будет 0x8AC5C5CC и т.д. Волшебство struct состоит в том, чтобы преобразовать это в последовательность байтов (должен был искать это из https://stackoverflow.com/a/26920983/874188). Это начнется с 0x8AC5C5CA и перейдет к 0xFFFFFFFF, затем развернется к 0x00000000 и поднимется до 0x8AC5C5C9.

Если у вас есть несколько диапазонов кандидатов, которые вы хотели бы изучить в определенном порядке, может быть что-то вроде

for rge in [(0x8AC5C5CA, 0x8AFFFFFF), (0x00C6C58A, 0x00FFFFFF),
        (0x00000000, 0x00C6C589), (0x01000000, 0x8AC5C5C9)]:
    for val in range(*rge):
        seq=list(reversed(struct.pack(">I", val)))
        copy = ...

но тогда вам нужно убедиться, что пары (начало, конец) в rge покрывают все пространство между 0x00000000 и 0xFFFFFFFF, если вы действительно хотите проверить все это. (И снова обратите внимание, что диапазон увеличивает последний байт и что seq применяет байты значения в обратном порядке, в соответствии с вашими заявленными требованиями.)

Если вы хотите использовать два разных base адреса, вы быстро столкнетесь с границами того, что можно сделать в своей жизни с помощью грубой силы; но вы могли бы, например, разделить 4-байтовое число на две 2-байтовые части и применить их с разными смещениями.

base1 = 0x1234
base2 = 0x2345

for seq in range(whatever):
    copy = binary[0:base1]
    copy += bytes(seq[0:1])
    copy += binary[base1+2:base1+base2]
    copy += bytes(seq[2:3])
    copy += binary[base2+2:]
4

Нет, нет, нет и снова НЕТ!

Редкий ответ, который вы получаете, не тот, который вы ожидаете.

Несколько вопросов для вас:

  • Возможно ли, что эксперт не знает, что можно грубо форсировать строку байтов и повторять попытку SHA-1, пока она не сойдет? нет
  • Возможно ли, что он забыл это? нет
  • Возможно ли, что вы не можете сделать это на RAR-файле? нет
  • Другой ответ неверен? абсолютно НЕТ

И что? ... Время.

Дело в том, что вы должны изменить так мало байтов ... только 4!

Что это значит? 256 4, то есть 256x256x256x256 возможностей, действительно очень большое число.
Если бы ваш компьютер мог обрабатывать 1 операцию в секунду (подстановка в файле + sha1)...
вам следует подождать более 136 лет или, если вы предпочитаете более 49710 дней.

Вам повезло, предварительно кэшированный файл размером 5 МБ (уже загруженный в оперативную память и в кэш) запрашивает всего около 0,03 секунды (мин. 0,025 с) на старом компьютере. Это сокращает ваше ожидаемое время до 1242-1492 дней (что превышает 3 года).

Это правда, кстати, что по статистике у вас должен быть положительный ответ в половине случаев. Тем не менее, вам следует подождать, пока вы не попробуете все возможности, чтобы быть уверенным, что есть только одна замена, которая даст вам такую же контрольную сумму SHA-1 ...

Теперь это НЕВОЗМОЖНО звучит как «невозможно в ДОСТОЙНОЕ количество времени».


Как действовать

Более правильный ответ на ваш технический вопрос: когда вы говорите о грубой силе, необязательно использовать слепую грубую силу.

  • В другом ответе просто указано, что вам не нужно вычислять контрольную сумму sha1 для детали до повреждения. Вы делаете 1-й раз и экономите время для каждой последующей итерации (может быть, фактор 2 зависит от позиции).

  • Что-то, что может изменить бесполезные усилия - это написать параллельный код, который будет работать на GPU. Если у вас хорошая графическая карта, у вас может быть около 1000 ядер, которые могут вычислять для вас параллельно (даже больше, но их частота ниже, чем у процессора, но все же их много). Если вы можете сократить время с 1400 до 1,4 дня, может быть, вы даже можете сделать это.

  • Другой подход может привести вас к более быстрому решению.
    Вы сказали, что это RAR файл. Структура файла rar разделена на блоки. Если вы примете это во внимание, вы увидите, куда падает коррупция. Если это на части данных, на части заголовков или на обоих. Тогда вы можете действовать соответственно. Для простоты предположим, что это по данным:
    Вы можете сделать грубую силу своего смещения, проверить для каждого положительного CRC этого блока, если это даже положительный SHA1 для всего файла. Снова вы можете сделать параллельный код.

Конечная нота

Если бы они были 6 байтов вместо 4, вы вышли из игры с существующей технологией.

Всё ещё ищете ответ? Посмотрите другие вопросы с метками .