Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Delphi программирование > Общие вопросы Delphi
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 22.04.2012, 03:20   #1
-Jack-
Форумчанин
 
Регистрация: 19.04.2009
Сообщений: 368
Смех Творческая работа с командной строкой

Всем доброго времени суток. У меня появился вопрос по поводу воплощения идеи из разряда творческий идиотизм.

Вопрос такой: возможно ли написать программу,
1. которая будет считывать данные появляющиеся в командной строке (cmd )
2. которая будет вводить туда необходимую информацию ( это в принципе намного легче )


Если ест у кого какие идеи, буду рад с ними ознакомиться )))

Последний раз редактировалось -Jack-; 22.04.2012 в 03:22.
-Jack- вне форума Ответить с цитированием
Старый 22.04.2012, 11:18   #2
Stilet
Белик Виталий :)
Старожил
 
Аватар для Stilet
 
Регистрация: 23.07.2007
Сообщений: 57,097
По умолчанию

Как вариант через пайпы: http://yandex.ua/yandsearch?text=Exe...oc=10&lr=20554
I'm learning to live...
Stilet вне форума Ответить с цитированием
Старый 22.04.2012, 14:54   #3
-Jack-
Форумчанин
 
Регистрация: 19.04.2009
Сообщений: 368
По умолчанию

Нашёл вот такую заготовочку, правда не совсем понял принцип её работы

Моя программа состоит из батника и исполняемого файла. При запуске батника, открывается командная строка и в неё происходят все действия.


Код:
unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls;

type
  TForm1 = class(TForm)
    Button1: TButton;
    Memo1: TMemo;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

procedure ExecConsoleApp(CommandLine: AnsiString; Output: TStringList; Errors:   
  TStringList);
var  
  sa: TSECURITYATTRIBUTES;   
  si: TSTARTUPINFO;   
  pi: TPROCESSINFORMATION;   
  hPipeOutputRead: THANDLE;   
  hPipeOutputWrite: THANDLE;   
  hPipeErrorsRead: THANDLE;   
  hPipeErrorsWrite: THANDLE;   
  Res, bTest: Boolean;   
  env: array[0..100] of Char;   
  szBuffer: array[0..256] of Char;
  dwNumberOfBytesRead: DWORD;   
  Stream: TMemoryStream;   
begin  
  sa.nLength := sizeof(sa);   
  sa.bInheritHandle := true;   
  sa.lpSecurityDescriptor := nil;   
  CreatePipe(hPipeOutputRead, hPipeOutputWrite, @sa, 0);   
  CreatePipe(hPipeErrorsRead, hPipeErrorsWrite, @sa, 0);   
  ZeroMemory(@env, SizeOf(env));   
  ZeroMemory(@si, SizeOf(si));   
  ZeroMemory(@pi, SizeOf(pi));   
  si.cb := SizeOf(si);   
  si.dwFlags := STARTF_USESHOWWINDOW or STARTF_USESTDHANDLES;   
  si.wShowWindow := SW_HIDE;
  si.hStdInput := 0;   
  si.hStdOutput := hPipeOutputWrite;   
  si.hStdError := hPipeErrorsWrite;   
    
  (* Remember that if you want to execute an app with no parameters you nil the  
     second parameter and use the first, you can also leave it as is with no  
     problems.                                                                 *)  
  Res := CreateProcess(nil, pchar(CommandLine), nil, nil, true,   
    CREATE_NEW_CONSOLE or NORMAL_PRIORITY_CLASS, @env, nil, si, pi);   
    
  // Procedure will exit if CreateProcess fail   
  if not Res then  
  begin  
    CloseHandle(hPipeOutputRead);
    CloseHandle(hPipeOutputWrite);   
    CloseHandle(hPipeErrorsRead);   
    CloseHandle(hPipeErrorsWrite);   
    Exit;   
  end;   
  CloseHandle(hPipeOutputWrite);   
  CloseHandle(hPipeErrorsWrite);   
    
  //Read output pipe   
  Stream := TMemoryStream.Create;   
  try  
    while true do  
    begin  
      bTest := ReadFile(hPipeOutputRead, szBuffer, 256, dwNumberOfBytesRead,
        nil);   
      if not bTest then  
      begin  
        break;   
      end;   
      Stream.Write(szBuffer, dwNumberOfBytesRead);   
    end;   
    Stream.Position := 0;   
    Output.LoadFromStream(Stream);   
  finally  
    Stream.Free;   
  end;   
    
  //Read error pipe
  Stream := TMemoryStream.Create;   
  try  
    while true do  
    begin  
      bTest := ReadFile(hPipeErrorsRead, szBuffer, 256, dwNumberOfBytesRead,   
        nil);   
      if not bTest then  
      begin  
        break;   
      end;   
      Stream.Write(szBuffer, dwNumberOfBytesRead);   
    end;   
    Stream.Position := 0;   
    Errors.LoadFromStream(Stream);
  finally
    Stream.Free;
  end;

  WaitForSingleObject(pi.hProcess, INFINITE);
  CloseHandle(pi.hProcess);
  CloseHandle(hPipeOutputRead);
  CloseHandle(hPipeErrorsRead);
