Решение крэкми вида имя-пароль. Крэкинг ч.16

Обсудить статью на форуме


Свежая 2020 года подборка видеоуроков, инструментов крэкера, книг и статей - здесь.


В этой части мы начнём разбор крэкми, которые отличаются от предыдущих тем, что серийный номер является переменным и высчитывается на основе имени, которое мы вводим.

Способ его решения очень похож, но рассмотрим несколько примеров, чтобы всё стало понятным.

Начнём с поиска правильного серийного номера в крэкми CrueHead’а.

Откроем его в OllyDbg.

Взлом программ отладчиком OllyDbg

Мы находимся на точке входа.

Смотрим, какие API-функции используются для получения введённого серийного номера.

Взлом программ отладчиком OllyDbg

Попробуем установить BP на указанной функции, чтобы остановиться на том месте, где будет считываться имя и серийный номер.

Взлом программ отладчиком OllyDbg

Делаем RUN.

Взлом программ отладчиком OllyDbg

После нажатия на OK оказываемся на api-функции и в стеке видим параметры.

Взлом программ отладчиком OllyDbg

Взлом программ отладчиком OllyDbg

Взлом программ отладчиком OllyDbg

Буфер, в котором сохраняется введённый текст, начинается с 40218E, посмотрим через DUMP, что там находится – правый клик мыши и FOLLOW IN DUMP на строке, где приводится информация о буфере.

Взлом программ отладчиком OllyDbg

Здесь ничего нет, потому что API-функция ещё не выполнилась, так что выполняем DEBUG-EXECUTE TILL RETURN, и когда оказываемся на RET, нажимаем F7, чтобы вернуться в программу.

Взлом программ отладчиком OllyDbg

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

Взлом программ отладчиком OllyDbg

Встречаем ту же API-функцию во второй раз. Здесь используется новый буфер, куда помещается введённый серийник. Посмотрим его через дамп.

Взлом программ отладчиком OllyDbg

То же самое, что и в прошлый раз; выполняем API-функцию с помощью EXECUTE TILL RETURN, а чтобы вернуться в программу, нажмём F7.

Теперь здесь наш неправильный серийный номер, начиная с этого места программа будет сравнивать его с правильным, который высчитывается на основании имени, поэтому можем установить BPM ON ACCESS на неверном серийнике, чтобы узнать, что с ним делает программа.

Взлом программ отладчиком OllyDbg

Отметим нужные байты, правый клик – BREAKPOINT – MEMORY ON ACCESS, и RUN.

Взлом программ отладчиком OllyDbg

Видим, что остановка произошла там, где программа считывает первый байт неправильного серийного номера и перемещает его в BL. Нажимаем F7.

Взлом программ отладчиком OllyDbg В BL находится 39 – значение первого байта. Нам нужно отловить, что программа делает с ним и, по возможности, записать, какие математические действия программа над ним совершает.

Взлом программ отладчиком OllyDbg

Здесь делается проверка на то, равен ли он нулю, если да – это конец строки и произойдёт выход из цикла.

Взлом программ отладчиком OllyDbg

Так как нулю первый байт не равен, то перехода не происходит и попадаем на SUB BL, 30.

Взлом программ отладчиком OllyDbg

После того, как было вычтено 30, в BL осталось 9.

На следующей строке EDI умножается на EAX.

Взлом программ отладчиком OllyDbgs

Эти регистры были инициализированы следующими значениями: в начале процедуры в EAX было помещено 0A, а EDI до входа в цикл приравнен к нулю с помощью инструкции XOR EDI, EDI.

Взлом программ отладчиком OllyDbg

Взлом программ отладчиком OllyDbg



По нажатию F7, как мы помним, исходя из определения инструкции IMUL с двумя операндами, в данном случае, они будут умножены с учётом знака, а результат сохранён в первый операнд, т.е. в EDI.

Взлом программ отладчиком OllyDbg

Таким образом, в EDI остаётся ноль, ставший результатом выполнения предыдущей операции.

Взлом программ отладчиком OllyDbg

Дальше идёт сложение EDI со значением в EBX.

Взлом программ отладчиком OllyDbg



В результате в EDI остаётся 9, а на следующей строке выполняется инструкция INC ESI, что увеличивает ESI, чтобы затем вернуться на начало цикла и прочитать следующий байт неправильного серийника.

Взлом программ отладчиком OllyDbg

После это в AL снова помещается значение 0A, прочитывается следующий байт неправильного серийного номера (это будет 38), проверяется, равно ли оно нулю, из него вычитается 30 и прибываем в IMUL.

