title: pipe, fork and shell commands in C
body: <p>I am trying to reproduce the pipes in a shell. for example ls | sort
  At first I am trying the pipes but I can't get the parent to read the result of what the child has executed:</p>
  
  <pre><code>//pipes essai
  # include &lt;stdio.h&gt;
  # include &lt;stdlib.h&gt;
  # include &lt;unistd.h&gt;
  # include &lt;sys/types.h&gt;
  # include &lt;sys/wait.h&gt;
  # include &lt;assert.h&gt;
  # include &lt;string.h&gt;
  # include &lt;sys/stat.h&gt;
  # include &lt;fcntl.h&gt;
  
  enum {
  MaxLigne = 1024, // longueur max d'une ligne de commandes
  MaxMot = MaxLigne / 2, // nbre max de mot dans la ligne
  MaxDirs = 100, // nbre max de repertoire dans PATH
  MaxPathLength = 512,
   // longueur max d'un nom de fichier
   };
  
  void decouper(char *, char *, char **, int);
  int spawn(char * pathname, char * mot[]);
  
  # define PROMPT "? "
  
  int main(int argc, char * argv[]) {
  char ligne[MaxLigne];
  char pathname[MaxPathLength];
  char * mot[MaxMot];
  char * dirs[MaxDirs];
  int i, tmp, x;
  int fd[2];
  int t, res = 0;
  char buf[1024];
  char * mot2[10];
  
  /* Decouper PATH en repertoires */
  decouper(getenv("PATH"), ":", dirs, MaxDirs);
  
  /* read the command lines and try to execute them */
  for (printf(PROMPT); fgets(ligne, sizeof ligne, stdin) != 0; printf(PROMPT)) {
      decouper(ligne, " \t\n", mot, MaxMot);
      if (mot[0] == 0) // empty line
          continue;
  
          //launch the pipe
          int p=pipe(fd);
          assert(p&gt;=0);
  
  
          tmp = fork(); // launch the pipe process
          if (tmp &lt; 0) {
              perror("fork");
              continue;
          }
  
          if (tmp != 0) { // parent wait for end of child
  
              //close this side of the pipe
              close(fd[1]);
              //waiting
              while (wait(0) != tmp)
                  ;
              //when finish waiting read what the child has written in the pipe
              read(fd[0], buf, sizeof(buf));
              //print the result
              printf("read %s\n", buf);
              //get back the hand to the user
              continue;
  
          }else if (tmp==0){
  
          // child
  
          //close this side of the pipe
          close(fd[0]);
          //close stdout
          t=close(1);
          //make sur stdout is closed
          assert(t&gt;=0);
          //open the pipe for writing in it instead of in the stdout
          FILE * sortie=fdopen(fd[1], O_WRONLY);
          //make sure it is ok
          assert(sortie!=NULL);
  
          //try to execute the command
          for (i = 0; dirs[i] != 0; i++) {
              snprintf(pathname, sizeof pathname, "%s/%s", dirs[i], mot[0]);
              execv(pathname, mot);
  
          }
          }
  
          // if exec was unsuccessful
          fprintf(stderr, "%s: not found\n", mot[0]);
          exit(1);
  
  }
  
      printf("Bye\n");
      return 0;
  
  }
  
  void decouper(char * ligne, char * separ, char * mot[], int maxmot){
  int i;
  
  mot[0] = strtok(ligne, separ);
  for(i = 1; mot[i - 1] != 0; i++){
  if (i == maxmot){
    fprintf(stderr, "Erreur dans la fonction decouper: trop de mots\n");
    mot[i - 1] = 0;
   }
   mot[i] = strtok(NULL, separ);
  }
  }
  </code></pre>
  
  <p>there is a problem with this line FILE * sortie=fdopen(fd[1], O_WRONLY);</p>
  
  <p>pipe1.c: In function ‘main’:
  pipe1.c:81:4: warning: passing argument 2 of ‘fdopen’ makes pointer from integer without a cast
  /usr/include/stdio.h:303:14: note: expected ‘const char *’ but argument is of type ‘int’</p>
  
  <p>but how can I make the child to output in the pipe??? freopen doesn't work either</p>
  
  <p>the result I get:
  ? ls
  read </p>
  
  <p>which means of course nothing is read. What can I do I am really out of ideas now???
  thank you very much in advance</p>