Исследование защиты программы Restorator
Скриншот программы Restorator
Restorator - один из самых известных редакторов ресурсов для Windows. Основная фишка, которая мне в нем нравилась больше всего - это возможность создания автономных патчей ресурсов, например, для русификации программ. Но этим, конечно же, список его достоинств не ограничивается. К недостаткам могу отнести, пожалуй, весьма специфический интерфейс для работы с файлами и необходимость выкладывать деньги за лицензию. Много лет этот редактор не обновлялся, а тут вдруг разработчики решили допилить его под современные реалии. Так что эта статья посвящается возвращению легенды.
Как обычно, первым делом забираем с офсайта дистрибутив. На сайте есть еще триальная версия, она не регистрируется и ее качать не надо. Устанавливаем, запускаем. Программа с ходу встречает нас окном с предложением ввести ключ. Без этого ничего не сделать.
Триальное окно
Ладно, файл ничем не упакован, отправляем его в дизассемблер. А пока давайте поищем в файле что-нибудь, относящееся к этому окну, например, заголовок. В ресурсах обнаружится следующая строчка.
Строка в ресурсах
Ее индекс 64778 в десятичной или 0FD0Ah в шестнадцатеричной системе счисления. Поищем индекс в листинге.
Code (Assembler) : Убрать нумерацию
- .text:0054B094 off_54B094 dd offset hModule
- .text:0054B098 dd 0FD0Ah
Code (Assembler) : Убрать нумерацию
- .text:0054B09C sub_54B09C proc near ; CODE XREF: sub_54B110+5 p
- .text:0054B09C var_4 = dword ptr -4
- .text:0054B09C push ebp
- .text:0054B09D mov ebp, esp
- .text:0054B09F push 0
- .text:0054B0A1 push ebx
- .text:0054B0A2 mov ebx, eax
- .text:0054B0A4 xor eax, eax
- .text:0054B0A6 push ebp
- .text:0054B0A7 push offset loc_54B102
- .text:0054B0AC push dword ptr fs:[eax]
- .text:0054B0AF mov fs:[eax], esp
- .text:0054B0B2 lea edx, [ebp+var_4]
- .text:0054B0B5 mov eax, offset off_54B094
- .text:0054B0BA call @System@LoadResString
- .text:0054B0BF mov edx, [ebp+var_4]
- .text:0054B0C2 mov eax, ebx
- .text:0054B0C4 call @Controls@TControl
- .text:0054B0C9 xor edx, edx
- .text:0054B0CB mov eax, [ebx+368h]
- .text:0054B0D1 call @Extctrls@TNotebook
- .text:0054B0D6 mov eax, [ebx+360h]
- .text:0054B0DC mov [eax+114h], ebx
- ...
Code (Assembler) : Убрать нумерацию
- .text:0054B110 sub_54B110 proc near
- .text:0054B110 push ebx
- .text:0054B111 mov ebx, eax
- .text:0054B113 mov eax, ebx
- .text:0054B115 call sub_54B09C
- .text:0054B11A mov eax, ebx
- .text:0054B11C mov edx, [eax]
- .text:0054B11E call dword ptr [edx+0FCh]
- .text:0054B124 pop ebx
- .text:0054B125 retn
- .text:0054B125 sub_54B110 endp
Code (Assembler) : Убрать нумерацию
- .text:005754AD mov eax, off_599548
- .text:005754B2 mov eax, [eax]
- .text:005754B4 call sub_4DB038
- ; Указатель на блок параметров
- .text:005754B9 mov eax, off_599548
- .text:005754BE mov eax, [eax]
- ; Байт по смещению 15h должен быть ненулевым, иначе вывести окно регистрации
- .text:005754C0 cmp byte ptr [eax+15h], 0
- .text:005754C4 jnz short loc_57550C
- .text:005754C6 mov ecx, off_5999DC
- .text:005754CC mov ecx, [ecx]
- .text:005754CE mov dl, 1
- .text:005754D0 mov eax, ds:off_54A858
- .text:005754D5 call @Forms@TCustomForm
- .text:005754DA mov edx, off_5997D8
- .text:005754E0 mov [edx], eax
- .text:005754E2 mov eax, off_5997D8
- .text:005754E7 mov eax, [eax]
- .text:005754E9 call sub_54B110
- .text:005754EE mov eax, off_599548
- .text:005754F3 mov eax, [eax]
- .text:005754F5 cmp byte ptr [eax+15h], 0
- .text:005754F9 jnz short loc_57550C
- .text:005754FB mov eax, off_5999DC
- .text:00575500 mov eax, [eax]
- .text:00575502 call @Forms@TApplication@Terminate
- .text:00575507 jmp loc_575645
- .text:0057550C ; ---------------------------------------------
- .text:0057550C loc_57550C:
- .text:0057550C cmp byte_5992FC, 0
- .text:00575513 jz short loc_575534
- .text:00575515 mov eax, off_5999DC
Собщение о поврежденном файле
Где-то выполняется проверка целостности исполняемого файла. Мы его пропатчили, стало быть, целостность нарушена. Давайте поищем, где находится строка этого сообщения.
Строка сообщения в ресурсах
Вот, строка найдена в ресурсах. Ее индекс 64581 в десятичной или 0FC45h в шестнадцатеричной системе счисления. Поищем индекс в листинге.
Code (Assembler) : Убрать нумерацию
- .text:0057512C off_57512C dd offset hModule
- .text:00575130 dd 0FC45h
Code (Assembler) : Убрать нумерацию
- .text:0058204B call sub_5076E0
- .text:00582050 test al, al
- .text:00582052 jnz short loc_582075
- .text:00582054 lea edx, [ebp+var_C]
- .text:00582057 mov eax, offset off_57512C
- .text:0058205C call @System@LoadResString
- .text:00582061 mov ecx, [ebp+var_C]
- .text:00582064 mov dl, 1
- .text:00582066 mov eax, ds:off_408858
- .text:0058206B call unknown_libname_157
- .text:00582070 call @System@@RaiseExcept$qqrv
Невозможно создать патч
Внешне все работает, но при попытке создать автономный патч ресурсов проявляется еще одно ограничение.
Строка сообщения в ресурсах
Строка сообщения найдена в ресурсах. Точнее, таких строк там две, нас интересует вторая. По ее индексу выходим на следующий указатель:
Code (Assembler) : Убрать нумерацию
- .text:0056A5C0 off_56A5C0 dd offset X
- .text:0056A5C4 dd 0FC9Ah
Code (Assembler) : Убрать нумерацию
- .text:0056A64F call @Registry@TRegistry@ValueExists
- .text:0056A654 test al, al
- .text:0056A656 jz short loc_56A67A
- .text:0056A658 mov edx, offset _str_Password.Text
- .text:0056A65D mov eax, [ebp+var_18] ; this
- .text:0056A660 call @Registry@TRegistry@ValueExists
- .text:0056A665 test al, al
- .text:0056A667 jz short loc_56A67A
- .text:0056A669 mov edx, offset _str_Type.Text
- .text:0056A66E mov eax, [ebp+var_18] ; this
- ; Проверить наличие ключа в реестре
- .text:0056A671 call @Registry@TRegistry@ValueExists
- .text:0056A676 test al, al
- .text:0056A678 jnz short loc_56A67E
- .text:0056A67A loc_56A67A:
- ; Ключа нет, программа не зарегистрирована
- .text:0056A67A xor eax, eax
- .text:0056A67C jmp short loc_56A680
- .text:0056A67E ; ---------------------------------------
- .text:0056A67E loc_56A67E:
- ; Ключ в наличии, программа зарегистрирована
- .text:0056A67E mov al, 1
- .text:0056A680 loc_56A680:
- ; Программа зарегистрирована?
- .text:0056A680 test al, al
- ; Да, продолжить работу
- .text:0056A682 jnz short loc_56A6A5
- .text:0056A684 lea edx, [ebp+var_28]
- ; Загрузить строку сообщения из ресурсов
- .text:0056A687 mov eax, offset off_56A5C0
- .text:0056A68C call @System@LoadResString
- .text:0056A691 mov ecx, [ebp+var_28]
- .text:0056A694 mov dl, 1
- .text:0056A696 mov eax, ds:off_408858
- .text:0056A69B call unknown_libname_159
- ; Бросить исключение
- .text:0056A6A0 call @System@@RaiseExcept$qqrv
Остался еще один момент. Хоть все функциональные ограничения сняты и программа запускается, в окне "О программе" и сплеш-окне, которое появляется при старте, все равно наблюдается надпись "Trial Version":
Триальная надпись
Оно вроде и не мешается, и вообще, сплеш-окно можно отключить в настройках, но хочется, чтобы все было красиво.
Строка в ресурсах
Находим строку в ресурсах, по индексу находим указатель на указатель.
Code (Assembler) : Убрать нумерацию
- .text:00573440 off_573440 dd offset hModule
- .text:00573444 dd 0FC64h
Code (Assembler) : Убрать нумерацию
- ; Сравнить переменную с нулевым значением
- .text:005735FE cmp [ebp+var_11], 0
- .text:00573602 jz short loc_573641
- ; Если она не равна 0, то вывести строку "Licended to.."
- .text:00573604 lea eax, [ebp+var_24]
- .text:00573607 push eax
- .text:00573608 lea edx, [ebp+var_28]
- .text:0057360B mov eax, offset off_573448
- .text:00573610 call @System@LoadResString
- .text:00573615 mov eax, [ebp+var_28]
- .text:00573618 push eax
- .text:00573619 mov eax, [ebp+var_4]
- .text:0057361C mov [ebp+var_30], eax
- .text:0057361F mov [ebp+var_2C], 0Bh
- .text:00573623 lea edx, [ebp+var_30]
- .text:00573626 xor ecx, ecx
- .text:00573628 pop eax
- .text:00573629 call unknown_libname_127
- .text:0057362E mov edx, [ebp+var_24]
- .text:00573631 mov eax, [ebp+var_8]
- .text:00573634 mov eax, [eax+37Ch]
- .text:0057363A call @Controls@TControl@SetText
- .text:0057363F jmp short loc_57365F
- .text:00573641 ; ---------------------------------------
- .text:00573641 loc_573641:
- ; Если 0, то строка будет "Trial version"
- .text:00573641 lea edx, [ebp+var_34]
- .text:00573644 mov eax, offset off_573440
- .text:00573649 call @System@LoadResString
- .text:0057364E mov edx, [ebp+var_34]
- .text:00573651 mov eax, [ebp+var_8]
- .text:00573654 mov eax, [eax+37Ch]
- .text:0057365A call @Controls@TControl
Code (Assembler) : Убрать нумерацию
- .text:00573555 push [ebp+var_20]
- .text:00573558 push offset stru_573898.Text
- .text:0057355D push offset _str_Registration_0.Text
- .text:00573562 lea eax, [ebp+var_1C]
- .text:00573565 mov edx, 3
- .text:0057356A call @System@@LStrCatN$qqrv
- .text:0057356F mov edx, [ebp+var_1C]
- .text:00573572 xor ecx, ecx
- .text:00573574 mov eax, [ebp+var_18]
- .text:00573577 call @Registry@TRegistry@OpenKey
- .text:0057357C test al, al
- .text:0057357E jz short loc_5735A2
- .text:00573580 mov edx, offset _str_Name_2.Text
- .text:00573585 mov eax, [ebp+var_18]
- .text:00573588 call @Registry@TRegistry@ValueExists
- .text:0057358D test al, al
- .text:0057358F jz short loc_5735A2
- .text:00573591 mov edx, offset _str_Password_0.Text
- .text:00573596 mov eax, [ebp+var_18]
- .text:00573599 call @Registry@TRegistry@ValueExists
- .text:0057359E test al, al
- .text:005735A0 jnz short loc_5735A6
- .text:005735A2 loc_5735A2:
- .text:005735A2 xor eax, eax
- .text:005735A4 jmp short loc_5735A8
- .text:005735A6 ; ---------------------------------------
- .text:005735A6 loc_5735A6:
- .text:005735A6 mov al, 1
- .text:005735A8 loc_5735A8:
- .text:005735A8 mov [ebp+var_11], al
Данные хранятся в реестре, так что на новой машине придется повторять процесс заново. Поэтому для удобства можно оформить регистрацию в виде reg-файла.
Windows Registry Editor Version 5.00
[HKEY_CURRENT_USER\Software\Bome Software\Restorator\Registration]
"Name"="ManHunter / PCL"
"Password"="Fuck Shareware"
Последняя контрольная проверка - все работает.
Программа успешно "зарегистрирована"
Но это еще не все. С самых первых версий Restorator имеет дурную привычку помечать отредактированные ресурсы своей меткой "Bome". Вроде ничего смертельного, но неприятно. Давайте исправим это недоразумение. Маркеры формируются по кусочкам из двух WORD'ов:
Code (Assembler) : Убрать нумерацию
- .text:005080C4 call sub_50880C
- .text:005080C9 test al, al
- .text:005080CB jz short loc_5080E5
- .text:005080CD mov eax, [ebp+arg_0]
- .text:005080D0 mov eax, [eax-8]
- .text:005080D3 mov word ptr [eax+8], 6F42h ; 'Bo'
- .text:005080D9 mov eax, [ebp+arg_0]
- .text:005080DC mov eax, [eax-8]
- .text:005080DF mov word ptr [eax+0Ah], 656Dh ; 'me'
Code (Assembler) : Убрать нумерацию
- .text:00508183 call sub_5089B0
- .text:00508188 test al, al
- .text:0050818A jz short loc_5081A4
- .text:0050818C mov eax, [ebp+arg_0]
- .text:0050818F mov eax, [eax-8]
- .text:00508192 mov word ptr [eax+8], 6F42h ; 'Bo'
- .text:00508198 mov eax, [ebp+arg_0]
- .text:0050819B mov eax, [eax-8]
- .text:0050819E mov word ptr [eax+0Ah], 656Dh ; 'me'
Code (Assembler) : Убрать нумерацию
- .text:00508954 mov eax, [eax+4]
- .text:00508957 cmp dword ptr [eax+18h], 0
- .text:0050895B jz short loc_508977
- .text:0050895D mov edx, [eax+18h]
- .text:00508960 cmp word ptr [edx+8], 6F42h ; 'Bo'
- .text:00508966 jnz short loc_508970
- .text:00508968 cmp word ptr [edx+0Ah], 656Dh ; 'me'
- .text:0050896E jz short loc_508974
Вот и все, программа работает, в реестре прописано правильное регистрационное имя, косметические изменения внесены, а жизнь прекрасна. Цель достигнута. Хотя, как мне кажется, подобные программы должны быть портативными "из коробки".
Просмотров: 3155 | Комментариев: 22
Метки: исследование защиты, реверсинг
Внимание! Статья опубликована больше года назад, информация могла устареть!
Комментарии
Отзывы посетителей сайта о статье
ManHunter
(20.02.2024 в 16:59):
ida pro
Анд
(20.02.2024 в 16:58):
Добрый день, какой программой дезассемблировали в листингах?
ManHunter
(01.12.2020 в 15:23):
Добавил все патчи из камментов в статью.
ManHunter
(26.07.2019 в 16:59):
.text:0050818A jz short loc_5081A4
такая же конструкция
и для профилактики
.text:0050895B jz short loc_508977
не знаю, что это делает, но лучше предусмотреть
такая же конструкция
и для профилактики
.text:0050895B jz short loc_508977
не знаю, что это делает, но лучше предусмотреть
==DJ==[ZLO]
(26.07.2019 в 16:56):
Оперативно. Но, он даже при таком патче вешает метку.
.text:005080CB jmp short loc_5080E5
.text:005080CD mov eax, [ebp+arg_0]
.text:005080D0 mov eax, [eax-8]
.text:005080D3 mov word ptr [eax+8], 0
.text:005080D9 mov eax, [ebp+arg_0]
.text:005080DC mov eax, [eax-8]
.text:005080DF mov word ptr [eax+0Ah], 0
http://prntscr.com/okevmv
.text:005080CB jmp short loc_5080E5
.text:005080CD mov eax, [ebp+arg_0]
.text:005080D0 mov eax, [eax-8]
.text:005080D3 mov word ptr [eax+8], 0
.text:005080D9 mov eax, [ebp+arg_0]
.text:005080DC mov eax, [eax-8]
.text:005080DF mov word ptr [eax+0Ah], 0
http://prntscr.com/okevmv
ManHunter
(26.07.2019 в 16:21):
.text:005080C4 call sub_50880C
.text:005080C9 test al, al
.text:005080CB jz short loc_5080E5 <---- jmp
.text:005080CD mov eax, [ebp+arg_0]
.text:005080D0 mov eax, [eax-8]
.text:005080D3 mov word ptr [eax+8], 6F42h ; 'Bo'
.text:005080D9 mov eax, [ebp+arg_0]
.text:005080DC mov eax, [eax-8]
.text:005080DF mov word ptr [eax+0Ah], 656Dh ; 'me'
.text:005080C9 test al, al
.text:005080CB jz short loc_5080E5 <---- jmp
.text:005080CD mov eax, [ebp+arg_0]
.text:005080D0 mov eax, [eax-8]
.text:005080D3 mov word ptr [eax+8], 6F42h ; 'Bo'
.text:005080D9 mov eax, [ebp+arg_0]
.text:005080DC mov eax, [eax-8]
.text:005080DF mov word ptr [eax+0Ah], 656Dh ; 'me'
==DJ==[ZLO]
(26.07.2019 в 16:12):
Приветствую вас Дмитрий. Все получилось. Но, есть маленькая неприятность Помогите избавиться от дополнительного мусора который ресторатор оставляет после себя. 20шт(у меня) меток "Bome".
http://prntscr.com/oke28n
http://prntscr.com/oke28n
Андрей
(26.03.2019 в 14:59):
всё супер. огромное спасибо.
http://prntscr.com/n33mcm
http://prntscr.com/n33mcm
ManHunter
(26.03.2019 в 13:43):
.text:0056A67A xor eax, eax <-- mov al,1
Андрей
(26.03.2019 в 12:55):
маленькая поправочка.
наг окошко было на русском языке. возможно с руссиком что-то было не так.
но и без всяких других patchs тоже самое.
P.S. через ключ такое не выскакивает.
http://prntscr.com/n31ogw
ManHunter (26.03.2019 в 12:40):
Регистрацию в реестр занес?
- да, конечно.
http://prntscr.com/n31q19
наг окошко было на русском языке. возможно с руссиком что-то было не так.
но и без всяких других patchs тоже самое.
P.S. через ключ такое не выскакивает.
http://prntscr.com/n31ogw
ManHunter (26.03.2019 в 12:40):
Регистрацию в реестр занес?
- да, конечно.
http://prntscr.com/n31q19
ManHunter
(26.03.2019 в 12:40):
Регистрацию в реестр занес?
Андрей
(26.03.2019 в 05:12):
добрый день.
всё супер. окно регистрации пропало. в "About" тоже всё хорошо.
но где-то не срослось, может у меня...
при попытке создать patch через Restorator вылезло плохое окно. удалил и заного поставил Restorator с чисткой реестра и с регистрацией от ключа. Patch вышел отлично. делал patch регистрации через dUP2(скрины прилагаю). проверьте кто так-же попробовал зарегать. а так всё супер, сайт нравиться и читаю с удовольствием.
http://prntscr.com/n2x2mi
http://prntscr.com/n2x2xg
http://prntscr.com/n2x4n0
всё супер. окно регистрации пропало. в "About" тоже всё хорошо.
но где-то не срослось, может у меня...
при попытке создать patch через Restorator вылезло плохое окно. удалил и заного поставил Restorator с чисткой реестра и с регистрацией от ключа. Patch вышел отлично. делал patch регистрации через dUP2(скрины прилагаю). проверьте кто так-же попробовал зарегать. а так всё супер, сайт нравиться и читаю с удовольствием.
http://prntscr.com/n2x2mi
http://prntscr.com/n2x2xg
http://prntscr.com/n2x4n0
ManHunter
(17.09.2018 в 08:33):
С таким уровнем рановато браться за взломы. Подтяни теорию, через пару лет возвращайся.
Сергей
(17.09.2018 в 05:54):
Здравствуйте
Можно несколько вопросов от новичка?
Как определили что индекс 64581 в десятичной в шестнадцатеричной системе будет 0FC45h
Что такое листинг и как в нем искать
Как патчить условный переход по адресу 00582052 на безусловный
Спасибо
Можно несколько вопросов от новичка?
Как определили что индекс 64581 в десятичной в шестнадцатеричной системе будет 0FC45h
Что такое листинг и как в нем искать
Как патчить условный переход по адресу 00582052 на безусловный
Спасибо
pawel97
(08.08.2018 в 17:39):
p.s. Не, crc всё равно патчить. Первый раз при изменении 5754C0 в памяти (не в файле) вылезло сообщение, а 4db44d нет, может глюк... Не важно, будет 2-й вариант.
pawel97
(08.08.2018 в 16:55):
Как вариант - этот кусок под проверку целостности не попал, и выполняется чуть раньше, и патчить чуть меньше:
004DB44D FE40 15 inc byte ptr ds:[eax+15]
Вышел хардварным бряком на нужный байт.
004DB44D FE40 15 inc byte ptr ds:[eax+15]
Вышел хардварным бряком на нужный байт.
Styx
(07.08.2018 в 15:11):
Спасибо за еще одно руководство к действию! :)
Прошел немного дальше и записал данные регистрации в исполняемом файле, чтобы не вносить их каждый раз в реестр.
Прошел немного дальше и записал данные регистрации в исполняемом файле, чтобы не вносить их каждый раз в реестр.
xussr
(06.08.2018 в 12:37):
Классика!!!!(какие дрова)
Спасибо за прекрасный урок
Спасибо за прекрасный урок
Владимир
(06.08.2018 в 11:26):
в процессе исследования столкнулись с отслеживанием, ведь программа могла быть не знаю как правильно сказать оболочкой для драйвера, просто есть прога, которая общается с драйвером, а процмон нифига не показывает
ManHunter
(06.08.2018 в 10:53):
Process Monitor. Только какое отношение это имеет к статье?
Владимир
(06.08.2018 в 08:59):
Спасибо! А если к реестру обращается драйвер, уже никак не отследить?
Добавить комментарий
Заполните форму для добавления комментария
В Restorator 2007 отключается в настройках: Сохранение файлов ? Создавать метки на изменённых ресурсах (стрелочка).
Полагаю что в версии 2018 аналогично.