Взлом программ отладчиком OllyDbg

Видим, что умножается EDI, в котором осталось значение ещё с прошлого пробега цикла, на 0A, а результат помещается в EDI же.

Взлом программ отладчиком OllyDbg

Теперь EDI содержит 5A, а на следующей строке он складывается с EBX.

Взлом программ отладчиком OllyDbg

То есть результат всех производящихся операций накапливается в EDI; тем, кто усерден и прилежен на ниве крэкинга, уже ясно, что происходит. Объясним.

Взлом программ отладчиком OllyDbg

Достаточно установить точку останова на выход из цикла: нажимаем F9 и, когда происходит остановка, видим, чему равен EDI.

Взлом программ отладчиком OllyDbg

Если кликнем два раза на EDI.

Взлом программ отладчиком OllyDbg Значение EDI – значение шестнадцатеричное, во втором поле видим его же в десятеричной системе счисления, и это значение соответствует серийному номеру, введённому мной, т.е. после выхода из цикла в EDI содержится серийник в шестнадцатеричном виде.

Т.е. резюмируя кратко: если напечатаем слово 98989898, оно будет трансформировано в десятеричное число 98989898 или шестнадцатеричное 5E6774A.

Взлом программ отладчиком OllyDbg

На следующей строке EDI xor’ится с 1234.

Взлом программ отладчиком OllyDbg

В результате получается 5E6657E, которое перемещается в EBX, а затем мы прибываем в RET.

Взлом программ отладчиком OllyDbg

Видим, что выйдя через RET, мы оказались у сравнения EAX с EBX, то есть туда, где находится переход, решающий, правилен или нет серийный номер.

Взлом программ отладчиком OllyDbg

Взлом программ отладчиком OllyDbg



И видим, что сравнивается вычисленное значение, находящееся в EBX с EAX, который содержит 547B.

Так как EAX определяется программой, а EBX – высчитывается, то очевидно, что поскольку мой серийный номер неверен, то и значения этих регистров не будет равно.

Если EBX был бы равен EAX, то программа сделала бы нужный переход, поэтому нам нужно проанализировать, отчего произошло неравенство регистров.

Смотрим сделанные нами заметки.

EBX= (Шестнадцатиричное значение неверного серийного номера) XOR 1234

Мне нужно, чтобы EBX был равен EAX, тогда проверка на равенство выдаст нужный результат.

Если EAX=EBX

Reemplazo EBX por EAX ya que son iguales

Заменим EBX на EAX, то есть чтобы они были равны.

EAX=(Шестнадцатиричное значение правильного серийного номера) XOR 1234

При выполнении этого условия введенный серийный номер будет верным.

Переформулируем.

EAX XOR 1234= (Шестнадцатиричное значение правильного серийного номера)

И поскольку в EAX есть значение (547B), то можем заменить на него EAX.

547B XOR 1234 = (Шестнадцатеричное значение правильного серийника)

Если посчитаем результат операции XOR:

464F = (Шестнадцатеричное значение правильного серийника)

Если 464F – это шестнадцатеричное значение, то соответствующее десятеричное, которое нужно ввести, будет:

Взлом программ отладчиком OllyDbg

Переводим в десятеричную систему.

Взлом программ отладчиком OllyDbg

Это и есть правильный серийный номер для имени “narvaja”. Убираем все BPM и BP.

Взлом программ отладчиком OllyDbg

Нажимаем OK.

Взлом программ отладчиком OllyDbg

Так мы получили серийник для моего имени.

Это один способ решения. Можно прибегнуть и к другому ходу мысли, чтобы придти к тому же результату.

Если над моим неправильным серийным номером выполняются некие операции, трансформирующие его, то эти операции назовём функцией F.

F (неправильный серийный номер) =EBX

То есть над неправильным серийником производятся операции, называемые функцией F, результат чего сохраняется в EBX, с которым и происходит сравнение.

Другим членом сравнения является EAX, что приводит нас к следующему равенству:

F (правильный серийный номер)=EAX

Применение вышеуказанных операций над правильным серийным номером в данном случае даст то же значение, что и в EAX, поэтому если у нас есть EAX, то мы также имеем на руках данные для сравнения и производимые операции.

Чтобы получить правильный серийный номер, нужно применить над EAX операции, обратные используемым при проверке введённого серийника.

Правильный серийный номер = (операции, обратные F)EAX

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

