Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате |
Форум программистов > C/C++: Общие вопросы > Замена кода С++ на ходу |
Автор: dark_religion 17.7.2007, 20:01 |
Подскажите пожалуйста как можно заменить код программы во время выполнения и выполнить его снова без перекомпиляции на С++ Или какие еще другие варианты возможны кроме С++ |
Автор: Daevaorn 17.7.2007, 20:23 |
С++ компилируемый язык, поэтому на выходе получается машинный код. Вот его с некоторыми трудностями, но можно редактировать в ран-тайм |
Автор: bsa 17.7.2007, 20:25 |
Имхо, проще для этого использовать наследование классов и виртуальные функции. А если надо писать самомодифицирующийся код (вирус пишишь?), то пиши на ассемблере. |
Автор: chipset 17.7.2007, 20:26 |
Скрипты или (до некоторого уровня) полиморфизм спасет тебя ![]() |
Автор: dark_religion 17.7.2007, 20:37 |
Ребята а можно поконкретнее про каждый метод. Каким образом . кто-то может предложить реализацию для например "Hello world " шоб менялось С "привет Россия" если "Hello world" выводится вот так printf("Hello world"); без переменной. без всяких if & else шоб эта строчка в коде менялась на printf("Privet Russia"); |
Автор: Daevaorn 17.7.2007, 20:41 |
этого "так" в exe нет. менять нужно данные, а не код. |
Автор: dark_religion 17.7.2007, 20:43 |
А мне нужно именно код. Но я не поспорить кто-то может показать конкретный метод? |
Автор: dark_religion 17.7.2007, 21:10 |
Мне посоветовали менять линки в минарнике .. как это можно понять? что такое бинарник? |
Автор: nickless 17.7.2007, 21:23 |
http://forum.vingrad.ru/index.php?showtopic=155591&view=findpost&p=1164944 был небольшой примерчик самомодифицирующегося кода ![]() dark_religion, а ты уверен что оно тебе надо? ![]() |
Автор: fish9370 17.7.2007, 21:42 | ||
пояснение к примеру.. здесь код фунции помещается в область стека, в которой позволяется производить запись/чтение/исполнение кода.. после чего функции передается управление.. |
Автор: bsa 17.7.2007, 22:00 |
fish9370, мало того, что глупость сморозил, так еще и _main не проинициализировал перед использованием. А потом, кто тебе сказал, что функция из области стека будет исполняться? |
Автор: fish9370 17.7.2007, 22:07 |
а _main лишь нужен, чтобы вычислить конец функции.. ![]() читай матчасть!! |
Автор: bsa 17.7.2007, 22:31 | ||||||||
Во-первых, твой код компилируется так (после убирания кривых заголовков, прагм и getch):
Во-вторых, после земены unsigned int на unsigned long (не забываем, что кроме 32-х битной windows существуют другие платформы с другой разрядностью) программа собирается без ошибок. Но при этом при запуске повисает. В-третьих, после добавления между строк 25 и 26 операции printf("%i\n", func_len); появляется вывод:
|
Автор: bsa 17.7.2007, 22:46 |
Более того, даже если бы эта прога заработала, то чуть более сложная все равно не пойдет, так как в ней обязательно будут внутренние абсолютные переходы, которые перестанут работать, если поместить код функции в другое место адресного пространства. Я поражаюсь, меня - программиста-ассемблерщика с 10-ти летним стажем обвиняют в незнании матчасти!!! ![]() |
Автор: fish9370 17.7.2007, 22:49 | ||
заметь, не я первый начал.. ![]() bsa, код заточен под Windows (включая XP).. при компиляции нужно отключать свяческую оптимизацию.. код проверялся компилятором из BDS 2006 c опцией С++ Compiler (bcc32)->optimizations->Optimize: Disable all optimizations. (-Od) |
Автор: bsa 17.7.2007, 22:55 |
НУ НЕ МОГ ОН РАБОТАТЬ ПРАВИЛЬНО! Так как ты переменную _main не проинициализировал. У тебя размер функции определялся неправильно. Соответственно, ты неизвестно сколько байт скопировал в буфер. |
Автор: fish9370 17.7.2007, 23:00 | ||
идея заключается в том, чтобы на основании этого реализовывать защиту програм.. поскольку самомодифицирующийся код анализировать труднее.. и ломается сложне.. вот эти все заморочки с описанием указателей на функции и призваны создать перемещаемый код.. ведь тут же нет прямого вызова printf.. тебе ли это не знать с твоим 10 летним опытом.. кстати, за 10 лет можно многое подзабыть.. уж я то со своим 15 летним опытом знаю.. ![]() Добавлено через 3 минуты и 44 секунды прикрепляю проект.. |
Автор: dumb 17.7.2007, 23:09 | ||||
что такое DEP слышал?
это... как бы помягче... вобщем, если приведенный выше код - демонстрация защитного механизма, то это была плохая, негодная идея.
да, только никакой связи между твоим примером и "самомодифицирующимся кодом" нет. |
Автор: bsa 17.7.2007, 23:13 |
У меня и сейчас основной доход именно от продукции на asm. ![]() Про защиту это понятно... Но в данном случае у тебя простая ошибка. Более того, их две - значение func_len всегда случайное число... Под Линуксом не работает в принципе, даже если это исправить. Вываливается сегфолт. Думаю, потому что у меня в ядре включено опция защиты от выполнения кода в левых местах. |
Автор: fish9370 17.7.2007, 23:18 | ||||||||||||
по началу ты и в то, что код можно в стеке исполнять не верил.. еще по теме..
|
Автор: fish9370 17.7.2007, 23:34 | ||||
нет.. но с удовольствием послушаю.. )
как бы это помягче сказать.. это похоже на защитный код!?! это лишь пример доказывающий, что код может быть исполнен в области стека..
нет? то что можно править код в области стека ты не веришь? P.S. читай выше.. |
Автор: W4FhLF 18.7.2007, 03:31 | ||
Повешают бряк на исполнение в стеке и будут отлаживать точно такой же код, а все эти заморочки побоку ![]() |
Автор: dark_religion 18.7.2007, 13:22 |
Спасибо fish9370, Я хоть и ниче не понял и немогу подискусировать, что будет, а чего не будет, но он единственный из всех показал реальное решение остальные просто поговорили. Может это и не оптимально, но лучшего никто не предложил. |
Автор: Daevaorn 18.7.2007, 14:04 |
ага. которое не правильное. |
Автор: bsa 18.7.2007, 14:06 | ||
Ты не понял. Повторяю еще раз коротко и ясно то, что было сказано ранее: 1. Данный код содержит ошибки. 2. Данный код если и работает, то только у автора. А после включения DEP может и перестать работать. 3. Даже после устранения всех ошибок код у меня не заработал. |
Автор: anthony 18.7.2007, 14:47 | ||
bsa, Программа полностью работоспособна с небольшой модификацией (инициализацией _main и _Demo) (Microsoft Visual Studio 2005 Professional Edition C++) даже с включенной оптимизацией (контроль ошибок выключен, сборка в Release).
W4FhLF, DEP по умолчанию отключен, с включенным протестирую после (нужно перегружаться). Но и в принципе Ваш довод не так силен. Так что господа Вы не правы. bsa относитесь к другим и их программам с большим уважением и пониманием, а не предвзято. |
Автор: W4FhLF 18.7.2007, 15:12 | ||
Я что-то про DEP говорил? |
Автор: anthony 18.7.2007, 15:15 | ||
Да с включенным DEP тоже работает. Та же программа немного модифицированная для языка С (проверено на MSVC 2005 PE, Release, Warnings Level 1)
|
Автор: bsa 18.7.2007, 16:48 |
Хорошо, плюс еще один компилятор, который это делать позволяет. Но только после исправления ошибок, про которые я кучу раз говорил... Повторяю, на Linux x86_64 с компилятором g++ 4.1.2 программа не заработала, даже после исправления ошибок. |
Автор: JackYF 18.7.2007, 16:58 |
anthony, по твоей программе. XP SP2, MinGW - g++ 3.4.5 без оптимизаций - работает. Те же, там же, с оптимизациями - сегфолт. Linux Fedora 5, i686, g++ 4.1.1 без оптимизаций - сегфолт. Те же, там же, с оптимизациями - сегфолт. Вопросы? |
Автор: Damarus 18.7.2007, 17:04 | ||
При тех же условиях у меня не работает. |
Автор: bsa 18.7.2007, 17:32 | ||
Проверил еще на x86 (gentoo, x86, gcc 4.1.2). Результат забавный:
|
Автор: fish9370 18.7.2007, 18:27 | ||
anthony, спасибо за поддержку.. в чем неправильность, друг?
ты идею не понял.. я вынесу часть кода за приделы проги.. зашифрую ключем.. при вводе правильного ключа сформируется правельный код.. без ключа, куда бряк будешь накладывать? это как пример.. Добавлено @ 18:30 и вообще, когда я о линуксе хоть раз заякнулся? в линуксе кругом один опенсорс, там вопрос о защите вообще не стоит.. bsa, так вообще код в отстой записал, типа код не по теме.. хм.. хотя сам ничего, кроме своей нелепой критики, предложить не может.. |
Автор: JackYF 18.7.2007, 18:37 |
ты три предыдущих сообщения прочитал? почему твой правильный код не работает на перечисленных нами выше платформах? |
Автор: nickless 18.7.2007, 20:12 |
Попробовал код у себя, с выключеным NX-битом работает, со включеным нет, теперь будем знать что NX действительно пашет ![]() |
Автор: Damarus 18.7.2007, 20:24 | ||
Тогда может проще сделать обычную dll'ку, а потом зашифровать её ![]() ![]() P.S. Только толку от такой защиты не много будет. |
Автор: fish9370 18.7.2007, 21:14 | ||||
а ты мои сообщения читал? что я говорил про линукс..
как известно, самым слабым звеном, в любой защите, является человек.. против раскаленного утюга еще никто не устоял.. Dll'ку шифровать это велосипед, тут я согласен.. шифровать код это тема не новая.. просто у некоторых все еще много стериотипов.. |
Автор: JackYF 18.7.2007, 21:31 |
а что из твоего кода принципиально заточено под XP, можно спросить? |
Автор: fish9370 18.7.2007, 21:33 | ||
идея!! |
Автор: JackYF 18.7.2007, 21:41 | ||
почему тогда не работает
это (вторая строчка)? |
Автор: fish9370 18.7.2007, 21:51 |
у кого руки прямые, и есть необходимость, тот идею доведет до ума.. что и говорить.. вот мне не понятно, что мы обсуждаем? че мы флудим? есть мысли по теме? кстати, у меня еще есть способ модификации кода во время исполнения.. не такой интересный, но есть.. |
Автор: dumb 19.7.2007, 04:54 | ||||
так как это был мой довод, то и отвечу я. он не отключен, а включен только для сервисов итп. в XP. в серверных вариантах - по умолчанию включен для всех программ. гон. ![]() если кому интересно, посмотрите на кашу, получающуюся в результате оптимизации. ![]() ответь на простой вопрос: какое отношение имеет представленный тобой код к вопросу в первом посте темы? - то, что автор этого вопроса сказал тебе спасибо, можно не упоминать - он сам, к сожалению, не понимает о чем спросил и что ты ему "выдал".
вобщем после всех этих "идей, заточенных под XP" становится как-то скучно и грустно. ![]() fish9370, можно тебя просто попросить не употреблять выражений типа "пустозвон","нелепый","прямые руки"? - становится смешно. а с таким набором ощущений и до "белых столбов" недалеко... ps.
![]() |
Автор: W4FhLF 19.7.2007, 07:22 | ||
Ты просто собираешься шифровать часть кода ключом, который куда-то там вынесен-перенесён? А где защита? Ну да, допустим без ключа не узнают, какой у тебя там код, а с одним валидным ключом(это в худшем случае, в лучшем просто кейген напишут, всё от твоей грамотности зависит) смогут отвязать твою программу от любых проверок. Можешь выложить свою задумку в виде готового exe, мне бы просто интересно было посмотреть, т.к. возможно, что я тебя неправильно понимаю. С таким же успехом можно программу заархивировать в rar с 20 символьным паролем и назвать это защитой. |
Автор: Santilka85 19.7.2007, 07:53 | ||
![]() ![]() ![]() |
Автор: anthony 19.7.2007, 09:25 | ||
Обновленный код (устранены ошибки и предупреждения, сокращен объем, изменен стиль). Протестировано на Win XP PE/HE SP 2 с включенным и выключенным DEP (процессоры без поддержки DEP). Проверена большая часть настроек компиляции для MSVC 2005 PE SP 1, для других компиляторов нужно аккуратно проверять настройки.
|
Автор: bsa 19.7.2007, 10:33 |
anthony, какой у тебя процессор? Он поддеживает DEP? |
Автор: JackYF 19.7.2007, 11:28 |
Вот теперь лучше. g++ [-O2] -Wall, 4.1.3, Debian lenny - полет нормальный. DEP, естественно, не стоит. С ним не должно работать, так как программа пытается выполнить инструкции, находящиеся в стеке. |
Автор: Daevaorn 19.7.2007, 14:07 |
fish9370, продолжай в том же духе и получишь предупреждение. |
Автор: fish9370 19.7.2007, 19:56 | ||||
Добавлено @ 20:04 обсуждаем дальше..
PS. надеюсь, это никому не придет в голову, компилить под линукс.. ) |
Автор: JackYF 20.7.2007, 11:46 |
Daevaorn, вообще-то, модератор этого раздела. Так что не надо здесь разжигать страсти. а, собственно, что мы сейчас обсуждаем? Теперь. Приведенные участки кода - это хорошо. Однако раздел называется: "С++: Общие вопросы". И тема называется "Замена кода С++ на ходу". А не "Замена кода С++ на ходу в операционной системе Windows". Так что последнее полным решением не является. Есть раздел "С++: Системное программирование и WinAPI". Вот там последний код окажется полезен, наверное. |
Автор: Earnest 20.7.2007, 20:45 |
Ребята, давайте жить дружно ![]() ![]() ![]() Конечно, заставить код выполняться в стеке или другой не-исполняемой памяти можно, хотя и не на всех системах. Причем прошу заметить, со временем этих систем (где нельзя), видимо, будет становиться все больше. Я когда-то этим баловалась и тоже с целью защиты, но тогда это работало почти всегда, т.к. защитный флажок хоть и имелся, но явно был задумкой на будущее... Ладно, допустим, загрузили, расшифровали, передали управление... Однако это может быть совсем не любой код, а ведь чтобы удовлетворить задумку автора, такой код должен быть a) достаточно объемный (не три оператора), б) критичный для правильной работы приложения... Ладно, напряглись, преодолели все трудности... Однако не забываем, что программ с одной версией не бывает; если программа не развивается, причем быстро, кому она нафиг нужна ... А такой способ защиты будет мешать жить прежде всего самому разработчику... Особенно приятно будет изменять и отлаживать код, который вынесен из программы (помним, что он не должен быть совсем уж тривиальным). И наконец, как уже было сказано, это спасает до получения взломщиком первого же валидного ключа (а у мало-мальски ценной программы они всегда утекают - как только появляются первые пользователи)... Т.е. само по себе это абсолютно не достаточно. Нужно применять и другие приемы... Короче, не стоит овчинка выделки. Сложность защиты (в смысле усилий, потраченных как на ее разработку, так и на развитие) должна соответствовать ценности программы. |
Автор: chipset 20.7.2007, 21:37 | ||
|
Автор: DDyDog 21.7.2007, 10:43 | ||
1. Первый раз запустил программу(скопировал выше), вывело Hello, World! 2. Закоментировал часть кода
Снова вывело Hello, World! В первом случае выполнялась функция из стека (buf), во втором из сегмента кода А вопрос такой, где произошла модификация кода? И даже если модифицировать буфер и выполнить его, чем это будет отличатся от вызова еще одной функции адресс которой присвоен _Demo (вот если бы произвести модификацию сегмента кода или исполняемого файла)? А стек мы и так постоянно модифицируем ![]() И так для мыслей, может лучше вместо функций использовать обьекты-функции, и размер легче найти, и скопировать с стек легко? |