Blog. Just Blog

Исследование защиты программы SVG To PNG Converter

Версия для печати Добавить в Избранное Отправить на E-Mail | Категория: Темная сторона Силы | Автор: ManHunter
Скриншот программы SVG To PNG Converter
Скриншот программы SVG To PNG Converter

SVG To PNG Converter - весьма толковая программа для пакетного конвертирования файлов из векторного формата SVG в более привычный формат PNG. Сейчас на сайте разработчика 1533 программы, в числе которых различные конвертеры, надстройки над офисными пакетами и всякое подобное. Если циферками не зашло, продублирую буковками: у разработчика в списке релизов числятся более полутора тысяч программ. Часть из них используют бесплатные утилиты других авторов, другая часть, как мне кажется, какие-то бесплатные компоненты. Пора воплощать в жизнь марксистский термин "экспроприация экспроприаторов".

Забираем с офсайта последний дистрибутив, устанавливаем, смотрим. Основной файл написан на Visual Basic, отправляем его на дизассемблирование. А пока посмотрим на проявления незарегистрированной программы. После запуска программы открывается окно с предложением регистрации. Но главное ограничение, что за один раз можно обработать не более двух файлов. При этом появляется сообщение с предложением метнуться в кассу.

Триальное ограничение программы
Триальное ограничение программы

Поиском по листингу строки этого сообщения обнаруживается следующий код:
  1. .text:00468CAA                 mov     dword ptr [ebp-4], 31h
  2. .text:00468CB1                 lea     eax, [ebp-38h]
  3. .text:00468CB4                 push    eax
  4. .text:00468CB5                 call    sub_460B20
  5. .text:00468CBA                 movsx   ecx, ax
  6. .text:00468CBD                 test    ecx, ecx
  7. .text:00468CBF                 jnz     short loc_468D31
  8. .text:00468CC1                 mov     dword ptr [ebp-4], 33h
  9. .text:00468CC8                 push    offset aOnlyTwoFilesCa
  10. ; "Only two files can be worked on at a ti"...
  11. .text:00468CCD                 push    offset dword_408758
  12. .text:00468CD2                 call    ds:__vbaStrCat
  13. .text:00468CD8                 mov     edx, eax
  14. .text:00468CDA                 lea     ecx, [ebp-70h]
  15. .text:00468CDD                 call    ds:__vbaStrMove
  16. .text:00468CE3                 push    eax
  17. .text:00468CE4                 push    offset dword_408758
  18. .text:00468CE9                 call    ds:__vbaStrCat
  19. .text:00468CEF                 mov     edx, eax
  20. .text:00468CF1                 lea     ecx, [ebp-74h]
  21. .text:00468CF4                 call    ds:__vbaStrMove
  22. .text:00468CFA                 push    eax
  23. .text:00468CFB                 push    offset aWouldYouLike_0
  24. ; "Would you like to purchase a personal l"...
  25. .text:00468D00                 call    ds:__vbaStrCat
  26. .text:00468D06                 mov     edx, eax
  27. .text:00468D08                 lea     ecx, [ebp-78h]
  28. .text:00468D0B                 call    ds:__vbaStrMove
  29. .text:00468D11                 lea     edx, [ebp-78h]
  30. .text:00468D14                 push    edx
  31. .text:00468D15                 call    sub_460DB0