В данном случае операцией, обратной XOR, является тот же самый XOR, так как эта операция инвертируемая.

Поэтому XOR EAX будет функцией обратной F и даст мне шестнадцатеричное значение правильного серийного номера, из которого, если переведём его в десятеричную систему, получится собственно серийник.

Таким образом, можем применять любой из этих способов, чтобы получить правильный серийный номер, за исключением тех случаев, когда у операции нет обратного эквивалента. Мы рассмотрим и такие варианты.

Теперь снова вернёмся к SPLISH. Мы решили ту часть, которая касалась жёстко заданного серийника, а теперь решим вторую с вводом имени пользователя.

Загрузим SPLISH в OllyDbg и окажемся на точке входа.

Взлом программ отладчиком OllyDbg

Смотрим используемые API-функции.

Взлом программ отладчиком OllyDbg

Ставим BPX на уже знакомую нам GetWindowTextA.

Взлом программ отладчиком OllyDbg

И запускаем программу с помощью F9.

Взлом программ отладчиком OllyDbg

Вводим имя и неверный серийник, после чего нажимаем кнопку NAME/SERIAL CHECK.

Взлом программ отладчиком OllyDbg

Остановившись на вызове API-функции, смотрим буфер.

Взлом программ отладчиком OllyDbg

Ищем буфер в DUMP’е.

Взлом программ отладчиком OllyDbg

Взлом программ отладчиком OllyDbg



Так как здесь ничего нет, выполним EXECUTE TILL RETURN, чтобы остановиться на RET, а заме нажмём F7 для возврата в программу.

Взлом программ отладчиком OllyDbg

Видим, что сначала получили неправильный серийный номер, поэтому отмечаем его и устанавливаем BPM ON ACCESS.

Взлом программ отладчиком OllyDbg

Делаем RUN.

Взлом программ отладчиком OllyDbg

Снова останавливаемся на вызове той же функции, которая в этот раз получает из формы имя, но поскольку нам это сейчас не интересно, снова нажимаем RUN.

Взлом программ отладчиком OllyDbg

Останавливаемся на этой процедуре.

Первая строка перемещает первый байт неправильного серийник. Если выполним её:

Взлом программ отладчиком OllyDbg

Дальше следует инструкция CDQ. Посмотрим, что о ней говорит наш друг Google.

CDQ
IDIV ESI

Инструкция IDIV ESI делит содержимое EDX:EAX на ESI, сохраняя результат деления в EAX, а остаток в EDX. Чтобы быть это деление было эффективным, содержимое EDX должно быть равно нулю, что можно сделать с помощью CDQ или XOR EDX, EDX. В этом случае не нужно помещать ноль в регистр EDX, потому что результат предыдущей инструкции уже делает это.

В этом случае EDX подготавливается перед делением для получения остатка, а поскольку у нас здесь цикл, то каждый раз для этой цели перед выполнением команды IDIV используется CDQ.

EDX:EAX делится на ECX, результат помещается в EAX, а остаток в EDX. Ок, это посмотрим, как это работает. Первый байт равен 39, он делится на ECX, который содержит 0A.

Взлом программ отладчиком OllyDbg Видим, что получилось.

Взлом программ отладчиком OllyDbg

Здесь результат деления (5) оказывается в EAX, а остаток (7) – в EDX.

Взлом программ отладчиком OllyDbg

Видим, что следующая строка сохраняет результат деления в 40324D. Посмотрим через DUMP, что там.

Взлом программ отладчиком OllyDbg

Взлом программ отладчиком OllyDbg

Продолжаем выполнение с помощью F7.

Взлом программ отладчиком OllyDbg

Здесь сохраняется 7.

Взлом программ отладчиком OllyDbg

Взлом программ отладчиком OllyDbg



Видим, что EBX, равный нулю, увеличивается на 1 и сравнивается с 6, и так как эти значения не равны, то цикл повторяется.

Взлом программ отладчиком OllyDbg

Взлом программ отладчиком OllyDbg

Теперь посмотрим, что происходит со вторым байтом.

Взлом программ отладчиком OllyDbg

Снова происходит деление на 0A и сохранение остатка.

Взлом программ отладчиком OllyDbg

Взлом программ отладчиком OllyDbg



Сохраняем…

Взлом программ отладчиком OllyDbg

Ок, одна и та же операция производится над всеми байтами.

Взлом программ отладчиком OllyDbg

И выходим из цикла, так как не происходит перехода с помощью JNZ, возвращавшего нас раньше.

Взлом программ отладчиком OllyDbg