end;


procedure TForm1.Button1Click(Sender: TObject);
var
  OutP: TStringList;
  ErrorP: TStringList;
begin
  OutP := TStringList.Create;
  ErrorP := TstringList.Create;

  ExecConsoleApp('cmd.exe', OutP, ErrorP);
  Memo1.Lines.Assign(OutP);

  OutP.Free;
  ErrorP.Free;
end;

end.
-Jack- вне форума Ответить с цитированием
Старый 22.04.2012, 15:05   #4
Stilet
Белик Виталий :)
Старожил
 
Аватар для Stilet
 
Регистрация: 23.07.2007
Сообщений: 57,097
По умолчанию

Принцип работы - перенаправить стандартный поток ввода вывода в определенный тобой контейнер. Тобишь все что должно попадать в консоль, будет попадать в OutP.
Таким образом к примеру можно в Мемо вывести все что консольная программа выводит.
I'm learning to live...
Stilet вне форума Ответить с цитированием
Старый 22.04.2012, 15:40   #5
-Jack-
Форумчанин
 
Регистрация: 19.04.2009
Сообщений: 368
По умолчанию

Цитата:
Сообщение от Stilet Посмотреть сообщение
Принцип работы - перенаправить стандартный поток ввода вывода в определенный тобой контейнер. Тобишь все что должно попадать в консоль, будет попадать в OutP.
Таким образом к примеру можно в Мемо вывести все что консольная программа выводит.
Ну то что OutP выводится в Memo это видно))) Мне не совсем понятно то, каким образом этот скрипт подправить под мою ситуацию, или я его просто-на-проста как то не так использую )
-Jack- вне форума Ответить с цитированием
Старый 25.04.2012, 03:53   #6
-Jack-
Форумчанин
 
Регистрация: 19.04.2009
Сообщений: 368
По умолчанию

Эм ... Народ, кто может помочь, как этот код должен работать ??? )))

Каким образом он перехватывает ? Нужно ли подкорректировать код для моего случая ? что именно подправить ?
-Jack- вне форума Ответить с цитированием
Старый 26.04.2012, 17:54   #7
Stilet
Белик Виталий :)
Старожил
 
Аватар для Stilet
 
Регистрация: 23.07.2007
Сообщений: 57,097
По умолчанию

Поскольку сей пример я скомуниздил на заре столетия у... Не помню точно, кажись у Александра Багеля, причем не особо разбираясь как он работает, сказать могу только одно: Тебе нужно попробовать добавить выгрузку твоих данных в эту консоль.
Создать еще один пайп
Код:
CreatePipe(hPipeWrite, hPipeWrite, @sa, 0);
Указать его для процесса:
Код:
si.hStdInput := 0;
И сделать еще один Stream подобный тем что в примере.
I'm learning to live...
Stilet вне форума Ответить с цитированием
Старый 26.04.2012, 18:17   #8
-Jack-
Форумчанин
 