Все просто и понятно. Вызывается функция проверки по адресу 00460B20, если ее результат не нулевой, то сообщение не выводится и ограничение не применяется. Посмотрим на функцию проверки.
  1. .text:00460B20                 push    ebp
  2. .text:00460B21                 mov     ebp, esp
  3. .text:00460B23                 sub     esp, 8
  4. .text:00460B26                 push    offset __vbaExceptHandler
  5. .text:00460B2B                 mov     eax, large fs:0
  6. .text:00460B31                 push    eax
  7. .text:00460B32                 mov     large fs:0, esp
  8. .text:00460B39                 sub     esp, 34h
  9. .text:00460B3C                 push    ebx
  10. .text:00460B3D                 push    esi
  11. .text:00460B3E                 push    edi
  12. .text:00460B3F                 mov     [ebp+var_8], esp
  13. .text:00460B42                 mov     [ebp+var_4], offset dword_4012B8
  14. .text:00460B49                 mov     ebx, [ebp+arg_0]
  15. .text:00460B4C                 xor     eax, eax
  16. .text:00460B4E                 mov     [ebp+var_1C], eax
  17. .text:00460B51                 mov     [ebp+var_18], eax
  18. .text:00460B54                 lea     eax, [ebp+var_2C]
  19. .text:00460B57                 mov     [ebp+var_24], ebx
  20. .text:00460B5A                 push    eax
  21. .text:00460B5B                 mov     [ebp+var_2C], 4008h
  22. .text:00460B62                 call    ds:rtcIsNumeric
  23. .text:00460B68                 cmp     ax, 0FFFFh
  24. .text:00460B6C                 jnz     loc_460BF8
  25. .text:00460B72                 mov     ecx, [ebx]
  26. .text:00460B74                 push    ecx
  27. .text:00460B75                 push    offset dword_4072B8
  28. .text:00460B7A                 call    ds:__vbaStrCmp
  29. .text:00460B80                 test    eax, eax
  30. .text:00460B82                 jz      short loc_460BF8
  31. .text:00460B84                 mov     edi, 1
  32. .text:00460B89 loc_460B89:
  33. .text:00460B89                 mov     eax, 0C8h
  34. .text:00460B8E                 cmp     di, ax
  35. .text:00460B91                 jg      short loc_460BF8
  36. .text:00460B93                 push    edi
  37. .text:00460B94                 call    ds:__vbaStrI2
  38. .text:00460B9A                 mov     edx, eax
  39. .text:00460B9C                 lea     ecx, [ebp+var_1C]
  40. .text:00460B9F                 call    ds:__vbaStrMove
  41. .text:00460BA5                 lea     edx, [ebp+var_1C]
  42. .text:00460BA8                 push    edx
  43. .text:00460BA9                 call    sub_4608F0
  44. .text:00460BAE                 call    ds:__vbaFpR8
  45. .text:00460BB4                 mov     eax, [ebx]
  46. .text:00460BB6                 fstp    [ebp+var_44]
  47. .text:00460BB9                 push    eax
  48. .text:00460BBA                 call    ds:__vbaR8Str
  49. ; Сравнить введенный номер и правильный серийный номер из массива
  50. .text:00460BC0                 fcomp   [ebp+var_44]
  51. .text:00460BC3                 fnstsw  ax
  52. .text:00460BC5                 test    ah, 40h
  53. .text:00460BC8                 jz      short loc_460BD1
  54. ; Серийник правильный
  55. .text:00460BCA                 mov     esi, 1
  56. .text:00460BCF                 jmp     short loc_460BD3
  57. .text:00460BD1 ; -------------------------------
  58. .text:00460BD1 loc_460BD1:
  59. .text:00460BD1                 xor     esi, esi
  60. .text:00460BD3 loc_460BD3:
  61. .text:00460BD3                 lea     ecx, [ebp+var_1C]
  62. .text:00460BD6                 call    ds:__vbaFreeStr
  63. .text:00460BDC                 neg     esi
  64. .text:00460BDE                 test    si, si
  65. .text:00460BE1                 jz      short loc_460BEA
  66. ; Один из 200 проверенных серийников оказался правильным
  67. .text:00460BE3                 mov     [ebp+var_18], 0FFFFFFFFh
  68. .text:00460BEA loc_460BEA:
  69. .text:00460BEA                 mov     eax, 1
  70. .text:00460BEF                 add     ax, di
  71. .text:00460BF2                 jo      short loc_460C22
  72. .text:00460BF4                 mov     edi, eax
  73. .text:00460BF6                 jmp     short loc_460B89
  74. .text:00460BF8 ; -------------------------------
  75. .text:00460BF8 loc_460BF8:
  76. .text:00460BF8                 wait
  77. .text:00460BF9                 push    offset loc_460C0B
  78. .text:00460BFE                 jmp     short locret_460C0A
  79. .text:00460C00 ; -------------------------------
  80. .text:00460C00 loc_460C00:
  81. .text:00460C00                 lea     ecx, [ebp+var_1C]
  82. .text:00460C03                 call    ds:__vbaFreeStr
  83. .text:00460C09                 retn
  84. .text:00460C0A ; -------------------------------
  85. .text:00460C0A locret_460C0A:
  86. .text:00460C0A                 retn
  87. .text:00460C0B ; -------------------------------
  88. .text:00460C0B loc_460C0B:
  89. .text:00460C0B                 mov     ecx, [ebp+var_10]
  90. ; Результат проверки 0 или 0xFFFF
  91. .text:00460C0E                 mov     ax, word ptr [ebp+var_18]
  92. .text:00460C12                 pop     edi
  93. .text:00460C13                 pop     esi
  94. .text:00460C14                 mov     large fs:0, ecx
  95. .text:00460C1B                 pop     ebx
  96. .text:00460C1C                 mov     esp, ebp
  97. .text:00460C1E                 pop     ebp
  98. .text:00460C1F                 retn    4
