Форум: "Основная";
Текущий архив: 2004.08.08;
Скачать: [xml.tar.bz2];
ВнизДамп памяти процесса Найти похожие ветки
← →
Form (2004-07-22 10:03) [0]Вопрос: Есть некоторый процесс (например стандартный "калькулятор"), необходимо сделать дамп памяти этого процесса! Под Вынь98 все работает, но под ХП и 2000 не работает, проблема с правами! Как мне взять своему приложению права, чтобы можно было читать память чужего процесса ("Калькулятора")???
Итак текст процедуры (вроде так):
function GetWMPath:string;
var
memarr:array of char; // динамический массив для памяти!
hProc : THandle;
MBI : MEMORY_BASIC_INFORMATION;
counter,i,j : cardinal;
ln : Integer;
MaxAddy,temp : Cardinal;
dwSize, dwAddress: cardinal;
hwnd, proc_id: dword;
f: file;
begin
enabledebug; // вызов процедуры получения прав, смотри ниже!!!
counter :=0;
SetLength(memarr, 0);
dwAddress := $400000;
MaxAddy := $80000000;
hwnd:=FindWindow (pchar("SciCalc"), nil); // получаем хэндл по классу окна
GetWindowThreadProcessId (hwnd,@proc_id);
hProc := OpenProcess(PROCESS_QUERY_INFORMATION, False, Proc_ID);
While (VirtualQueryEx(hProc, Pointer(dwAddress), MBI, SizeOf(MEMORY_BASIC_INFORMATION)) > 0) and (cardinal(MBI.BaseAddress) + MBI.RegionSize < MaxAddy) do
begin
If (MBI.Protect = PAGE_READWRITE) and (MBI.Type_9 = MEM_PRIVATE) and ((MBI.State = MEM_COMMIT) or (MBI.State = MEM_RESERVE)) Then
begin
dwSize := MBI.RegionSize;
dwAddress := cardinal(MBI.BaseAddress) + (MBI.RegionSize - dwSize);
SetLength(memarr, counter + dwSize);
ReadProcessMemory(hproc,
pointer(dwAddress),
@memarr[counter],
dwSize,
temp);
counter := counter + dwSize;
end;
Inc(dwAddress, MBI.RegionSize);
end;
CloseHandle(hProc);
assignfile(f, "test.txt"); // debug - сохранение дампа
rewrite(f,1); // оставил на всякий случай!
i:=0;
repeat
blockwrite(f, memarr[i], 50);
i:=i+50;
until i >= counter;
closefile(f);
Finalize(memarr);
FreeMem(memarr);
end;
---
А вот так я пытаюсь взять себе нужные права(НЕ РАБОТАЕТ!!!):
procedure enabledebug;
var TokenHandle: THandle; dwNull: DWORD;
TokenPrivilege, Tmp: TTokenPrivileges;
begin
try
OpenProcessToken(GetCurrentProcess, TOKEN_ADJUST_PRIVILEGES or TOKEN_QUERY, TokenHandle);
LookupPrivilegeValue(nil, "SeDebugPrivilege", TokenPrivilege.Privileges[0].Luid);
with TokenPrivilege do begin
PrivilegeCount := 1;
Privileges[0].Attributes := SE_PRIVILEGE_ENABLED;
end;
dwNull := 0;
AdjustTokenPrivileges(TokenHandle, False,
TokenPrivilege, SizeOf(TTokenPrivileges), Tmp, dwNull);
except
ShowMessage("debug error!");
end;
end;
← →
Digitman © (2004-07-22 10:22) [1]
> НЕ РАБОТАЕТ
тебя кто научил так вызывать функции WinAPI ?
почему вызываешь их как процедуры ? почему не анализируешь результат их выполнения ?
> except
> ShowMessage("debug error!");
> end;
с какого перепугу ты решил, что любое исключение следует интерпретировать как ошибка отладки ? где анализ класса исключения, если оно возникает ?
WinAPI-функции вообще не возбуждают никаких исключений ! они всегда возвращают результат !
← →
Form_1 © (2004-07-22 10:25) [2]К сожалению писал это всё не я первая функция работает под виндоус 98(я проверил) а в 2000 винде действительно нехватает привилерий (1 мессадж скопирован с другого форума. там вразумительного ответа автору получить не удалось у меня сейчас таже проблема)
← →
Digitman © (2004-07-22 10:29) [3]
> Form
> SetLength(memarr, counter + dwSize);
тебе на кой ляд весь дамп в памяти хранить-то ? а если потребуется целый гигабайт ? или более ? виртуальное адресное пространство тек.процесса не резиновое ! да и еще перераспределяешь память при каждой итерации, ничтоже сумняшеся "ворочая" огромные блоки памяти туда-сюда.. нет бы сразу в файл писать !
← →
Form_1 © (2004-07-22 10:33) [4]Это всё уже второй вопрос (с которым сам наверно разберусь) надо чтобы хотябы так сначало работало.
← →
Digitman © (2004-07-22 10:36) [5]hProc := OpenProcess(PROCESS_VM_READ, False, Proc_ID);
PROCESS_VM_READ
Enables using the process handle in the ReadProcessMemory function to read from the virtual memory of the process.
> скопирован с другого форума
причем - бездумно
← →
Digitman © (2004-07-22 10:38) [6]
> чтобы хотябы так сначало работало
вот ты сказал "не хватает привелегий"
а на основании чего ты сделал такое умозаключение ?
я не вижу в твоем коде НИ ЕДИНОЙ проверки рез-та выполнения WinAPI-функций
← →
Form_1 © (2004-07-22 10:42) [7]hProc := OpenProcess(PROCESS_VM_READ, False, Proc_ID); -
Выскакивает I\O error :(
← →
Digitman © (2004-07-22 10:47) [8]
> Выскакивает I\O error
и далеко скачет ? инф-ция о коде ошибки кому выводится системой ? Пушкину ? или все-таки тебе ? для анализа причин ?
← →
Form_1 © (2004-07-22 10:49) [9]Отладчиком Дельфи.
← →
Digitman © (2004-07-22 10:55) [10]
> Form_1 © (22.07.04 10:49) [9]
> Отладчиком Дельфи.
чего "Отладчиком Дельфи" ?!
я спросил , КОМУ системой адресована инф-ция об ошибке, а не КЕМ ! Тебе она адресована, значит, тебе и искать ее причины ..
Дословный текст сообщения об ошибки из тебя клещами вытаскивать ? Или сам сподобишься наконец-то привести его ?
← →
Form_1 © (2004-07-22 10:57) [11]Debugger Exception Notification x
Project mem.exe raised exception class EInOutError with message "I/O error 1784". Process stopped. Use Step or Run to continue.
OK Help
← →
Form_1 © (2004-07-22 10:58) [12]причём выскакивает на
blockwrite(f, memarr[i], 50);
....
До изминений никаких ошибок небыло
← →
VMcL © (2004-07-22 11:06) [13]>>Form_1 © (22.07.04 10:58) [12]
>blockwrite(f, memarr[i], 50);
С какого перепугу 50?
← →
Digitman © (2004-07-22 11:06) [14]а что ж ты мне тогда мозги пудришь ?
сначала
> hProc := OpenProcess(PROCESS_VM_READ, False, Proc_ID); -
> Выскакивает I\O error :(
а теперь уже
> причём выскакивает на
> blockwrite(f, memarr[i], 50);
?
вот описание кода ошибки, мог бы и сам посмотреть его в модуле Windows.pas
{ The supplied user buffer is not valid for the requested operation. }
ERROR_INVALID_USER_BUFFER = 1784;
← →
Form_1 © (2004-07-22 11:12) [15]2Digitman И что делать?
← →
Digitman © (2004-07-22 11:18) [16]
> Form_1 © (22.07.04 11:12) [15]
> И что делать?
это ты меня спрашиваешь ?!
цитирую тебя
Form_1 © (22.07.04 10:33) [4] :
> Это всё уже второй вопрос (с которым сам наверно разберусь)
> надо чтобы хотябы так сначало работало.
ты еще с первым вопросом не разобрался - читаешь ли ты безошибочно регионы чужого процесса в свой буфер, а уже за второй вопрос взялся .. к тому же сам решил попробовать со "вторым вопросом" разобраться ... а "второй вопрос", кстати, никакого отношения к работе с вирт.памятью процесса не имеет
← →
Form_1 © (2004-07-22 11:24) [17]>"ты еще с первым вопросом не разобрался - читаешь ли ты безошибочно регионы чужого процесса в свой буфер"
Думаю да т.к. проверик код под Windows 98 всё отлично работает.
← →
Digitman © (2004-07-22 11:27) [18]
> Form_1
я тебе сразу сказал - не занимайся ерундой с дин.массивом
перед циклом создай объект класса TFilestream
при каждой итерации цикла
- запрашивай вызовом GetMem() указатель на блок памяти того размера, который возвращен тебе в поле MBI.RegionSize
- вызовом ReadProcessMemory() считывай в этот блок содержимое региона
- вызовом Filestream.WriteBuffer() записывай содержимое блока в файл
- вызовом Freemem() освобождай блок
и даже это неоптимально с т.з. расхода ресурсов тек.процесса
перед циклом выдели память размером в 4к
получив MBI.RegionSize подели его на 4к (размер региона всегда кратен 4к), получишь число страниц в регионе
в цикле по числу страниц в регионе считывай очередную страницу в блок выделенной тобой единожды памяти и тут же записывай блок в FileStream
← →
Digitman © (2004-07-22 11:33) [19]
> Думаю да т.к. проверик код под Windows 98 всё отлично работает
что значит "думаю" ? на основании чего ты уверен, что в файле у тебя оказывается именно то, что ожидалось ? и причем здесь Win9x ? речь-то , кажется, шла про Винтукей .. а в Win9x у тебя, ты сам сказал в 1-м своем посте, и так все работает..
цитирую тебя :
> Под Вынь98 все работает
и как это могло "работать" в оригинально приведенном тобой коде ? если это не могло работать в принципе хотя бы из-за использования PROCESS_QUERY_INFORMATION вместо требуемого в дан.случае PROCESS_VM_READ ? снова лапшу вешаешь ?
← →
Form_1 © (2004-07-22 11:53) [20]Всё работако с PROCESS_QUERY_INFORMATION ! в файле явно оказывалась часть памятьи калькулятора. (1мб)
← →
Digitman © (2004-07-22 12:00) [21]
> в файле явно оказывалась часть памятьи калькулятора. (1мб)
откуда ты знаешь ? ты сравнивал свой рез-т с результатами работы иных утилит, заведомо правильно работающих ?
почему именно 1мб ? где это написано, что в ВАП процесса калькулятора сумм.размер данных страниц с атрибутом доступа PAGE_READWRITE составляет именно 1мб и ни байтом меньше/больше ? и почему в твоем понимании дамп ВАП процесса ассоциируется только с данными в READWRITE-регионах ? а как же PAGE_READ ? а как же PAGE_EXECUTE ? или это уже не дамп ?
← →
Form_1 © (2004-07-22 12:05) [22]2Digitman - Приношу свои извинения всё дело было какраз в том про то-что ты говорил только ставить надо было
PROCESS_ALL_ACCESS
← →
Digitman © (2004-07-22 12:12) [23]
> ставить надо было
> PROCESS_ALL_ACCESS
а накой ляд тебе полный доступ, если тебе нужно только чтение вирт.памяти ?
Страницы: 1 вся ветка
Форум: "Основная";
Текущий архив: 2004.08.08;
Скачать: [xml.tar.bz2];
Память: 0.53 MB
Время: 0.031 c