Оболочка

Тема в разделе "Машинное отделение", создана пользователем Binary, 4 дек 2006.

  1. TopicStarter Overlay

    Binary Учаcтник

    • Участник
    Рег.:
    27.08.2006
    Сообщения:
    135
    Симпатии:
    0
    Репутация:
    0
    Адрес:
    Мытищи
    Оффлайн
    Тут на днях понадобилось что-то вроде оболочки для консольных программ наваять ...
    кто-нибудь может поведать как привязаться к произвольной консоли и считать - вписать в нее?

    WildCat вроде сделал GUI оболочку

    желательно код привести :D
  2. WildCat Коршунов Игорь

    • Команда форума
    Рег.:
    04.05.2006
    Сообщения:
    3.599
    Симпатии:
    4
    Репутация:
    0
    Адрес:
    Гомель
    Оффлайн
    В CreateProcess нужно указать какие потоки куда пристыковывать. По-типу так:
    Код:
      HANDLE e_read, e_write; // соединяются с движком
      STARTUPINFO si;
      memset(&si, 0, sizeof(si));
      si.cb = sizeof(si);
      si.hStdInput  = e_read;
      si.hStdOutput = e_write;
      si.hStdError  = e_write;
      si.dwFlags = STARTF_USESTDHANDLES;
    Вот пример как дальше с ними работать:
    Код:
    // послать сообщение движку
    void Engine::Send(char *s)
    {
      if (!ready) return;
      DWORD size;
      WriteFile(write, s, DWORD(strlen(s)), &size, 0);
      fprintf(fl, "> %s", s);
      fflush(fl);
    }
    
    // принять сообщение от движка
    // fl - это лог файл
    // buf - это буфер ввода, член класса Engine
    char *Engine::Get()
    {
      static char res[BUF_SIZE];
    
      do
      {
        char *p = strchr(buf, '\r');
        if (p)
        {
          *(p++) = 0;
          fprintf(fl, "%s\n", buf);
          fflush(fl);
          strcpy(res, buf);
          if (*p == '\n') p++;
          strcpy(buf, p);
          return res;
        }
    
        char b[BUF_SIZE];
        DWORD size;
        ReadFile(read, b, BUF_SIZE, &size, 0);
        b[size] = 0;
        strcat(buf, b);
      } while (1);
    
      return buf;
    }
  3. TopicStarter Overlay

    Binary Учаcтник

    • Участник
    Рег.:
    27.08.2006
    Сообщения:
    135
    Симпатии:
    0
    Репутация:
    0
    Адрес:
    Мытищи
    Оффлайн
    спасибо , WildCat , я знал , что ты поможешь :)
  4. WildCat Коршунов Игорь

    • Команда форума
    Рег.:
    04.05.2006
    Сообщения:
    3.599
    Симпатии:
    4
    Репутация:
    0
    Адрес:
    Гомель
    Оффлайн
    Еще забыл сказать, что read и write это хэндлы потоков, которые со стороны GUI.
  5. NS Нефёдов Сергей

    • Заслуженный
    • Ветеран
    • Старожил
    Рег.:
    02.05.2006
    Сообщения:
    6.811
    Симпатии:
    96
    Репутация:
    3
    Адрес:
    Санкт-Петербург
    Оффлайн
    Образец менеджера на Паскале (переходник для подмены контроля)

    program Menedger;

    {$APPTYPE CONSOLE}

    uses
    SysUtils,
    mmsystem,
    IniFiles,
    windows;
    var
    Ini: TIniFile;
    var NameDvig:pAnsiChar;
    Var tt:integer;
    VAR Stdin,stdout:Thandle;
    var
    sa: TSecurityAttributes;
    pi: TProcessInformation;
    si: TStartupInfo;
    StdOutPipeRead, StdOutPipeWrite,
    StdInPipeRead, StdInPipeWrite : THandle;
    var s,s1:string;
    function ReadNS(StdOutPipeRead:THandle):AnsiString;
    Var
    chBuf: Char; BufSize,i: DWORD; res:boolean; s:AnsiString;
    begin
    chbuf:=chr(0);
    BufSize:=0;
    sleep(1);
    Res:=PeekNamedPipe(StdOutPipeRead, nil, 0, nil, @BufSize, nil);
    Res:=Res and (BufSize > 0);
    If Res Then
    while chbuf<>chr(10) do
    begin
    s:='';
    for I := 1 to Bufsize do
    Begin
    chBuf:=chr(0);
    ReadFile(StdOutPipeRead, chBuf, 1, BufSize, Nil);
    if chBuf>chr(13) then s:=s+chBuf;
    if chBuf=Chr(10) then break;
    end;
    Result:=s;
    end
    Else
    Result:='';
    end;
    procedure WriteNS(Data: AnsiString;StdInPipeWrite:THandle);
    Var
    chBuf: PChar; BufSize,i: DWORD;
    begin
    chBuf:=PChar(Data+Chr($0D)+Chr($0A));
    BufSize:=Length(chBuf);
    WriteFile(StdInPipeWrite, chBuf^, BufSize, i, Nil);
    end;
    begin
    Ini := TIniFile.Create( ChangeFileExt( Paramstr(0), '.INI' ) );
    namedvig:=PAnsiChar(ini.ReadString('general','name',''));
    tt:=ini.Readinteger('general','time',100);
    sa.nLength := sizeof(sa);
    sa.bInheritHandle := TRUE;
    sa.lpSecurityDescriptor := nil;

    CreatePipe(StdOutPipeRead,StdOutPipeWrite,@SA,0);
    CreatePipe(StdInPipeRead,StdInPipeWrite,@SA,0);

    ZeroMemory(@SI, SizeOf(SI));
    SI.cb := sizeof(SI);
    SI.dwFlags := STARTF_USESHOWWINDOW or STARTF_USESTDHANDLES;
    SI.wShowWindow := SW_HIDE;
    SI.hStdInput := StdInPipeRead;
    SI.hStdOutput := StdOutPipeWrite;

    CreateProcess(nil,
    namedvig,
    nil,
    nil,
    TRUE,
    0,
    nil,
    nil,
    si,
    pi);

    StdIn:= GetStdHandle(STD_Output_HANDLE);
    StdOut:=GetStdHandle(STD_INPUT_HANDLE);
    s:='';
    s1:='';
    while s1<>'quit' do
    Begin
    sleep(1);
    s:=Trim(ReadNS(StdOutPipeRead));
    while s<>'' do
    begin
    writeNS(s,Stdin);
    s:='';
    s:=Trim(ReadNS(StdOutPipeRead));
    end;
    sleep(1);
    s1:=Trim(ReadNS(stdout));
    if length(s1)>3 then if (copy(s1,1,2)='go') then s1:='go movetime '+inttostr(tt);
    while s1<>'' do
    Begin
    writeNS(s1,StdInPipeWrite);
    s1:='';
    s1:=Trim(ReadNS(stdout));
    if length(s1)>3 then if (copy(s1,1,2)='go') then s1:='go movetime '+inttostr(tt);
    end;
    end;
    end.
  6. TopicStarter Overlay

    Binary Учаcтник

    • Участник
    Рег.:
    27.08.2006
    Сообщения:
    135
    Симпатии:
    0
    Репутация:
    0
    Адрес:
    Мытищи
    Оффлайн
    Код:
     STARTUPINFO si;
      PROCESS_INFORMATION pi;
    
      HANDLE read, write;
      char buf[BUF_SIZE];
      DWORD size;
    
      memset(&si, 0, sizeof(si));
      si.cb = sizeof(si);
      si.hStdInput  = &read;
      si.hStdOutput = &write;
      si.hStdError  = &write;
      si.dwFlags = STARTF_USESTDHANDLES;
    
        
        if( !CreateProcess(
            Edit1->Text.c_str(),   
            0, // Command line.
            NULL,             // Process handle not inheritable.
            NULL,             // Thread handle not inheritable.
            FALSE,            // Set handle inheritance to FALSE.
            0,                // No creation flags.
            NULL,             // Use parent's environment block.
            NULL,             // Use parent's starting directory.
            &si,              // Pointer to STARTUPINFO structure.
            &pi )             // Pointer to PROCESS_INFORMATION structure.
        )
        {
            ShowMessage( "CreateProcess failed " + IntToStr(GetLastError()));
        }
        else
        {
            ShowMessage( "OK " );
       
        char s[128] = "***!";
        WriteFile(read, s, DWORD(strlen(s)), &size, 0);
        WriteFile(write, s, DWORD(strlen(s)), &size, 0);    
    
        }
    собрал в Builder - e => В edit прописана моя прога , которую он находит , ее единственная функция - сканить
    входной поток и выводить его в MessageBox - подключил ее к Арене - работает , к этому коду - не работает ,
    в чем может быть лажа?!
  7. NS Нефёдов Сергей

    • Заслуженный
    • Ветеран
    • Старожил
    Рег.:
    02.05.2006
    Сообщения:
    6.811
    Симпатии:
    96
    Репутация:
    3
    Адрес:
    Санкт-Петербург
    Оффлайн
    Сразу - в конце команды должно быть Chr($0D)+Chr($0A)
  8. TopicStarter Overlay

    Binary Учаcтник

    • Участник
    Рег.:
    27.08.2006
    Сообщения:
    135
    Симпатии:
    0
    Репутация:
    0
    Адрес:
    Мытищи
    Оффлайн
    дописал
    Код:
        char s[128] = "***!";
        char end[3] = {0x0D,0x0A};
        strcat(s, end);
        WriteFile(write, s, DWORD(strlen(s)), &size, 0);
    все равно не пашет!
  9. NS Нефёдов Сергей

    • Заслуженный
    • Ветеран
    • Старожил
    Рег.:
    02.05.2006
    Сообщения:
    6.811
    Симпатии:
    96
    Репутация:
    3
    Адрес:
    Санкт-Петербург
    Оффлайн
    Сначала - неправильные параметры в CreateProcess,
    Не созданы Пайпы и т.д.
  10. NS Нефёдов Сергей

    • Заслуженный
    • Ветеран
    • Старожил
    Рег.:
    02.05.2006
    Сообщения:
    6.811
    Симпатии:
    96
    Репутация:
    3
    Адрес:
    Санкт-Петербург
    Оффлайн
  11. WildCat Коршунов Игорь

    • Команда форума
    Рег.:
    04.05.2006
    Сообщения:
    3.599
    Симпатии:
    4
    Репутация:
    0
    Адрес:
    Гомель
    Оффлайн
    Забыл создать трубы для чтения из потоков. Я думал сам догадаешься. Откуда ты думал read, write появяться?

    CreatePipe(&e_read, &write, &sa, 0);
    CreatePipe(&read, &e_write, &sa, 0);

    Кроме того создавать процесс нужно так:

    CreateProcess(exe, cmd, &sa, &sa, TRUE, DETACHED_PROCESS, 0, dir, &si, &pi)
  12. NS Нефёдов Сергей

    • Заслуженный
    • Ветеран
    • Старожил
    Рег.:
    02.05.2006
    Сообщения:
    6.811
    Симпатии:
    96
    Репутация:
    3
    Адрес:
    Санкт-Петербург
    Оффлайн
    Наверно лучше первым парметром задавать null, а вторым уже полностью строку запуска.
    Там более так рекомендует делать MSDN :)
  13. Mustitz Заслуженный

    • Заслуженный
    • Участник
    • Старожил
    Рег.:
    30.09.2006
    Сообщения:
    3.546
    Симпатии:
    1.265
    Репутация:
    36
    Адрес:
    Киев
    Оффлайн
    Для Delphi я когда-то написал компонент для общения с консольными программами, могу поделиться если надо. Приведенный код рабоатет только под Win 9x, потому что в нем не используются security attributes, а они в данном конкретном слуае нужны. У меня запуск процесса запись и чтение выглядят так:

    Код:
    procedure TConsoleIO.RunProcess(const CmdLine: string; CurrentDir: string = ''; ShowWindow: Boolean = False);
    var
      SA: TSecurityAttributes;
      SI: TStartupInfo;
      PI: TProcessInformation;
    
      InputWriteTmp: THandle;
      OutputReadTmp: THandle;
      ErrorReadTmp: THandle;
    
      ThreadId: Cardinal;
    begin
      SA.nLength := SizeOf(SA);
      SA.lpSecurityDescriptor := nil;
      SA.bInheritHandle := True;
    
      WinCheck(CreatePipe(InputReadPipe, InputWriteTmp, @SA, 0));
      WinCheck(CreatePipe(OutputReadTmp, OutputWritePipe, @SA, 0));
      WinCheck(CreatePipe(ErrorReadTmp, ErrorWritePipe, @SA, 0));
    
      InprocessDuplicateHandle(InputWriteTmp, InputWritePipe);
      InprocessDuplicateHandle(OutputReadTmp, OutputReadPipe);
      InprocessDuplicateHandle(ErrorReadTmp, ErrorReadPipe);
    
      CloseAndZeroHandle(InputWriteTmp);
      CloseAndZeroHandle(OutputReadTmp);
      CloseAndZeroHandle(ErrorReadTmp);
    
      FillChar(SI, SizeOf(SI), $00);
      SI.cb := SizeOf(SI);
      SI.dwFlags := STARTF_USESTDHANDLES or STARTF_USESHOWWINDOW;
      SI.hStdInput := InputReadPipe;
      SI.hStdOutput := OutputWritePipe;
      SI.hStdError := ErrorWritePipe;
      SI.wShowWindow := ToShowWindowArg(ShowWindow);
    
      WinCheck(CreateProcess(
        nil,
        PChar(CmdLine),
        @SA,
        nil,
        True,
        CREATE_NEW_CONSOLE,
        nil,
        ToPChar(CurrentDir),
        SI,
        PI));
    
      CloseAndZeroHandle(PI.hThread);
      ProcessHandle := PI.hProcess;
      BeginThread(nil, 0, @IOReadOutput, Self, 0, ThreadId);
      BeginThread(nil, 0, @IOReadError, Self, 0, ThreadId);
      BeginThread(nil, 0, @WaitProcess, Self, 0, ThreadId);
    end;
    
    procedure TConsoleIO.SendInput(Msg: string);
    var
      BytesWritten: Cardinal;
    begin
      Msg := Msg + SplitSendAvail;
      WinCheck(WriteFile(InputWritePipe, Msg[1], Length(Msg), BytesWritten, nil));
    end;
    
    procedure TConsoleIO.ReaderProc(Handle: THandle; MessageCode: Integer);
    var
      Buf: array[0..1024] of Char;
      BytesRead: Cardinal;
      Err: string;
    begin
      repeat
        if not ReadFile(Handle, Buf, SizeOf(Buf), BytesRead, nil) then
          try
            if not IsRunning then Exit;
            RaiseLastOSError;
          except
            on E: Exception do
            begin
              Err := E.Message;
              Windows.SendMessage(FWindowHandle, MIO_ERROR, Integer(PChar(Err)), Length(Err) + 1);
            end;
          end;
    
        if BytesRead > 0 then
          Windows.SendMessage(FWindowHandle, MessageCode, Integer(@Buf), BytesRead);
      until False;
    end;
  14. WildCat Коршунов Игорь

    • Команда форума
    Рег.:
    04.05.2006
    Сообщения:
    3.599
    Симпатии:
    4
    Репутация:
    0
    Адрес:
    Гомель
    Оффлайн
    А в чем прикол? И так вроде работает.
  15. NS Нефёдов Сергей

    • Заслуженный
    • Ветеран
    • Старожил
    Рег.:
    02.05.2006
    Сообщения:
    6.811
    Симпатии:
    96
    Репутация:
    3
    Адрес:
    Санкт-Петербург
    Оффлайн
    Не знаю :) Это лучше спросить у Майкрософт :)
  16. WildCat Коршунов Игорь

    • Команда форума
    Рег.:
    04.05.2006
    Сообщения:
    3.599
    Симпатии:
    4
    Репутация:
    0
    Адрес:
    Гомель
    Оффлайн
    Mustitz
    Если так делать ReaderProc(), то она за раз сразу будет выдавать по нескольку строк. Разбирайся потом в них :)
    К тому же может и разрывать строки. Сначала придет "This is a st".
    А потом "ring\n".

    Ну не до такой степени конечно :) Но все же.
  17. WildCat Коршунов Игорь

    • Команда форума
    Рег.:
    04.05.2006
    Сообщения:
    3.599
    Симпатии:
    4
    Репутация:
    0
    Адрес:
    Гомель
    Оффлайн
    program Menedger;

    Смотрю и думаю что же здесь не так :)
    Ага!
    Лучше так:

    program Manager;
  18. NS Нефёдов Сергей

    • Заслуженный
    • Ветеран
    • Старожил
    Рег.:
    02.05.2006
    Сообщения:
    6.811
    Симпатии:
    96
    Репутация:
    3
    Адрес:
    Санкт-Петербург
    Оффлайн
    Я когда начинал писать и участовать в олимпиадах - не знал ни одного английского слова, сейчас - могу читать технические тексты, но не могу написать ни одного слова без ошибки :)
    Поэтому если именую сам, и разработка не коллективная - всё называю рускими именами в английской транскрипции :)
  19. WildCat Коршунов Игорь

    • Команда форума
    Рег.:
    04.05.2006
    Сообщения:
    3.599
    Симпатии:
    4
    Репутация:
    0
    Адрес:
    Гомель
    Оффлайн
    Я в школе считал самым сложным писать английские слова. Никак не мог понять как можно угадывать из каких букв они состоят :lol:
  20. NS Нефёдов Сергей

    • Заслуженный
    • Ветеран
    • Старожил
    Рег.:
    02.05.2006
    Сообщения:
    6.811
    Симпатии:
    96
    Репутация:
    3
    Адрес:
    Санкт-Петербург
    Оффлайн
    У меня хуже - я начал влотно писать в 13 лет (понемногу начал раньше), при этом в школе изучал Французский.
    А в Университете - если очень большого желания не было то английский выучить было невозможно - в основном пичкали математикой, а в группе начинающих - и на Мат-мехе и на прикладной математике вообще не было английского! Нехватка преподавателей :)
  21. TopicStarter Overlay

    Binary Учаcтник

    • Участник
    Рег.:
    27.08.2006
    Сообщения:
    135
    Симпатии:
    0
    Репутация:
    0
    Адрес:
    Мытищи
    Оффлайн
    Код:
      STARTUPINFO si;
      PROCESS_INFORMATION pi;
    
      HANDLE read, write;
      HANDLE e_read, e_write;
      char buf[BUF_SIZE];
      DWORD size;
      SECURITY_ATTRIBUTES sa;
    
      sa.nLength = sizeof(SECURITY_ATTRIBUTES);
      sa.bInheritHandle = TRUE;
      sa.lpSecurityDescriptor = NULL;
    
      memset(&si, 0, sizeof(si));
      si.cb = sizeof(si);
      si.hStdInput  = &e_read;
      si.hStdOutput = &e_write;
      si.hStdError  = &e_write;
      si.dwFlags = STARTF_USESTDHANDLES;
    
      if(
          CreatePipe(&e_read, &write, &sa, 0) &&
          CreatePipe(&read, &e_write, &sa, 0)   )
    
              ShowMessage( "Pipe->OK " );
    
      SetHandleInformation( e_read, HANDLE_FLAG_INHERIT, 0);
      SetHandleInformation( e_write, HANDLE_FLAG_INHERIT, 0);
    
      if( !CreateProcess(
            0,                    // No module name (use command line).
            Edit1->Text.c_str(), // Command line.
            &sa,
            &sa,
            TRUE,              // Set handle inheritance to TRUE.
            DETACHED_PROCESS,
            0,                 // Use parent's environment block.
            0,                 // Use parent's starting directory.
            &si,               // Pointer to STARTUPINFO structure.
            &pi )              // Pointer to PROCESS_INFORMATION structure.
        )
        {
            ShowMessage( "CreateProcess failed " + IntToStr(GetLastError()));
        }
        else
        {
            ShowMessage( "OK " );
    
            char s[128] = "benchnm";
            char end[3] = {0x0D,0x0A};
            strcat(s, end);
    
            if(WriteFile(e_write, s, DWORD(strlen(s)), &size, 0))
                ShowMessage("WriteOK!");
    
             //if(ReadFile(e_read, buf, BUF_SIZE, &size, 0))
             //    ShowMessage(IntToStr(size)+" " + AnsiString(buf));
             //else
             //    ShowMessage("failed");
    
        }
    подопытная программа
    Код:
    int main(int argc, char* argv[])
    {
        char input[128];
        MessageBoxA(0, 0, "I was run!", MB_ICONWARNING);
    
        for(;;)
        {
              if (scanf("%s", input) == EOF)
                return 0;
                  MessageBoxA(0, 0, input, MB_ICONERROR);    
        };
        return 0;
    }
    результат - подопытная прога сообщает , что запущена , главная - что WriteFile вернул TRUE , но подопытная ничего не получает
    Такое ощущение , что я наму... намудрил с пайпами :(
  22. WinPooh В.М.

    • Команда форума
    Рег.:
    13.02.2006
    Сообщения:
    9.492
    Симпатии:
    3.122
    Репутация:
    95
    Адрес:
    Москва
    Оффлайн
    Может быть, стоит добавить \n в посылаемую строку - вдруг scanf() не понимает, что ввод закончен?
  23. TopicStarter Overlay

    Binary Учаcтник

    • Участник
    Рег.:
    27.08.2006
    Сообщения:
    135
    Симпатии:
    0
    Репутация:
    0
    Адрес:
    Мытищи
    Оффлайн
    пробовал и \n указать , хотя
    Код:
    char s[128] = "benchnm";
    char end[3] = {0x0D,0x0A};
    strcat(s, end);
    0x0D,0x0A - я так понимаю символы конца строки \n и \0 - если не напутал ничего
  24. WildCat Коршунов Игорь

    • Команда форума
    Рег.:
    04.05.2006
    Сообщения:
    3.599
    Симпатии:
    4
    Репутация:
    0
    Адрес:
    Гомель
    Оффлайн
    перевод строки + возврат каретки обозначаются так:

    char s[128] = "benchnm\n";
  25. WildCat Коршунов Игорь

    • Команда форума
    Рег.:
    04.05.2006
    Сообщения:
    3.599
    Симпатии:
    4
    Репутация:
    0
    Адрес:
    Гомель
    Оффлайн
    Кстати такая хрень может совсем глючить, т.к. в end[2] - лежит мусор, а что за ним дальше вообще неизвестно.
  26. WinPooh В.М.

    • Команда форума
    Рег.:
    13.02.2006
    Сообщения:
    9.492
    Симпатии:
    3.122
    Репутация:
    95
    Адрес:
    Москва
    Оффлайн
    \0 - это символ с кодом ноль, 0x00, а вовсе не 0x0a
  27. WinPooh В.М.

    • Команда форума
    Рег.:
    13.02.2006
    Сообщения:
    9.492
    Симпатии:
    3.122
    Репутация:
    95
    Адрес:
    Москва
    Оффлайн
    Ну да, более грамотно было бы написать:

    const char end[3] = "\n\r";

    Нулевой символ в конце строковой константы будет добавлен компилятором автоматически.

    P.S. Керниган-Ричи - рулез. Читайте, люди, Кернигана...
  28. WildCat Коршунов Игорь

    • Команда форума
    Рег.:
    04.05.2006
    Сообщения:
    3.599
    Симпатии:
    4
    Репутация:
    0
    Адрес:
    Гомель
    Оффлайн
    Лучше делать так:
    SECURITY_ATTRIBUTES sa;
    memset(&sa, 0, sizeof(sa));
    sa.nLength = sizeof(sa);
    sa.bInheritHandle = TRUE;

    И еще я не использую SetHandleInformation().
  29. WildCat Коршунов Игорь

    • Команда форума
    Рег.:
    04.05.2006
    Сообщения:
    3.599
    Симпатии:
    4
    Репутация:
    0
    Адрес:
    Гомель
    Оффлайн
    Это три символа: перевод строки + возврат каретки + еще один возврат каретки.
    \r - лишний.
  30. WinPooh В.М.

    • Команда форума
    Рег.:
    13.02.2006
    Сообщения:
    9.492
    Симпатии:
    3.122
    Репутация:
    95
    Адрес:
    Москва
    Оффлайн
    Знающие люди вообще советуют держаться от scanf() и компании подальше, если только не нужна её специфическая функциональность по разбору форматов.

    Простых вызовов read()/write() в 99% случаев вполне достаточно (рассматриваемый явно из их числа).
  31. WinPooh В.М.

    • Команда форума
    Рег.:
    13.02.2006
    Сообщения:
    9.492
    Симпатии:
    3.122
    Репутация:
    95
    Адрес:
    Москва
    Оффлайн
  32. TopicStarter Overlay

    Binary Учаcтник

    • Участник
    Рег.:
    27.08.2006
    Сообщения:
    135
    Симпатии:
    0
    Репутация:
    0
    Адрес:
    Мытищи
    Оффлайн
    продолжаю долбаться нал этой хренью :) ... теперь она работает наполовину
    Код:
        STARTUPINFO         sui;
        PROCESS_INFORMATION pi;
        SECURITY_ATTRIBUTES sa ;
    
        DWORD            dw_readed,
                         err = 0;
    
        sa.nLength                  = sizeof(sa);
        sa.lpSecurityDescriptor     = NULL;
        sa.bInheritHandle           = true;
    
        if(OpenDialog1->Execute())
        {
            ZeroMemory(ch_buffer, 6000);
            err = GetLastError();
            Memo1->Lines->Strings[0] = OpenDialog1->FileName;
    
    // Главный баг : если закомментировать один из
    // CreatePipe() , то программа работает
    // В противном случае - зависает!
    
            CreatePipe(&e_read_handle, &write_handle, &sa , 3000);
    //ShowMessage(IntToStr(err));
            CreatePipe(&read_handle, &e_write_handle, &sa , 3000);
    //ShowMessage(IntToStr(err));
    
            err = GetLastError();
    
            ZeroMemory(&sui, sizeof(sui));
    
            sui.cb          = sizeof(sui);
            sui.dwFlags     = STARTF_USESHOWWINDOW | STARTF_USESTDHANDLES;
            sui.wShowWindow = SW_HIDE;
    
            sui.hStdOutput  = write_handle;
            sui.hStdError   = write_handle;
            sui.hStdInput   = read_handle;
    
    //ShowMessage("done1");
    //ShowMessage(IntToStr(err));
    
            CreateProcess(0,
                          OpenDialog1->FileName.c_str(),
                          0,
                          0,
                          true,
                          0,
                          0,
                          0,
                          &sui,
                          &pi
                          );
    
            err = GetLastError();
    
            Sleep(250);
     //ShowMessage(IntToStr(err));
    
            ReadFile(e_read_handle, ch_buffer, 300, &dw_readed, 0);
            Memo1->Lines->Strings[1] = ch_buffer;
     //ShowMessage("done2");
            Sleep(150);
            WriteFile(e_write_handle, "bench", 300, &dw_readed, 0);
    
     //ShowMessage("done3");
    
        }
    не понимаю , почему винда не дает работать 2 пайпам!?
  33. atoku Модератор

    • Команда форума
    Рег.:
    05.02.2006
    Сообщения:
    2.949
    Симпатии:
    9
    Репутация:
    0
    Адрес:
    USA
    Оффлайн
    Ребят, разве в винде ЕСТЬ ПАЙПЫ? ;)
  34. WinPooh В.М.

    • Команда форума
    Рег.:
    13.02.2006
    Сообщения:
    9.492
    Симпатии:
    3.122
    Репутация:
    95
    Адрес:
    Москва
    Оффлайн
    Есть, конечно. См. файл win32.cpp из Греки.
    Что, по-твоему, делает функция PeekNamedPipe() из <windows.h> ? :)
  35. atoku Модератор

    • Команда форума
    Рег.:
    05.02.2006
    Сообщения:
    2.949
    Симпатии:
    9
    Репутация:
    0
    Адрес:
    USA
    Оффлайн
    Насколько я помнил, в винде были какие-то заморочки с пайпами. Но я уже забыл в чем была проблема. Давно не программировал под винду.

Поделиться этой страницей