Поясню словами, что тут происходит. Сперва проверяется, что введенный серийник является числом, затем проверяется, что он не пустой. Давайте попробуем отловить правильный серийник. Загружаем программу в отладчик, ставим точку останова по адресу 00460B20 и попробуем ввести любое число. В цикле проверяется 200 номеров, причем для этого используются команды математического сопроцессора. Ставим точку останова на проверку, смотрим, что и с чем сравнивается.

Сравнение чисел
Сравнение чисел

Число 123456789 - это введенный неправильный серийник, число 50653000 - это то, с чем оно сравнивается. Таким образом, в программе зашиты 200 предустановленных серийников, но нам достаточно и этого. Кстати, независимо от результата, проверяются все 200 чисел, что наводит на мысли о квалификации писавшего этот код.

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

Если не хочется заморачиваться с отладчиками и серийниками, то можно просто пропатчить функцию проверки, чтобы она всегда возвращала правильный результат. Для этого надо записать в ее начало по адресу 00460B20 пару команд MOV EAX,0FFFFh и RET 4. В этом случае даже не придется ничего вводить, все будет работать и так.

Еще одна гадость срабатывает случайным образом - иногда при старте открывается сайт разработчика. По названию сайта выходим на следующий код:
  1. .text:0046183B                 call    ds:rtcRandomNext
  2. .text:00461841                 fmul    ds:flt_401378
  3. .text:00461847                 fnstsw  ax
  4. .text:00461849                 test    al, 0Dh
  5. .text:0046184B                 jnz     loc_46192D
  6. .text:00461851                 call    ds:__vbaFPInt
  7. .text:00461857                 fadd    ds:flt_4012B0
  8. .text:0046185D                 fnstsw  ax
  9. .text:0046185F                 test    al, 0Dh
  10. .text:00461861                 jnz     loc_46192D
  11. .text:00461867                 call    ds:__vbaFpI2
  12. .text:0046186D                 lea     ecx, [ebp+var_28]
  13. .text:00461870                 mov     esi, eax
  14. .text:00461872                 call    edi ; __vbaFreeVar
  15. .text:00461874                 cmp     si, 7
  16. ; Рандомное условие не выполнено
  17. .text:00461878                 jnz     loc_461900
  18. .text:0046187E                 sub     esp, 10h
  19. .text:00461881                 mov     ecx, 0Ah
  20. .text:00461886                 mov     edx, esp
  21. .text:00461888                 mov     [ebp+var_38], ecx
  22. .text:0046188B                 mov     eax, 80020004h
  23. .text:00461890                 push    offset aKey     ; "Key"
  24. .text:00461895                 mov     [edx], ecx
  25. .text:00461897                 mov     ecx, [ebp+var_34]
  26. .text:0046189A                 mov     [ebp+var_30], eax
  27. .text:0046189D                 push    offset aSvgToPngConver
  28. ; "SVG To PNG Converter Software"
  29. .text:004618A2                 mov     [edx+4], ecx
  30. .text:004618A5                 push    offset aSobolsoft ; "Sobolsoft"
  31. .text:004618AA                 mov     [edx+8], eax
  32. .text:004618AD                 mov     eax, [ebp+var_2C]
  33. .text:004618B0                 mov     [edx+0Ch], eax
  34. .text:004618B3                 call    ds:rtcGetSetting
  35. .text:004618B9                 mov     edx, eax
  36. .text:004618BB                 lea     ecx, [ebp+var_14]
  37. .text:004618BE                 call    ds:__vbaStrMove
  38. .text:004618C4                 lea     ecx, [ebp+var_14]
  39. .text:004618C7                 push    ecx
  40. .text:004618C8                 call    sub_460B20
  41. .text:004618CD                 cmp     ax, 0FFFFh
  42. ; Обратное условие
  43. .text:004618D1                 jnz     short loc_461900
  44. .text:004618D3                 lea     edx, [ebp+var_38]
  45. .text:004618D6                 lea     ecx, [ebp+var_28]
  46. .text:004618D9                 mov     [ebp+var_30], offset aExplorerHttpWw
  47. ; "explorer \"http://www.sobolsoft.com/\""
  48. .text:004618E0                 mov     [ebp+var_38], 8
  49. .text:004618E7                 call    ds:__vbaVarDup
  50. .text:004618ED                 lea     edx, [ebp+var_28]
  51. .text:004618F0                 push    2
  52. .text:004618F2                 push    edx
  53. .text:004618F3                 call    ds:rtcShell
  54. .text:004618F9                 lea     ecx, [ebp+var_28]