Регистрация: 19.04.2009
Сообщений: 368
По умолчанию

Да я уже раздобыл другой код, который работает )))
Вот, если кому пригодится
Код:
procedure RunDosInMemo(CmdLine: string; AMemo: TMemo);
const
  ReadBuffer = 2400;
var
  Security: TSecurityAttributes;
  ReadPipe, WritePipe: THandle;
  start: TStartUpInfo;
  ProcessInfo: TProcessInformation;
  Buffer: Pchar;
  BytesRead: DWord;
  Apprunning: DWord;
begin
  Screen.Cursor := CrHourGlass;
  Form1.Button1.Enabled := False;
  with Security do
  begin
    nlength := SizeOf(TSecurityAttributes);
    binherithandle := true;
    lpsecuritydescriptor := nil;
  end;
  if Createpipe(ReadPipe, WritePipe,
    @Security, 0) then
  begin
    Buffer := AllocMem(ReadBuffer + 1);
    FillChar(Start, Sizeof(Start), #0);
    start.cb := SizeOf(start);
    start.hStdOutput := WritePipe;
    start.hStdInput := ReadPipe;
    start.dwFlags := STARTF_USESTDHANDLES +
      STARTF_USESHOWWINDOW;
    start.wShowWindow := SW_HIDE;

    if CreateProcess(nil,
      PChar(CmdLine),
      @Security,
      @Security,
      true,
      NORMAL_PRIORITY_CLASS,
      nil,
      nil,
      start,
      ProcessInfo) then
    begin
      repeat
        Apprunning := WaitForSingleObject
          (ProcessInfo.hProcess, 100);
        ReadFile(ReadPipe, Buffer[0],
          ReadBuffer, BytesRead, nil);
        Buffer[BytesRead] := #0;
        OemToAnsi(Buffer, Buffer);
        AMemo.Text := AMemo.text + string(Buffer);

        Application.ProcessMessages;
      until (Apprunning <> WAIT_TIMEOUT);
    end;
    FreeMem(Buffer);
    CloseHandle(ProcessInfo.hProcess);
    CloseHandle(ProcessInfo.hThread);
    CloseHandle(ReadPipe);
    CloseHandle(WritePipe);
  end;
  Screen.Cursor := CrDefault;
  Form1.Button1.Enabled := True;
end;

procedure TForm1.Button1Click(Sender: TObject);
begin
  Memo1.Clear;
  RunDosInMemo('java -Xmx1536M -Xms1536M -Dfile.encoding=UTF-8 -jar program.jar', Memo1);
end;

Последний раз редактировалось -Jack-; 26.04.2012 в 22:29.
-Jack- вне форума Ответить с цитированием
Старый 26.04.2012, 22:30   #9
-Jack-
Форумчанин
 
Регистрация: 19.04.2009
Сообщений: 368
По умолчанию

Только вот теперь другая проблемка ... С перехватом вывода разобрались, но вопрос теперь по отправке данных, команды и т.п.
-Jack- вне форума Ответить с цитированием
Старый 30.04.2012, 04:10   #10
-Jack-
Форумчанин
 
Регистрация: 19.04.2009
Сообщений: 368
По умолчанию

Ну что, кто нибудь сможет помочь с кодом для отправки команд консольному приложению ????
-Jack- вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Проблема с командной строкой Skydream Общие вопросы C/C++ 23 15.08.2009 18:54
Помогите С командной строкой manax Помощь студентам 6 08.11.2008 18:03
Помогите с командной строкой ARES-IVAN Помощь студентам 3 02.11.2008 19:22
Работа с командной строкой lyryks Помощь студентам 2 16.11.2007 13:06
Работа в Делфи с командной строкой Noor Общие вопросы Delphi 6 30.12.2006 12:49