Оригинальный DVD-ROM: eXeL@B DVD !
eXeL@B ВИДЕОКУРС !

ВИДЕОКУРС ВЗЛОМ
выпущен 12 ноября!


УЗНАТЬ БОЛЬШЕ >>
Домой | Статьи | RAR-cтатьи | FAQ | Форум | Скачать | Видеокурс
Новичку | Ссылки | Программирование | Интервью | Архив | Связь

От патча до кейгена : Sanchs Marine Aquarium v0.99L Beta.

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

Хорошая подборка видеоуроков, инструментов крэкера, книг и статей - здесь.
Автор: Fess Дата: 25.05.2002 Тьютор: 9
-+-+-+-+-+-+-+-+-+-+ For education uses only +-+-+-+-+-+-+-+-+-+-
 Target: Sanchs Marine Aquarium v0.99L Beta
 
 Tools:    Some brains
           Soft-Ice 3.24
           Win32Dasm 8.93
           Любой hex+asm-редактор (я использую QView)
 
 
Пролог
Вступление: Как-то около месяцев трех-четырех назад увидал я на softodrom'e хороший хранитель экрана в стиле "Эмуляция аквариума" и решил его себе закачать. Сказано сделано, скачал, поставил. Но по каким-то причинам он оказался шароварным. Дурацкий наг и возможность пользоваться одной рыбкой меня вдохновила на взлом. Наскоком взять не получилось, а со временем то- гда была напряженка сбацал патч и забыл. Но все возвращается, вот так и я от нечего делать решил вернуться и продолжить работу, как в следствии ок- азалось защита была плохой. Для начинающих крэкеров это в самый раз, и я предлагаю вашему вниманию 4 способа взлома этой программы. Что за прога: Один из самых лучших из видимых мной хранителей экрана, такой красоты и маленького размера (архив 1,1 Мб). Примечание: Если вы уже почетный крэкер и написание кейгена для любой проги для Вас плевое дело, то не читайте эту статью, так как в основном она предна- значена для начинающих желающих постичь все основы исскуства крэка. Я не считаю себя мастером крэкером, так что все огрехи в моей статье по незна- нию и не умению, но я стараюсь, чтобы их не было. Если вы нашли какие-ли- бо ошибки, не сочтите за труд и сообщите мне.
Вступление
Как я уже писал в прологе взлом будет производится четырьмя разными способами, это 1) Патч 2) Подсмотр кода 3) Написание кейгена на основе самой программы 4) Написание кейгена на Delphi
1) Патч
Патч это самый легкий способ взлома поэтому профессионалы и мастера в крэке считают его чем-то низким, я тоже стараюсь избегать использовать патч, но раз статья предназначена для начинающих, то не рассмотреть его это преступление. Но у легкости и быстроты патча есть и свои недостатки, по сравнению с серийным номером. Во-первых, это то, что он врядли будет работать с последующими версиями программы, во-вторых, сложно переносить патч, о... вот тут мне подсказывают, что для этого используют crk-файлы, согласен, но если программа запакована exe-паковщиком, то к этому файлу придется добавлять и распаковщик, а они подчас занимают достаточно много места. Ну что ж приступим. Программа ничем не запакована и написана на Visual C++. Поэтому сме- щение в файле равно смещению в памяти минус 400000h. Первое, что нужно сделать это установить программу. Логично скажите Вы и будете правы. Установили? Теперь идем в Настройки Экрана, выбираем наш Screen Saver. И жмем кнопку Настройка. Там видим большое поле, где надо вводить наш код. Введем любой код и нажмем кнопку Enter. Код пропал, а ничего не произошло. Хм, странно. Почитаем текст вокруг. Написано, что можно написать TESTFISH, пишем, вводим и видим надпись: TEMP REGISTRATION OK. Работает. Скорее всего здесь и высветиться информация о правиль- ном номере. Что еще можно прочитать... Так написано, что нужно заплатить им 19,95 американских портретов за Deluxe регистрацию. Ладно, наплевать лучше сразу дизассемблировать, а там посмотрим. Копируем файл fish.scr из каталога Windows в свой каталог, у меня это MUSOR. Дизассемблируем. И ле- зем в директорию найденных в программе строк: StrRef и ищем там, какие- нибудь интересные строки, таковыми оказались: "BASIC registration OK" "DELUXE registration OK" "TEMP registration OK" Последнюю мы уже видели, а две другие нет. Судя по названиям Deluxe это продвинутая регистрация, а Basic основная. На Basic наплюем, хотя мы еще с ней встретимся в 2 и 3 пункте, а сделаем себя люксами. Два раза тыкаем на строку с Deluxe и оказываемя здесь Прим: все основные строки я выделю таким цветом. :00411263 8B4D10 mov ecx, dword ptr [ebp+10] :00411266 81E1FFFF0000 and ecx, 0000FFFF :0041126C 81F95A020000 cmp ecx, 0000025A :00411272 0F85E1010000 jne 00411459 :00411278 833D7493420003 cmp dword ptr [00429374], 00000003 :0041127F 751B jne 0041129C * Possible StringData Ref from Data Obj ->"DELUXE registration OK" | :00411281 687C564200 push 0042567C :00411286 6892000000 push 00000092 :0041128B 8B5508 mov edx, dword ptr [ebp+08] :0041128E 52 push edx * Reference To: USER32.SetDlgItemTextA, Ord:022Ch | :0041128F FF154C024200 Call dword ptr [0042024C] Так в выделенной строке число по адресу 429374 сравнимается с 3 и если не равно, то идет куда-то дальше, а если равно, то выдает эту строку. Зна- чит надо, чтобы в этой ячейке памяти всегда было 3. Вы можете не согла- ситься со мной, сказав: "Может просто заменить переход после этого сравне- ния и все." Это самая главная ошибка начинающих борьба не с причиной, а со следствием, такой способ может сработать, но редко. Хотя никто Вас не дер- жит попробуйте, может и получится. Попробуем поискать фрагмент, где в эту ячейку записываются данные, это можно сделать с помощью Soft-Ice. Но зачем крэкеру геморой. Просто поищем строку mov dword ptr [00429374], 00000003. Глядишь, что и всплывет. Найде- но три адреса, вот текст около первого :00404026 6A03 push 00000003 :00404028 E8C3F0FFFF call 004030F0 :0040402D 83C404 add esp, 00000004 :00404030 85C0 test eax, eax :00404032 7434 je 00404068 :00404034 C7057493420003000000 mov dword ptr [00429374], 00000003 Каждые три раза вызывается эта процедура и если в eax она возвратит не 0, то все хорошо и идет присвоение, если 0, то плохо. Можно, конечно, поменять все jump'ы после этих процедур. И это скорее всего поможет, но я предпочи- таю действовать более тонко, сделать, чтобы процедура всегда возвращала не 0. Можно, конечно, прямо после входа в процедуру поставить ret, ведь скорее всего eax<>0. Процентов 91,2%. Но лучше присвоить eax единицу и выйти. Да- вайте так и сделаем. Открываем файл qview или hiew. Включаем 32 битный-hex&asm режим. Как это делается я в предыдущих тьюториалах писал. Переходим по адресу 30F0. И вписываем такие строки (после ";" приведена расшифровка строк) xor eax,eax ;обнулить eax inc eax ;увеличить eax на 1 ret ;выйти из процедуры Или прямо в hex-режиме начиная с адреса 30F0 пишем 33С040С3 это и будут эти команды. Теперь можете зайти в настройки и увидеть их совсем другими, а сверху долгожданную надпись Deluxe Version. И пользуйтесь ей до скончанья веков. Жалко, что это только бета, а в нормальной этот патч будет не дейтвителен. Хотя я думаю сломать ее будет так же легко, да и адреса врядли сильно по- меняются. Но уж лучше код, читайте дальше....
2) Подсмотр кода
Подсмотреть, подслушать это давнее изобретение человека из века в век на этом делали деньги. И мы сегодня заработаем ни много, ни мало 19.95$. Только, к сожалению, Вам их никто не отдаст, но зато программа за эту це- ну станет Вашей. Поехали. Самая главная задача это найти, где введенный нами код сравнивается с настоящим, сгенереным по каким-то законам с какими-то условиями. В этой главе нам на них превать. Тут вы можете меня осудить, мол сволочь, "тут, наверное, будет вычисляться контрольная сумма, ведь имя-то не вводим.". Я себе позволю сразу Вам заметить это тот редкий случай, когда это не так. Не забудьте включить SOFT-ICE, он нам понадобится подсмотреть код. Помните мы писали TESTFISH и получали ответ. Да. Тогда давайте посмо- трим откудова вызывается эта строка. Ведь она сравнивается с нашим вве- денным нами кодом. Жмем два раза на TESTFISH и оказываемся здесь. Я чтобы было по понятней понаставлю своих комментариев. :00411315 6A20 push 00000020 <- считать 20h символов :00411317 68A48E4200 push 00428EA4 <- сюда :0041131C 6892000000 push 00000092 <- из нашего поля(т.е. пароль) :00411321 8B5508 mov edx, dword ptr [ebp+08] :00411324 52 push edx <- идентификатор окна * Reference To: USER32.GetDlgItemTextA, Ord:0104h | :00411325 FF15E0014200 Call dword ptr [004201E0] * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:00411313(C) | * Possible StringData Ref from Data Obj ->"TESTFISH" | :0041132B 6870564200 push 00425670 <- Адрес строки TESTFISH :00411330 68A48E4200 push 00428EA4 <- Адрес нашего пароля * Reference To: KERNEL32.lstrcmpiA, Ord:02FFh <- сравниваем строки | :00411335 FF15A0004200 Call dword ptr [004200A0] :0041133B 85C0 test eax, eax :0041133D 750A jne 00411349 <- если не равны то переход :0041133F C7057493420001000000 mov dword ptr [00429374], 00000001 * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:0041133D(C) | :00411349 6A02 push 00000002 :0041134B E8A01DFFFF call 004030F0 <-сравнение на Basic регистрацию :00411350 83C404 add esp, 00000004 :00411353 85C0 test eax, eax :00411355 7414 je 0041136B <- если не равно, то переход :00411357 C7057493420002000000 mov dword ptr [00429374], 00000002 :00411361 6A01 push 00000001 :00411363 E8D825FFFF call 00403940 :00411368 83C404 add esp, 00000004 * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:00411355(C) | :0041136B 6A03 push 00000003 :0041136D E87E1DFFFF call 004030F0 <- сравнение на Deluxe :00411372 83C404 add esp, 00000004 :00411375 8945F8 mov dword ptr [ebp-08], eax :00411378 837DF800 cmp dword ptr [ebp-08], 00000000 :0041137C 7414 je 00411392 <- если не равно, то переход :0041137E C7057493420003000000 mov dword ptr [00429374], 00000003 Будем надеятся с коментариями все понятно. Как я угадал, где Basic, где Deluxe. Посмотрите на выделенные строки. Если не переходит адресу 429374 записывается значение. А о нем мы говорили, когда делали патч. Так же мы увидели, что наша введеная строка заносится в память по адресу 00428EA4. Кстати, Вы заметили, что процедура у Basic регистрации и Deluxe одна, и различаются только по значению кладущимуся в стэк 2 или 3. Заходим в эту процедуру и ищем, где наш введенный код сравнивается с истинным. "Истина, где-то рядом","как говорил один мой друг, ныне покой- ник". Сразу скажу программа написана на C++ и использует MFC, если, ко- нечно, это вам что-нибудь говорит. Ищем пока не доходим до такого места. :0040327A 8D4DC8 lea ecx, dword ptr [ebp-38] :0040327D 51 push ecx :0040327E 68A48E4200 push 00428EA4 * Reference To: KERNEL32.lstrcmpiA, Ord:02FFh | :00403283 FF15A0004200 Call dword ptr [004200A0] :00403289 85C0 test eax, eax :0040328B 0F851A010000 jne 004033AB Видно, что наш код сравнивается с чем-то. Теперь пора взятся за Soft- Ice. Заходим ставим бряк на GetDlgItemTextA строкой bpx GetDlgItemTextA. Из предыдущего фрагмента кода было видно, что именно эта функция исполь- зуется для чтения. Лезем в настройки и вводим такой код: 110022334455. Нажимаем Enter и вываливаемся в Soft-Ice нажимаем F11, чтобы вернуться в тело программы. Удаляем все бряки командой bc * и устанавливаем бряк на адрес 40327E команда bpx 40327E. Нажимаем F5. Но ничего не происходит программа до этого места не дошла. Тогда попробуем символьный код, такой FESSCOOL. Опять вводим и на сей раз вываливаемся, в Soft-Ice на нашем бряке. Даем команду d ecx, чтобы посмотреть, что будет по адресу ecx и видим следующее FESSCO760776. Жмем F5 и опять вываливаемся, опять d ecx и видим FESSCO966395. Рассуждаем логически, первое, программа использует первые 6 символов, введенного кода для генерации остальной части. Второе, эти первые 6 символов обязательно буквы, третье, первый код это скорее всего для Basic регистрации, а второй для Deluxe, поскольку процедура генерации одна. Попробуем ввести - подходит. Это круто теперь Вы можете получить код для своего имени или его части. И это круто. Можете теперь рассказать всем как вы купили эту программу и получили код, заплатив 20$. Но хорошего понемножку, и подсмотреть код просто, но что делать, ес- ли, кто-то не знает Soft-Ice можно дать ему свой код, но лучше другой. Каждый раз включать для этого Soft-Ice, ставить бряки и прочее. Неудобно лучше сделать кейген для начала на самой программе. Читайте дальше.
3) Написание кейгена на основе
самой программы
Если в программе можно подсмотреть правильный номер, то написание кей- гена на основе самой программы элементарно просто. Уже в нескольких ма- нуалах я писал, как это сделать. Мы уже нашли место, где правильный номер сравнивается с нашим. Оста- лось только вывести правильный номер на экран, для этого я обычно ис- пользую функцию MessageBoxA. Ищем любой код с этой функцией. Идем в секцию функций и два раза жмем на USER32.MessageBoxA. И попадаем в такое место. :00403A46 685C534200 push 0042535C :00403A4B 6A00 push 00000000 * Reference To: USER32.MessageBoxA, Ord:01BEh | :00403A4D FF1530024200 Call dword ptr [00420230] :00403A53 33C0 xor eax, eax Посмотрите hex представление этой функции и перепишите на бумажку, оно нам понадобиться. Формат функции MessageBoxA такой
push тип текста (обычно 0) push текст в заголовке push текст в окне push идентификатор окна (обычно 0) call MessageBoxA
Еще раз внимательно посмотрите на предыдущий фрагмент кода, нам надо начиная с 40327D. Написать такие строки, через дефис я буду приводить их hex представление. Запомните адрес MessageBoxA уникален для каждой прог- раммы, поэтому я беру его hex представление из самой программы.
push 0 - 6A00 push ecx - 51 push ecx - 51 push 0 - 6A00 CallMessageBoxA - FF1530024200 jmp 4033AB - E91D014000
Джамп после этого всего необходим, чтобы программа не посчитала себя зарегеной, а то как вводить код? Как вы понимаете вываливаться будет 2 раза. Первый Basic код, второй Deluxe-код. Вот пожалуй и все. Перейдем теперь к написанию настоящего кейгена.
4) Написание кейгена на Delphi
Сегодня мы покажем класс. Soft-Ice можете отложить в сторонку. Будем писать кейген, ТОЛЬКО опираясь на код в Win32Dasm'e. У каждого внутри есть свой Soft-Ice надо только научиться им пользоваться. Заходим в про- цедуру генерации пароля 4030F0 и анализируем ее. :004030F0 55 push ebp :004030F1 8BEC mov ebp, esp :004030F3 83EC4C sub esp, 0000004C :004030F6 56 push esi :004030F7 57 push edi :004030F8 C745B800000000 mov [ebp-48], 00000000 } :004030FF C745BC01000000 mov [ebp-44], 00000001 } Инициализация переменных :00403106 C745D800000000 mov [ebp-28], 00000000 } :0040310D C745C400000000 mov [ebp-3C], 00000000 } ;Помните push перед процедурой, так вот он в [ebp+8], а что он значил ;помните? Если 2, то это Basic, если 3 - Deluxe. :00403114 837D0802 cmp dword ptr [ebp+08], 00000002 <-Basic :00403118 7406 je 00403120 :0040311A 837D0801 cmp dword ptr [ebp+08], 00000001 :0040311E 7507 jne 00403127 * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:00403118(C) | :00403120 C745D803000000 mov [ebp-28], 00000003 * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:0040311E(C) | :00403127 837D0803 cmp dword ptr [ebp+08], 00000003 <-Наш Deluxe :0040312B 7406 je 00403133 <-Переходим :0040312D 837D0805 cmp dword ptr [ebp+08], 00000005 :00403131 7507 jne 0040313A * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:0040312B(C) | :00403133 C745D807000000 mov [ebp-28], 00000007 <-Так значит в переменной [ebp-28] теперь 7 * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:00403131(C) | :0040313A 837D0804 cmp dword ptr [ebp+08], 00000004 <- Не равно :0040313E 7507 jne 00403147 <- Переходим :00403140 C745D804000000 mov [ebp-28], 00000004 * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:0040313E(C) | :00403147 33C0 xor eax, eax } :00403149 8945C8 mov dword ptr [ebp-38], eax } :0040314C 8945CC mov dword ptr [ebp-34], eax } Обнуление переменных :0040314F 8945D0 mov dword ptr [ebp-30], eax } :00403152 668945D4 mov word ptr [ebp-2C], ax } :00403156 8B0DA48E4200 mov ecx, dword ptr [00428EA4] } Первые 6 введенных :0040315C 894DC8 mov dword ptr [ebp-38], ecx } символов переносят :0040315F 668B15A88E4200 mov dx, word ptr [00428EA8] } в память начиная с :00403166 668955CC mov word ptr [ebp-34], dx } [ebp-38] :0040316A C745C000000000 mov [ebp-40], 00000000 :00403171 EB09 jmp 0040317C * Referenced by a (U)nconditional or (C)onditional Jump at Addresses: |:004031A9(U), :004031C6(U) | :00403173 8B45C0 mov eax, dword ptr [ebp-40] } Добавление к счетчику :00403176 83C001 add eax, 00000001 } цикла единицы :00403179 8945C0 mov dword ptr [ebp-40], eax } * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:00403171(U) | :0040317C 837DC006 cmp dword ptr [ebp-40], 00000006 <- Проверка все ли 6 символов обработаны :00403180 7D46 jge 004031C8 :00403182 8B4DC0 mov ecx, dword ptr [ebp-40] <- В [ebp-40] счетчик цикла :00403185 8A540DC8 mov dl, byte ptr [ebp+ecx-38] <- Берем n-символ :00403189 8855DC mov byte ptr [ebp-24], dl <- Записываем его сюда :0040318C 0FBE45DC movsx eax, byte ptr [ebp-24] <- Опять его берем теперь в eax :00403190 0345C0 add eax, dword ptr [ebp-40] <- Добавляем к нему счетчик цикла :00403193 0FAF45BC imul eax, dword ptr [ebp-44] <- Умножаем получившееся на общую сумму в [ebp-44] :00403197 8945BC mov dword ptr [ebp-44], eax <- Записываем в общую сумму :0040319A 837DC001 cmp dword ptr [ebp-40], 00000001 <- Если символ 1 или 2 :0040319E 7E0B jle 004031AB <- то переходим :004031A0 0FBE4DDC movsx ecx, byte ptr [ebp-24] <- Заносим символ в ecx :004031A4 83F92D cmp ecx, 0000002D <- Сравниваем символ с символом '-' :004031A7 7502 jne 004031AB <- если не равно :004031A9 EBC8 jmp 00403173 <- иначе * Referenced by a (U)nconditional or (C)onditional Jump at Addresses: |:0040319E(C), :004031A7(C) | :004031AB 0FBE55DC movsx edx, byte ptr [ebp-24] <- Заносим символ в edx :004031AF 83FA7A cmp edx, 0000007A <- Если код больше 'Z' :004031B2 7F09 jg 004031BD <- переход на выход :004031B4 0FBE45DC movsx eax, byte ptr [ebp-24] <- Заносим символ в eax :004031B8 83F841 cmp eax, 00000041 <- Если код больше 'A' :004031BB 7D09 jge 004031C6 <- переход ; Это и есть сравнение "только большие латинские буквы" * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:004031B2(C) | :004031BD C745B801000000 mov [ebp-48], 00000001 :004031C4 EB02 jmp 004031C8 <- Выход с позором * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:004031BB(C) | :004031C6 EBAB jmp 00403173 <- Новый виток цикла * Referenced by a (U)nconditional or (C)onditional Jump at Addresses: |:00403180(C), :004031C4(U) | :004031C8 837DB800 cmp dword ptr [ebp-48], 00000000 :004031CC 0F85D9010000 jne 004033AB <- Не переходим :004031D2 8B4DD8 mov ecx, dword ptr [ebp-28] <- Берем число зависящее ;от типа регистрации для Deluxe это 7, для ;Basic это 3 :004031D5 69C9C8000000 imul ecx, 000000C8 <- Умножаем его на C8 :004031DB 8B45BC mov eax, dword ptr [ebp-44] <- Берем сумму из предыдущего цикла :004031DE 33D2 xor edx, edx :004031E0 F7F1 div ecx <- Eax делим нацело на ecx результат в eax :004031E2 8945BC mov dword ptr [ebp-44], eax <- Записываем его в сумму * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:004031F6(U) | :004031E5 817DBC301B0F00 cmp dword ptr [ebp-44], 000F1B30 <- Если сумма меньше F1B30 :004031EC 760A jbe 004031F8 <- переход :004031EE 8B55BC mov edx, dword ptr [ebp-44] } :004031F1 D1EA shr edx, 1 } Делим сумму на 2 :004031F3 8955BC mov dword ptr [ebp-44], edx } :004031F6 EBED jmp 004031E5 <- Проверяем заново * Referenced by a (U)nconditional or (C)onditional Jump at Addresses: |:004031EC(C), :00403209(U) | :004031F8 817DBCA0860100 cmp dword ptr [ebp-44], 000186A0 <- если сумма больше 186A0 :004031FF 730A jnb 0040320B <- переход :00403201 8B45BC mov eax, dword ptr [ebp-44] } :00403204 D1E0 shl eax, 1 } Умножаем сумму на 2 :00403206 8945BC mov dword ptr [ebp-44], eax } :00403209 EBED jmp 004031F8 <- Повторяем заново * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:004031FF(C) | :0040320B 8B4DBC mov ecx, dword ptr [ebp-44] } :0040320E 81C180000000 add ecx, 00000080 } Добавляем к сумме 80h :00403214 894DBC mov dword ptr [ebp-44], ecx } :00403217 8B55BC mov edx, dword ptr [ebp-44] :0040321A 52 push edx * Possible StringData Ref from Data Obj ->"%d" | :0040321B 6808524200 push 00425208 :00403220 8D45CE lea eax, dword ptr [ebp-32] :00403223 50 push eax <- Адрес памяти куда будет записан перевод :00403224 E8D31E0100 call 004150FC <- Перевод числа в строку :00403229 83C40C add esp, 0000000C :0040322C 8A4DCE mov cl, byte ptr [ebp-32] <- Берем первое число :0040322F 884DDC mov byte ptr [ebp-24], cl <- Помещаем в [ebp-24] :00403232 8A55D3 mov dl, byte ptr [ebp-2D] } Заменяем первое на :00403235 8855CE mov byte ptr [ebp-32], dl } последнее. :00403238 8A45DC mov al, byte ptr [ebp-24] } Заменяем последнее на число :0040323B 8845D3 mov byte ptr [ebp-2D], al } из буфера, т.е. бывшее первое :0040323E 0FBE4DCE movsx ecx, byte ptr [ebp-32] <- Берем первое число в ecx :00403242 83F930 cmp ecx, 00000030 <- Если число не равно '0' :00403245 7504 jne 0040324B <- Переходим :00403247 C645CE39 mov [ebp-32], 39 <- Иначе заменяем первое число на '9' * Referenced by a (U)nconditional or (C)onditional Jump at Address: |:00403245(C) | :0040324B C645D400 mov [ebp-2C], 00 <- Закрываем строку Теперь по адресу [ebp-32] число прибавив которое к введенной строке получится истинный код. Надеюсь все понятно из моих комментариев. Видите как просто, зачем здесь Soft-Ice. Я сляпал кейген на Delpi. Так как это быстро и просто. Да и Вас загружать не зачем. В нем я умышленно, чтобы не разрасталась статья не привожу проверку на заглавные буквы, т.к. программа воспринимает только заглавные. Если надо будет напишите сами это не сложно. Для создания кей- гена на основной форме нужно поместить два компонента Edit с именами Edit1 и Edit2 (они по умолчанию будут такими). И одну кнопку, имя любое. Затем жмете два раза на кнопку и вставляете этот фрагмент: if Length(Edit1.Text)>=6 then // Проверка на длинну Begin S:=Edit1.Text; I:=1; Z:=7; ; Тип регистрации Basic - 3 или Deluxe - 7 For C:=1 TO 6 DO I:=I*(Ord(S[C])+C-1); Z:=Z*$C8; I:=I div Z; while I>$F1B30 do I:=I div 2; while I<$186A0 do I:=I*2; I:=I+$80; S := IntToStr(I); C:=Ord(S[Length(S)]); S[Length(S)]:=S[1]; if c=$30 then c:=$39; S[1]:=Chr(C); Edit2.Text:=Edit1.Text+S; End; Разобраться с этими строками легко, я думаю вы справитесь, если что непонятно пишите. Адрес есть в начале и в конце.
Послесловие
Вот и закончена работа потирая руки вы регистрируете программу на себя. Винище льется рекой вы празднуете халявно заработанные 20$. Хочу надеяться, что эта статья Вас чему-либо научила и помогла в осво- ении этой нелегкой науки. Снять регистрацию можно, в разделе реестра: HKEY_CURRENT_USER\SOFTWARE\Serenescreen\SereneAquarium Удалив параметр Code. Люди, если у Вас есть деньги и Вам понравилась эта программа ку- пите ее, поддержите разработчиков для выпуска новых версий. Тем более прога действительно хороша. Крэкеры, крякеры и кракерята, сказать практически нечего разве, что только не ругайте сильно разработчиков за такую корявую защиту. Разработчики, если хотите, чтобы за Вашу программу платили Вам, а не пиратам защищайте сильнее, а то эта защита никуда не годна, ее слома- ет даже начинающий. Автор: Fess

Все ругательства отправлять в null
Все остальное на lomovskih@yandex.ru

Спасибо за интерес к моему творчеству!
Удачи в Reversing Engeneering!
P.S. Запомните все материалы публикуются только в учебных целях и автор за их использование ответственности не несет!!
P.P.S. Возможно имеют место опечатки, заранее извините!


With best wishes Fess

И да пребудет с вами великий дух bad-сектора.



Обсуждение статьи: От патча до кейгена : Sanchs Marine Aquarium v0.99L Beta. >>>


Материалы находятся на сайте https://exelab.ru



Оригинальный DVD-ROM: eXeL@B DVD !


Вы находитесь на EXELAB.rU
Проект ReactOS