Что интересно, тут проверяется обратное условие, то есть оно сработает как раз при условии пропатченной проверки. Ничего страшного, заменяем один из условных переходов на безусловный. Сохраняем изменения. Все, больше говносайт открываться не будет.

Теперь избавимся от ублюдочных скинов, чтобы окно программы приобрело привычный системный вид. Тут все просто, достаточно удалить файл o.cjs. Останется стилизация кнопок, но это можно пережить. А вот сейчас начнется самая мякотка. Если деинсталлировать программу, то она удалит вместе с собой регистрацию компонентов скинов, которые, во-первых, находятся во вложенной папке вместо корневой папки с программой, а во-вторых, они регистрируются для всех установленных программ этого производителя. В результате после деинсталляции ОДНОЙ программы ВСЕ оставшиеся программы разработчика перестают работать из-за ошибки скинового движка. Придется перекинуть файлы sblc.ocx и sbls.ocx из вложенной папки x в папку с программой, чтобы эти поделия хоть как-то заработали. Жесть, короче.

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

Поделиться ссылкой ВКонтакте Поделиться ссылкой на Facebook Поделиться ссылкой на LiveJournal Поделиться ссылкой в Мой Круг Добавить в Мой мир Добавить на ЛиРу (Liveinternet) Добавить в закладки Memori Добавить в закладки Google
Просмотров: 587 | Комментариев: 10

Комментарии

Отзывы посетителей сайта о статье
ManHunter (12.11.2020 в 22:21):
Вот, сразу видно, что у школьников каникулы. Русский язык, как я понимаю, в списке любимых предметов не числится.
1 (12.11.2020 в 21:45):
какой смысл с ней ковырятся дешовка
Aleksandr (10.11.2020 в 21:14):
Защиты никакой никакой обусфикации кода, никаких проверок, короче мелочь а не программа
user (09.11.2020 в 03:40):
Качество софта весьма говённое -
задрипанный фильтр для удаления символа <cr> из текста
весит 5 мегабайт.
brute (07.11.2020 в 12:25):
azaza, у XnView/IrfanView плагин CADImage.dll надо немного пролечить, чтобы триальную надпись не показывал:502EEFAE jmp loc_502EEFC9
azaza (07.11.2020 в 03:42):
rsvg-convert - https://sourceforge.net/projec...t-2.40.20.7z
(не на нем ли, случаем, разбираемое говноподелие работает?)

XnView с вышеуказанным плагином

IrfanView с последней версии
ManHunter (06.11.2020 в 18:38):
brute, так это редакторы, а тут просто конвертер. Когда надо выполнить пакетную обработку, такой конвертер будет лучше, имхо. Файлов накидал, нажал кнопку, получил результат.
brute (06.11.2020 в 18:34):
с перекодировкой SVG помогут Visio и PhotoLine
ManHunter (03.11.2020 в 18:01):
Vnv, 20 шекелей за 1 пакет и 1533*20 шекелей - это получаются совсем разные шекели
Vnv (03.11.2020 в 17:56):
Цитатана сайте разработчика 1533 программы

Смахивает на маниакальную шизофрению, мог бы все программки всунуть в один пакет. :)

Добавить комментарий

Заполните форму для добавления комментария
Имя*:
Текст комментария (не более 2000 символов)*:

*Все поля обязательны для заполнения.
Комментарии, содержащие рекламу, ненормативную лексику, оскорбления и т.п., а также флуд и сообщения не по теме, будут удаляться. Нарушителям может быть заблокирован доступ к сайту.
Наверх
Powered by PCL's Speckled Band Engine 0.2 RC3
© ManHunter / PCL, 2008-2020
При использовании материалов ссылка на сайт обязательна
Время генерации: 0.2 сек. / MySQL: 2 (0.0107 сек.) / Память: 5 Mb
Наверх