title: Two way parent child communication in windows with c++
body: <p><strong>Scroll down to see new update</strong></p>
  
  <p><strong>Update::
  In other word: I want to launch another program in the manner of a shell on Windows.</strong></p>
  
  <p>Need a two way communication between parent and child process using c++ on Windows. The parent is my program and the child is a random console application (like mysql terminal).</p>
  
  <p>It's been a couple days searching but couldn't find any working solution for Windows. Also MS documentations is not helping.</p>
  
  <p>Here i got a sample code from a question asked three years ago. How can i translate the code to Microsoft specific api and use it on Windows?</p>
  
  <pre><code>#include &lt;unistd.h&gt;
  #include &lt;stdlib.h&gt;
  #include &lt;stdio.h&gt;
  #include &lt;string.h&gt;
  #include &lt;errno.h&gt;
  
  #define Read            0
  #define Write           1
  #define ParentRead      read_pipe[1]
  #define ParentWrite     write_pipe[0]
  #define ChildRead       write_pipe[1]
  #define ChildWrite      read_pipe[0]
  
  int main()
  {
  int data_processed;
  
  /** Pipe for reading for subprocess */
  int read_pipe[2];
  /** Pipe for writing to subprocess */
  int write_pipe[2];
  
  char buffer[100];
  memset(buffer, '\0', 100);
  
  if (pipe(read_pipe) == 0 &amp;&amp; pipe(write_pipe) == 0)
  {
      pid_t pid = fork();
      if (pid == (pid_t)-1)
      {
          fprintf(stderr, "Fork failure");
          exit(EXIT_FAILURE);
      }
      else if (pid == (pid_t)0) //Child process
      {
          close(Read);
          close(Write);
          close(ParentRead);
          close(ParentWrite);
          dup(ChildRead);
          dup(ChildWrite);
          execlp("cat", (char*)NULL);
          exit(EXIT_FAILURE);
      }
      else { //Parent process
          close(ChildRead);
          close(ChildWrite);
  
          write(ParentWrite, "abc", 3);
          int r = read(ParentRead, buffer, 99);
          printf("%d %d", r, errno);
          puts(buffer);
      }
  }
  
  exit(EXIT_SUCCESS);
  }
  </code></pre>
  
  <p><strong>New Update:</strong></p>
  
  <p>So based on <a href="https://msdn.microsoft.com/en-us/library/windows/desktop/ms682499(v=vs.85).aspx" rel="nofollow">this sample</a> I wrote a modified version of the sample code and seems to be OK except that the redirected output is not what it's supposed to be. Here's the code:</p>
  
  <pre><code>#include &lt;iostream&gt;
  #include &lt;Windows.h&gt;
  #include &lt;string&gt;
  
  HANDLE hSTD_IN_READ = NULL;
  HANDLE hSTD_IN_WRITE = NULL;
  HANDLE hSTD_OUT_READ = NULL;
  HANDLE hSTD_OUT_WRITE = NULL;
  
  void WriteToPipe(std::string);
  void ReadFromPipe();
  
  
  int main()
  {
      SECURITY_ATTRIBUTES sa;
  
      std::cout &lt;&lt; "\nStart of parent execution: ";
  
      // Set the bInheritHandle flag so pipe handles are inherited. 
  
      sa.nLength = sizeof(SECURITY_ATTRIBUTES);
      sa.bInheritHandle = TRUE;
      sa.lpSecurityDescriptor = NULL;
  
      // Create pip for child process stdout
      if (!CreatePipe(&amp;hSTD_OUT_READ, &amp;hSTD_OUT_WRITE, &amp;sa, 0)) {
          std::cout &lt;&lt; "Error: CreatePipe STDOUT.\n";
          return -1;
      }
      // Ensure the read handle to the pipe for stdout is not inherited.
      if (!SetHandleInformation(hSTD_OUT_READ, HANDLE_FLAG_INHERIT, 0)) {
          std::cout &lt;&lt; "Error: STD_OUT_READ CreatePipe.\n";
          return -1;
      }
      // Create pipe for child process's stdin
      if (!CreatePipe(&amp;hSTD_IN_READ, &amp;hSTD_IN_WRITE, &amp;sa, 0)) {
          std::cout &lt;&lt; "Error: CreatePipe STDIN.\n";
          return -1;
      }
      // Ensure the write handle to the pipe for STDIN is not inherited. 
      if (!SetHandleInformation(hSTD_IN_WRITE, HANDLE_FLAG_INHERIT, 0)) {
          std::cout &lt;&lt; "Error: STD_IN_WRITE CreatePipe.\n";
          return -1;
      }
      // Create Child Process
  
      STARTUPINFO si;
      PROCESS_INFORMATION pi;
      BOOL bSuccess = FALSE;
  
      ZeroMemory(&amp;pi, sizeof(PROCESS_INFORMATION));
  
      ZeroMemory(&amp;si, sizeof(STARTUPINFO));
      // This structure specifies the STDIN and STDOUT handles for redirection.
      si.cb = sizeof(STARTUPINFO);
      si.hStdError = hSTD_OUT_WRITE;
      si.hStdInput = hSTD_IN_READ;
      si.hStdOutput = hSTD_OUT_WRITE;
      si.dwFlags |= STARTF_USESTDHANDLES;
  
      bSuccess = CreateProcess(TEXT("c:\\sqlite3.exe"), NULL, NULL, NULL, TRUE, 0, NULL, NULL, &amp;si, &amp;pi);
      if (!bSuccess) {
          std::cout &lt;&lt; "Error in CreateProcess.\n";
          return -1;
      }
      else {
  
          CloseHandle(pi.hProcess);
          CloseHandle(pi.hThread);
      }
  
      // Now execute your command then read the child process's output.
      WriteToPipe(".databases");
      ReadFromPipe();
  
      std::cout &lt;&lt; "End of program.\n";
      return 0;
  }
  
  void WriteToPipe(std::string buffer)
  {
      DWORD bWritten, BUFFSIZE = buffer.size();
      BOOL bSuccess = FALSE;
  
  
          bSuccess = WriteFile(hSTD_IN_WRITE, buffer.c_str(), BUFFSIZE, &amp;bWritten, NULL);
          if (!bSuccess)
              std::cout &lt;&lt; "WritetoPipe::Couldn't Write to std_in_write.\n";
  
          // Close the pipe handle so the child process stops reading.
          if (!CloseHandle(hSTD_IN_WRITE))
              std::cout &lt;&lt; "WriteToPipe::Couldn't close the handle after Writing to std_in_write.\n";
      }
  
  void ReadFromPipe()
  {
      DWORD bRead, bWritten;
      const DWORD BUFFSIZE = 4096;
      CHAR buffer[BUFFSIZE];
      BOOL bSuccess = FALSE;
      HANDLE hPARENT_STD_OUT = GetStdHandle(STD_OUTPUT_HANDLE);
  
      for (;;) {
          bSuccess = ReadFile(hSTD_OUT_READ, buffer, BUFFSIZE, &amp;bRead, NULL);
          if (!bSuccess || bRead == 0) {
              std::cout &lt;&lt; "ReadFromPipe::Exiting after ReadFile.\n";
              break;
          }
          bSuccess = WriteFile(hPARENT_STD_OUT, buffer, BUFFSIZE, &amp;bWritten, NULL);
          if (!bSuccess) {
              std::cout &lt;&lt; "ReadFromPipe::Exiting after WriteFile.\n";
              break;
          }
      }
  }
  </code></pre>
  
  <p>And the output:</p>
  
  <pre><code>Start of parent execution: seq  name             file
  ---  ---------------  ----------------------------------------------------------
  0    main
  ówVE_■   öΘ/ P╞ów    (┴M (┴M         êΘ/ (┴M     £Θ/ ╕å¥w  M áΘ/ ,╟₧w     Ω/ fr#u  M ╝îíw@r#u╕   (∞/     @∩/        ΣΘ/ @               @∩/ (∞/ ⁿΘ/ ép#u@∩/ (∞/ @∩/ &lt;ε/ o#u(∞/ @∩/ 8∩/ 4o#u┘╥₧w        ╓   ┤Ω/ ┘jƒw  M A÷₧w  M A÷₧wÿìM     ■≤₧w╪½└(     M    8┘M     M A÷₧wÿìM  ²   ¿½└(ªfM   M ~fM   xçM δ/   M A÷₧wxêM     ■≤₧wx¼└(      M    ╚½└(  M            δ/ ù    wáw  Vδ/ ╓   |δ/ ┘jƒwⁿδ/ Vδ/   ½└(αφ/ ⁿδ/
  kƒw
  kƒw    ⁿδ/ ░δ/ (°     M ╚╜M ΦÉM    îM Ç   ÉìM └ 3 6 9 5 7 \   ╨φ/ |δ/ πlƒw╢êM ¿δ/ \   αφ/ ^      ¼φ/ πiƒw╨φ/ áδ/     `ε/ ≥iƒw    ┐M \ ^ ¿δ/ S -   M A÷₧wÿêM     ■≤₧wP¡└(p     M h   1 6 2 2 ╠ ╔8 0   - 3 6 9 5 7 ╠ ╔8 1 4 - öfM 0 1       &amp;▄₧w  B·  A÷₧w       ÿêM c : ┘╥₧w@¡└(  M ÉêM     ╠ ╔  M ╠ ╔ê├M   äM Ç   ╨∞/ ╠ ╔φ/ Ä╘Γ á∞/
  ╬M    \φ/        φ/ \φ/ ╠ ╔=·  zφ/   M ÉêM ñÉM ≡∞/ Ç    ë½w┬ÇƒwL  |φ/    ÿêM      └&amp;       ê╤M ╕∞/           /  ówVE_■   dφ/ P╞ów    ÿêM ÿêM ╕φ/ á∩/     ÿêM     `M S B _ E tφ/ ,╟₧w    ÿêM °∩/ @X#u  M     ÿêM     É±/ SX#áwÉ±/ ┐M                               Ç±/     P   P6*uá∩/ ÿêM                                                                                                                                                                                                                                                                                                                                                                                                                                                                                               WΓF┼CÑ■ ìεπ╙≡WΓF┼CÑ■ ìεπ╙≡                           _╩╝H±/ ñU#u          Ç±/     t⌠/ ▒U#u
          (                                                                                                             ┘╥₧w╨▒└(┘╥₧w╪▒└(  M ┐M     ╚▒└(  M ░╛M             ≈         NM    ╠ ╔                              α╛M   M ░╛M ±   ▒X#u   ░╛M Ç      Ç      (╟M     ╕╛M ╠  └ M    L       ëM ╕╛M    ÿêM              ╪ÅM    ╪ÅM    `M ówVE_■   ▄±/ P╞ów    ┐M   M         ╕╛M ┐M ╕╛M     α±/ ╕╛M Φ±/ ,╟₧w    ⁿ±/ ?ñ#u  M     ┐M ╚≈/     ╚≈/ g⌡Θv╩ê∞v╬∩Θv╪D╔@┬Q┌ P_$u    ╬ ╧ ╨ ╤ ╥ ╙ ╘ ╒ ╓ ╫ ╪ ┘ ┌ █ ▄ ▌ ▐ ▀ α ß Γ π Σ σ                                                     αëM         â   É▀█ D       'M                                            ö   É   É   l@                       L      é£        "   ┐M ?      α²    √   @┤└(└           └ M                +   M     &gt;  &gt;          M        └ M                M ░  &amp;  &amp;  M H          ñ   ¿                 @   ≡²     α²             á&amp;    `°/                        £  t  h╝M     +             █               [           h  @           M                                                        P°/ ┐M ╨⌡/  α² ╨&amp;  °█     ¿                 ██                     ╕╛M
                         ¿       ■≤₧  └(    ñ              ╕╛M                  °█ c               └        M █  █'   └ M Ω    X╝M &amp;         └     ■       ┘╥₧wá   £   £  t          └ M Ç   @   @  ñ     °█ $ &amp; Φ╛M                                                           ╠⌠v   î÷/ á÷/ PΩ¥w╠⌠vî÷/       H⌠v   |⌠vH⌠v ⌠v▌Θ¥w░÷/         └≈/ ≤τ¥w┬Q┌ ÿ   Φ¥w    2   ⌠v  ⌠v   ì                °≈/ H⌠v                                                                                                                                                                                                                                                                            ⌠╢└(∞≈/ ┤ïΘv½½½½╝îíw╪ïΘvÿ   ┬Q┌ φïΘv░┌ ÿ   ⁿD╔@°/ ╩┌ ÿ   ■┌
     ┌S╙╫∞°/ Φå█     ┤°/ 8┌ .databas
  </code></pre>