Конференция "WinAPI" » Узнать хендлы открытых процессом файлов [D6, WinXP]
 
  • Виталий (10.04.08 14:57) [0]
    Уважаемые мастера, подскажите пожалуйста как по номеру процесса получить хендлы и пути файлов, которые он открыл?
    Если можно скажите какая последовательность вызовов функций  должна быть и какие точно функции для этого нужны

    Заранее спасибо.
  • Виталий (10.04.08 14:57) [1]
    О еще, может процессы где то в себе держат этот список, как его получить?
  • Сергей М. © (10.04.08 15:12) [2]
    И что ты с ними намерен делать ?

    Ты их потерял что ли ?)
  • Виталий (10.04.08 15:43) [3]
    Я хочу программно получить путь к файлу который открыт в Ворде.
    Я запускаю свою программу нахожу процесс WinWord и хочу увидеть какой файл(ы) он открыл
  • Виталий (10.04.08 15:43) [4]
    Это для сбора информации кто какой пользователь с чем работает
  • Сергей М. © (10.04.08 16:14) [5]
    Ты в курсе, что WinWord являет собой полноценный сервер OLE-автоматизации, (который способен сам сообщить о файлах, с которыми он работает, если его об этом спросят на его языке) ?

    Или ты про такую слыхом не слыхивал ?
  • Виталий (10.04.08 16:36) [6]
    В курсе, только мне не только ВинОфис нужно отлавливать а любую программу, окно которой активно в данный момент. Ворд это я к примеру.
    Ладно Ворд не нравится, возьмем Сполайт. Он то не сообщит о себе.

    Ты лучше скажи знаеш как это делать или как всегда в гугль идти?
  • Сергей М. © (10.04.08 16:40) [7]
    Ну раз ты на ходу меняешь формулировку задачи, то как всегда)
  • Riply © (10.04.08 17:21) [8]
    > [0] Виталий   (10.04.08 14:57)
    > подскажите пожалуйста как по номеру процесса получить хендлы и пути файлов, которые он открыл?

    Попробуй с помощью следующих функций:

    NtQuerySystemInformation(..,SystemHandleInformation,..)
    DuplicateHandle
    NtQueryObject

    P.S.
    Возможно, вместо NtQuerySystemInformation, можно использовать NtQueryInformationProcess для конкретного процесса.
    Не знаю, надо смотреть.
  • Riply © (10.04.08 17:22) [9]
    >  [8] Riply ©   (10.04.08 17:21)

    P.P.S.
    Будь осторожен с Pipe -ми :)
  • slow!alfamoon!com (10.04.08 18:14) [10]
    Riply: вроде проблема с пайпами в сп2 решилась, или я неправильно помню?
    Автор: http://slow.alfamoon.com/?module=filesdb&id=1&fid=12&get=1 только тут про сокеты, это тоже файлы, и для всех процессов, так что добавишь фильтрацию по PID нужного процесса
  • Riply © (10.04.08 22:04) [11]
    > [10] slow!alfamoon!com   (10.04.08 18:14)
    > Riply: вроде проблема с пайпами в сп2 решилась, или я неправильно помню?

    Давно это было, но до сих пор пайповая проблемма сидит у меня в голове с меткой "не решенная" :)
    Напомни, пожалуйста, на основании чего ты считаешь, что она решилась ?
  • Виталий (11.04.08 12:47) [12]
    Riply, slow!alfamoon!com - Спасибо за примеры. хоть кто-то не издевается, оказывается есть еще тут нормальные люди.

    Собсно почитал МС-Рема и Багеля, и решил проблему. Кстати Пайпы меня не интересуют, только физические файлы.
  • Rouse_ © (11.04.08 15:50) [13]
    С пайпами проблема не решилась :) Как висели так и висят :) Надо просто уметь их идентифицировать :)
  • slow!alfamoon!com (11.04.08 15:57) [14]

    > Напомни, пожалуйста, на основании чего ты считаешь, что
    > она решилась ?
    >

    в каком-то обсуждении на wasm.ru вроде пробегало, надо посмотреть будет.
  • Riply © (11.04.08 16:34) [15]
    > [13] Rouse_ ©   (11.04.08 15:50)
    > С пайпами проблема не решилась :) Как висели так и висят :) Надо просто уметь их идентифицировать :)

    Сколько не билась над их идентификацией (имея на руках только информацию от NtQuerySystemInformation), ничего у меня не вышло :(.
    На самом незначительном запросе - висла.
    Саш, подскажи как надо делать.
  • slow!alfamoon!com (11.04.08 16:36) [16]
    2 Riply собственно вариант решения это запрос в отдельном потоке, был предложен еще давно и ничего нового не придумано
  • Riply © (11.04.08 16:42) [17]
    > [16] slow!alfamoon!com   (11.04.08 16:36)
    > 2 Riply собственно вариант решения это запрос в отдельном потоке,
    > был предложен еще давно и ничего нового не придумано

    Терминирование нити ?
    Я не считаю это за "вариант решения". IMHO, так некузяво, что дальше некуда :)
    Кто-то из форумчан хорошо по этому поводу сказал: "Ведь по живому режешь".
    Я с ним согласна :)
  • Rouse_ © (11.04.08 16:46) [18]

    > Riply ©   (11.04.08 16:34) [15]

    Т.к. нужно искать только файловые хэндлы, то перед вызовом NtQueryObject нужно сказать NtQueryInformationFile и проверить результат, если STATUS_SUCCESS, то повиснуть не должны ;)
    Т.е. что-то вроде этого:

     function GetFileNameThread(lpParameters: Pointer): DWORD; stdcall;
     var
       FileNameInfo: FILE_NAME_INFORMATION;
       ObjectNameInfo: TOBJECT_NAME_INFORMATION;
       IoStatusBlock: IO_STATUS_BLOCK;
       pThreadParam: TGetFileNameThreadParam;
       dwReturn: DWORD;
     begin
       ZeroMemory(@FileNameInfo, SizeOf(FILE_NAME_INFORMATION));
       pThreadParam := PGetFileNameThreadParam(lpParameters)^;
       Result := NtQueryInformationFile(pThreadParam.hFile, @IoStatusBlock,
         @FileNameInfo, MAX_PATH * 2, FileNameInformation);
       if Result = STATUS_SUCCESS then
       begin
         Result := NtQueryObject(pThreadParam.hFile, ObjectNameInformation,
           @ObjectNameInfo, MAX_PATH * 2, @dwReturn);
         if Result = STATUS_SUCCESS then
         begin
           pThreadParam.Status := Result;
           WideCharToMultiByte(CP_ACP, 0,
             @ObjectNameInfo.Name.Buffer[ObjectNameInfo.Name.MaximumLength -
             ObjectNameInfo.Name.Length],
             ObjectNameInfo.Name.Length, @pThreadParam.Data[0],
             MAX_PATH, nil, nil);
         end
         else
         begin
           pThreadParam.Status := STATUS_SUCCESS;
           Result := STATUS_SUCCESS;
           WideCharToMultiByte(CP_ACP, 0,
             @FileNameInfo.FileName[0], IoStatusBlock.Information,
             @pThreadParam.Data[0],
             MAX_PATH, nil, nil);
         end;
       end;
       PGetFileNameThreadParam(lpParameters)^ := pThreadParam;
       ExitThread(Result);
     end;

     function GetFileNameFromHandle(hFile: THandle): String;
     var
       lpExitCode: DWORD;
       pThreadParam: TGetFileNameThreadParam;
       hThread: THandle;
     begin
       Result := '';
       ZeroMemory(@pThreadParam, SizeOf(TGetFileNameThreadParam));
       pThreadParam.hFile := hFile;
       hThread := CreateThread(nil, 0, @GetFileNameThread, @pThreadParam, 0, PDWORD(nil)^);
       if hThread <> 0 then
       try
         case WaitForSingleObject(hThread, 100) of
           WAIT_OBJECT_0:
           begin
             GetExitCodeThread(hThread, lpExitCode);
             if lpExitCode = STATUS_SUCCESS then
               Result := pThreadParam.Data;
           end;
           WAIT_TIMEOUT:
             TerminateThread(hThread, 0);
         end;
       finally
         CloseHandle(hThread);
       end;
     end;



    Я ж тебе помоемому давал уже этот код...
  • slow!alfamoon!com (11.04.08 17:02) [19]
    2 Rouse_
    NtQueryObject тоже виснет. На wasm.ru обсуждали

    http://www.wasm.ru/forum/viewtopic.php?id=7728
 
Конференция "WinAPI" » Узнать хендлы открытых процессом файлов [D6, WinXP]
Есть новые Нет новых   [134433   +22][b:0][p:0.002]