Попадаем сюда и видим сообщения о правильном и неправильном вводе серийного номера, так что похоже, что находимся рядом с тем, что нам нужно.

Взлом программ отладчиком OllyDbg

Здесь два LEA, которые помещают адреса в ESI и EDI.

Взлом программ отладчиком OllyDbg

ESI указывает туда, где сохраняются остатки, а EDI, возможно, на что-то интересное?

Взлом программ отладчиком OllyDbg

Продолжаем.

Взлом программ отладчиком OllyDbg Видим, что EBX содержит ноль, который сравнивается с 7, и если бы они были равны…

Взлом программ отладчиком OllyDbg

Перешли бы на окошко с сообщением о правильном вводе. В середине находится другой JNZ, который перемещает на другое окошко с сообщением о вводе неправильном.

Взлом программ отладчиком OllyDbg

Ок, видим, что сравнивается.

Взлом программ отладчиком OllyDbg

В EAX переместится первый байт, на который указывает EDI, то есть 02, а в ECX будет перемещён первый байт наших остатков, то есть 7.

Взлом программ отладчиком OllyDbg

Взлом программ отладчиком OllyDbg

И если остаток первого байта был бы равен 02, то был бы совершён переход.

В моём случае найти остаток можно было бы следующим образом.

39= 5 .0A + 7

То есть результатом деления 39 на 0A является 5 с остатком 7. Переформулируя, можно сказать, что умножив 0A на 5, получим 32 и прибавление 7 даст 39.

39= 5 x 0A + 7

Правильный остаток должен быть равен двум в случае правильного серийного номера.

BYTE CORRECTO= 5 x 0A + 2

BYTE CORRECTO= 32 +2 = 34

34 это цифра ‘4’ в ASCII.

Мы можем также увидеть, что

BYTE CORRECTO= 5 x 0A + 2

Даёт нам одно из цифровых значений (от 30 до 39). В случае, если результат выходит за эту границу, то нужно сделать понижение и считать так:

BYTE CORRECTO= 4 x 0A + RESTO

Ок, посчитали, что первый байт равен 34 или ‘4’ в ASCII.

Высчитаем другие правильные байты с помощью наших остатков.

Взлом программ отладчиком OllyDbg

C 02 уже посчитали.

Продолжаем с 08.

ПРАВИЛЬНЫЙ БАЙТ = 5 x 0A + 8

ПРАВИЛЬНЫЙ БАЙТ = 32 + 8

Получилось 40, что перевышаем максимальное установленное нами значение 39 (‘9’ в ASCII), поэтому понижаем и пересчитываем заново:

ПРАВИЛЬНЫЙ БАЙТ = 4 x 0A + 8

ПРАВИЛЬНЫЙ БАЙТ = 28 + 8 = 30 que es 0 en ASCII

Если хотите доказательство, то смотрим, что 30, делённое на 0A, даёт 4 с остатком 8.

Взлом программ отладчиком OllyDbg

Поэтому у нас есть второй правильный байт, равный 30, то есть ‘0’ в ASCII.

Посчитаем всё остальное байт за байтом.

Следующий опять 08, то есть результатом будет 30 или ‘0’ в ASCII.

Потом 03.

ПРАВИЛЬНЫЙ БАЙТ = 5 x 0A + 3

ПРАВИЛЬНЫЙ БАЙТ = 32+ 3= 35, то есть ‘5’ в ASCII.

Затем 05.

ПРАВИЛЬНЫЙ БАЙТ = 5 x 0A + 5

ПРАВИЛЬНЫЙ БАЙТ = 32+ 5= 37, то есть ‘7‘ в ASCII

Потом снова идёт 5, то есть повторяется 37 или ‘7’ в ASCII.

Последним идёт 3, который, как мы уже знаем, даёт 35 или ‘5’ в ASCII.

Таким образом, правильным серийным номером для имени ‘narvaja’ будет 4005775. Убираем все BPM и BPX и запускаем RUN.

Взлом программ отладчиком OllyDbg

Нажимаем кнопку NAME/SERIAL CHECK.

Взлом программ отладчиком OllyDbg

Ещё одна победа.

К этой главе прилагаетcz крэкми для практики под названием MEXCRK1.ZIP.

  [C] Рикардо Нарваха, пер. Aquila

Обсуждение статьи: Решение крэкми вида имя-пароль. Крэкинг ч.16 >>>


При перепечатке ссылка на https://exelab.ru обязательна.



Видеокурс ВЗЛОМ