Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Начинающим";
Текущий архив: 2007.06.10;
Скачать: [xml.tar.bz2];

Вниз

Запуск консольного приложения из программы.   Найти похожие ветки 

 
pathfinder ©   (2007-05-17 10:50) [0]

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


 
Сергей М. ©   (2007-05-17 11:03) [1]


> как запустить


см. CreateProcess


> получить код возврата


см. WaitForSingleObject + GetExitCodeProcess


 
pathfinder ©   (2007-05-17 12:35) [2]

нашел следующий код:

function Test_Prog( s : String; m : Uint) : Integer;
var
 lpprocessinformation : TProcessInformation;
 lpstartupinfo           : TStartUpInfo;
 p                          : array[0..254] of char;
 ExitCode                : DWord;
begin
 Result := -1;
 FillChar(lpstartupinfo, SizeOf(tstartupinfo), $00);
 with lpstartupinfo do
   begin
      lpdesktop   := nil;
      lptitle     := nil;
      dwflags     := STARTF_USESHOWWINDOW;
      wshowwindow := m;
   end;
 FillChar(p, sizeof(p), $00);
 StrPCopy(p, s);
 if CreateProcess(nil, P, nil, nil, False, CREATE_DEFAULT_ERROR_MODE, nil, nil,
    lpstartupInfo, lpprocessInformation) then
   begin
      WaitForSingleObject(lpprocessinformation.hprocess, infinite);
      GetExitCodeProcess (lpprocessinformation.hprocess, ExitCode);
      Result:=ExitCode;
      closehandle(lpprocessinformation.hprocess);
  end;
end;

Корректен ли он? Можно ли применять его в таком виде или лучше что-то исправить?

У меня возник вопрос по поводу параметра CreateProcess - dwCreationFlags. Какое значение там лучше указывать в моем случае?

И по поводу второго параметра WaitForSingleObject, не лучше ли задавать там таймаут?


 
ANB ©   (2007-05-17 12:57) [3]


> не лучше ли задавать там таймаут?

Если задать таймаут, то придется функцию вызывать в цикле с анализом ее результата.


 
Сергей М. ©   (2007-05-17 13:08) [4]


> по поводу параметра CreateProcess - dwCreationFlags. Какое
> значение там лучше указывать в моем случае?


В твоем случае это не принципиально. Можешь даже 0 указать.


> не лучше ли задавать там таймаут?


см. [3]


 
pathfinder ©   (2007-05-17 13:15) [5]

Спасибо.


 
Leonid Troyanovsky ©   (2007-05-17 13:30) [6]


> pathfinder ©   (17.05.07 12:35) [2]

> Корректен ли он? Можно ли применять его в таком виде или
> лучше что-то исправить?

В коде, по-крайней мере, 3 ошибки:
недостаточный размер p, (и, во-ще, все приседания с p лишние)
не задан lpstartupinfo.cb
не закрывается хендл потока.

--
Regards, LVT.


 
pathfinder ©   (2007-05-17 14:14) [7]


> недостаточный размер p, (и, во-ще, все приседания с p лишние)

т.е. вот так?

function Test_Prog( s : String; m : Uint) : Integer;
var
lpprocessinformation : TProcessInformation;
lpstartupinfo           : TStartUpInfo;
p                          : array[0..254] of char;
ExitCode                : DWord;
begin
Result := -1;
FillChar(lpstartupinfo, SizeOf(tstartupinfo), $00);
with lpstartupinfo do
  begin
     lpdesktop   := nil;
     lptitle     := nil;
     dwflags     := STARTF_USESHOWWINDOW;
     wshowwindow := m;
  end;
if CreateProcess(nil, PChar(s), nil, nil, False, CREATE_DEFAULT_ERROR_MODE, nil, nil,
   lpstartupInfo, lpprocessInformation) then
  begin
     WaitForSingleObject(lpprocessinformation.hprocess, infinite);
     GetExitCodeProcess (lpprocessinformation.hprocess, ExitCode);
     Result:=ExitCode;
     closehandle(lpprocessinformation.hprocess);
 end;
end;


> не закрывается хендл потока.

а closehandle(lpprocessinformation.hprocess); разве не закрывает?


 
Сергей М. ©   (2007-05-17 15:10) [8]


> losehandle(lpprocessinformation.hprocess); разве не закрывает?
>
>


Закрывает, но не хэндл потока, а хендл процесса.
А нужно еще закрыть хэндл потока (lpprocessinformation.hThread), в противном  случае это чревато утечкой ресурсов.


 
pathfinder ©   (2007-05-17 15:25) [9]

а в какой последовательности закрываются дескрипторы процесса и осн. потока?


 
Сергей М. ©   (2007-05-17 15:28) [10]


> pathfinder ©   (17.05.07 15:25) [9]


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


 
pathfinder ©   (2007-05-18 09:18) [11]

в итоге получилось следующее:

function ProgExec(s: String; m: Uint): Integer;
var
 ProcInfo  : TProcessInformation;
 StartInfo : TStartUpInfo;
 ExitCode  : DWord;
begin
 Result := -1;

 ZeroMemory(@StartInfo, SizeOf(StartInfo));
 ZeroMemory(@ProcInfo , SizeOf(ProcInfo ));

 with StartInfo do
   begin
      cb          := SizeOf(StartInfo);
      lpdesktop   := nil;
      lptitle     := nil;
      dwflags     := STARTF_USESHOWWINDOW;
      wshowwindow := m;
   end;

 if CreateProcess(nil,
                  PChar(s),
                  nil,
                  nil,
                  False,
                  0,
                  nil,
                  nil,
                  StartInfo,
                  ProcInfo
                  )
 then begin
        WaitForSingleObject(ProcInfo.hprocess, infinite);
        GetExitCodeProcess (ProcInfo.hprocess, ExitCode);
        Result:=ExitCode;
        closehandle(ProcInfo.hthread);
        closehandle(ProcInfo.hprocess);
      end;
end;

Подскажите пожалуйста, нет ли здесь ошибок?

И еще такой вопрос: какие поля структуры startupinfo необходимо инициализировать? В справке например инициализируется только cb.


 
pathfinder ©   (2007-05-18 09:20) [12]


> В справке например инициализируется только cb.


т.е. в примере который приведен в справке к делфи2006



Страницы: 1 вся ветка

Форум: "Начинающим";
Текущий архив: 2007.06.10;
Скачать: [xml.tar.bz2];

Наверх




Память: 0.48 MB
Время: 0.043 c
1-1176448717
mid
2007-04-13 11:18
2007.06.10
Экспорт в Excel


1-1176412599
Tack
2007-04-13 01:16
2007.06.10
Конвертирование текста в SGML (UTF-8) с кодированием спецсимволов


1-1176295641
[Salo] phantom
2007-04-11 16:47
2007.06.10
События формы


2-1179743066
dmdel
2007-05-21 14:24
2007.06.10
Richedit


2-1179517412
Konfetka
2007-05-18 23:43
2007.06.10
Дата





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский