|
|
| Посл.отвђт | Сообщенiе |
|
|
Дата: Мар 1, 2003 15:32:13 Есть ли у кого нибудь исходника как при работе приложения удольть самого себя????? |
|
|
Дата: Мар 1, 2003 17:43:15 А что будет если приложение запущено с CD-R? :) --------------------------- Извините... не удержался. Можно закрыть приложение и удалить его позже посредством другого приложения (например, при следующей загрузке Windows). А ещё, можно запускать приложение через BAT-файл и удалять его делетом: prog.exe del prog.exe Правда, парсер BAT'ов ведёт себя по-разному на разных виндах, т.е. CMD на XP ждёт завершения prog.exe перед тем как запустить del, а COMSPEC на 9x выполняет del сразу. (Или всё наоборот... :) |
|
|
Дата: Мар 1, 2003 19:23:56 Можно создать тред в другом процессе и вызвать в нем функцию WaitForSingleObject с параметром - хэндлом процесса. После завершения можно удалять. |
|
|
Дата: Мар 1, 2003 19:59:36 Можно проще: в куче (спокойней как-то) написать свое имя, потом подготовить стек, чтоб после возврата из FreeLibrary (на себя) мы приехали на DeleteFile и потом - ExitProcess или что-там-нужно. Или можно исполняться прям в стеке. Вариантов - масса. |
|
|
Дата: Мар 2, 2003 00:35:57 Songoku-> 90210: Так кинь исходник!!!! |
|
|
Дата: Мар 2, 2003 13:37:59 |
|
|
Дата: Мар 3, 2003 08:01:57 По просьбам трудящихся. #include <windows.h> void main(int argc, char *argv[]) { HMODULE kernel=GetModuleHandle("kernel32.dll"); DWORD fl=(DWORD)GetProcAddress(kernel,"FreeLibrary"); DWORD df=(DWORD)GetProcAddress(kernel,"DeleteFileA"); DWORD ep=(DWORD)GetProcAddress(kernel,"ExitProcess"); char mynameis[MAX_PATH]; DWORD wearedata=(DWORD)GetModuleHandle(0); GetModuleFileName((HMODULE)wearedata,mynameis,sizeof mynameis); CloseHandle((HANDLE)4); //close section object wearedata++; //dirty trick - say we are dll loaded //with LOAD_LIBRARY_AS_DATAFILE :) __asm { lea eax,mynameis push 0 push 0 push eax push ep push wearedata push df push fl ret } } |
|
|
Дата: Мар 3, 2003 11:25:11 Плиз можна пару слов по поводу CloseHandle(4) Со стеком все понятно - у Гарри Неббета вместо трика с FreeLibrary стоит UnmapViewOfFile. А шо такое CloseHandle(4) непонятно |
|
|
Дата: Мар 3, 2003 14:36:00 Когда создается процесс, то первым делом создается объект "раздел" (section object), для того чтобы спроецировать туда исполняемый файл. Это самый первый объект в процессе, поэтому его хэндл равен 4 (все хэндлы кратны 4, хэндла 0 не существует - его место зарезервировано). Вот CloseHandle(4) именно и закрывает раздел. |
|
|
Дата: Мар 15, 2003 01:29:55 Я еще немного по-надоедаю :) теперь уже в этой ветке. Вот какие три вопроса вызвал у меня вышеизложенный материал: 1)В тексте примера программы от 90210 есть строчка wearedata++. А для чего она нужна? Ну будет в большинстве случаев wearedata сначала 40000h, а потом 40001h - и что? Зачем это надо? 2)Теперь ключевой момент программы по ссылке "Self-Deleting Executables"(см. выше): char buf[MAX_PATH]; .... lea eax, buf push 0 push 0 push eax push ExitProcess push module push DeleteFile push UnmapViewOfFile ret Я переписал все это на асме и... не работает! И правильно не работает, по-моему. Вот смотрите, если разложить последний фрагмент "по-полчкам": A)Мы размэппируем наш экзешник вызовом UnmapViewOfFile с параметром module(хэндл). Тут все отлично, выгрузили файл. B)Вызываем ф-ию DeleteFile с параметром eax==>buf(т.е. eax кажет на некий буфер). Так ведь этот буфер - участок памяти нашего УЖЕ ВЫГРУЖЕННОГО!!! файла. И вполне резонно моя прога говорит: память по адресу buf "can't be reading" - читать-то уже нечего! Вот если бы DeleteFile то же принимал хэндл(число в регистре) то да, все работало бы. А так... Вопрос простой - чего я не допонял. :) 3)В заключении статьи по вышеупомянутой ссылке говорится:"This snippet ONLY works under Windows NT". Почему же ONLY? Правда в хелпе по UnmapViewOfFile в WinAPI32.hlp говорится: Windows 95: Files for which the last view has not yet been unmapped are held open with the same sharing restrictions as the original file handle. ***** Windows NT: Files for which the last view has not yet been unmapped are held open with no sharing restrictions. Но ведь вызовом UnmapViewOfFile мы "unmapped last view", так? Или дело совсем-совсем не в этом? |
|
|
Дата: Мар 15, 2003 23:25:44 1. Это для обмана FreeLibrary - чтоб вместо LdrUnloadDll вызывалось LdrUnloadAlternateResourceModule сотоварищи. 2. Ты абсолютно прав насчет выгруженной памяти. Поэтому надо использовать или кучу, или стек. Стек проще - сишные компилеры автоматом суют локальные переменные в стек процедуры. char buf[MAX_PATH], например. |
|
|
Дата: Мар 16, 2003 14:42:52 · Поправил: Four-F К сказанному выше могу добавить, что на асме это должно выглядеть так (инклуды стандартные, которые с jump-table): .386 .model flat, stdcall option casemap:none include \masm32\include\windows.inc include \masm32\include\kernel32.inc includelib \masm32\lib\kernel32.lib .code start proc option EPILOGUE:NONE local buf[MAX_PATH]:CHAR invoke GetModuleFileName, NULL, addr buf, sizeof buf invoke CloseHandle, 4 lea eax, buf push 0 push 0 push eax mov eax, ExitProcess mov eax, [eax+2] push [eax] ; push ExitProcess invoke GetModuleHandle, NULL push eax mov eax, DeleteFile mov eax, [eax+2] push [eax] ; push DeleteFile mov eax, UnmapViewOfFile mov eax, [eax+2] push [eax] ; push UnmapViewOfFile ret start endp end start На ХР скорее всего работать не будет из-за CloseHandle, 4. Что-то M$ там переделала: то ли хендл секции не равен 4, то ли она вообще хендла не имеет. Щас возможности протестить под ХР нет. Прогоните у кого хрюша. |
|
|
Дата: Мар 16, 2003 19:05:10 To:Four-F Что-то не работает пример на 98-ом. |
|
|
Дата: Мар 16, 2003 23:46:41 Тэк-с, что могу сказать: 1)Идея, что для буфера с именем файла под удаление надо использовать стек - то, что надо. Теперь ошибки "can't be reading" нет. 2)Легче от этого не стало. :) Теперь ф-ия DeleteFile "нормально" отрабатывает(т.е. нет упомянутой выше ошибки), но в EAX возвращается 0, а последующий вызов GetLastError говорит об этом: // MessageId: ERROR_SHARING_VIOLATION // // MessageText: // // The process cannot access the file because it is being used by another process. // #define ERROR_SHARING_VIOLATION 32L 3)CloseHandle,4 отрабатывается на ура, EAX=1. Так что что-то такое под номером 4 мы закрываем. Но что именно? 4)Если предположить, что п.3 закрывает все-таки section object, то есть такая мысль(возможно ересь):наш процесс самоудаления(назовем его SelfDestroy.exe) порождается кернелом при помощи CreateProcess. При этом создаюся:объект ядра ПРОЦЕСС+объект ядра ВЕТВЬ. Хэндлы этих объектов должны быть закрыты(помимо всего прочего) и самим кернелом иначе ядро эти объекты не разрушит. Так вот если кернел закрывает эти хэндлы только ПОСЛЕ возврата из SelfDestroy.exe(а наверное так оно и есть) то мы никак эти объекты удалить не сможем. А ересь заключается в том, что вполне возможно наличие объекта ПРОЦЕСС НЕ ПРЕПЯТСТВУЕТ удалению файла содержащего код этого процесса(разумеется файл должен быть размэппирован). Вот, тут у меня пробел в знаниях. :( P.S. Все опыты из данной мессаги проводились как-раз под XP. Хотя выше сказано, что и в 98-м картина столь же безрадостна. :) Просто какой-то фантомный код - работать должен(судя по публикациям), но никто его работающим не видел. :) |
|
|
Дата: Мар 17, 2003 01:30:24 · Поправил: Four-F [ Asterix: Что-то не работает пример на 98-ом. ] Оно и не задумывалось под 9x. Только NT, 2000 и очень маловероятно ХР. Этот код придумал Гари Неббет (автор книги "Windows NT-2000 Native API Reference"). Придуман он во времена, когда 2000 только появилась (или где-то около того). И работать он будет только на клоне NT. У мя под 2000 Pro работает. Smarty, все твои траблы под ХР, IMHO, потому, что M$ изменила что-то. То что "CloseHandle,4 отрабатывается на ура" совсем не значит, то закрывается именно хендл секции образа. И скорее всего именно так. Поэтому видимо и после DeleteFile возвращается такая ошибка, т.е. хэндл секции не закрыт. Я даже думаю, что хэндла секции вообще не создается, т.к. юзерному процессу он не за чем. Косвенно об этом мне говорит тот факт, что в 2000 в структуре EPROCESS поле SectionHandle равно 4 для всех процессов. ; w2k EPROCESS STRUCT . . . SectionHandle PVOID ? ; 1ACh . . . SectionBaseAddress PVOID ? ; 1B4h . . . EPROCESS ENDS А в ХР в структуре EPROCESS вместо SectionHandle появилось SectionObject (указатель на SECTION_OBJECT). Т.е. ядро просто не делится с юзером хендлом. ; xp EPROCESS STRUCT . . . SectionObject PVOID ? ; 0138h SectionBaseAddress PVOID ? ; 013ch . . . EPROCESS ENDS Но это все мои догадки. Будет возможность гляну под ХР. Что касается всех незакрытых хендлов и удаления созданных CreateProcess объектов, то это работа для ExitProcess. И никакой прямой связи с секцией образа тут нет. Просто при загрузке образа в память работает механизм проецирования файлов. Такая память должна быть поддержана либо файлом подкачки, либо (в нашем случае) самим образом exe, лежащим на диске. Из-за этого-то и нельзя удалить запущенный экзешник. Как только объект секция исчезает сразу становится возможным удалить файл образа с диска - в этом "CloseHandle, 4" вся соль этого кода, остальное ерунда. |
|
Powered by miniBB 1.6 © 2001-2002
Время загрузки страницы (сек.): 0.133 |