La mise en place des tuyaux

J’essaie d’implémenter un shell Linux qui supporte le piping. J’ai déjà fait des commandes simples, des commandes s’exécutant en arrière-plan, des redirections, mais il manque toujours du piping.

J’ai déjà lu à ce sujet et vu des extraits de code, mais je n’ai toujours pas réussi à trouver une solution de travail.

Ce que j’ai jusqu’à présent:

int fd[2]; pipe(fd); pid_t pid = fork(); if (pid == -1) return -1; if (pid == 0) { close(fd[1]); //close write to pipe, in child execlp("cat", "cat", "names.txt", NULL); } else { close(fd[0]); //close read from pipe, in parent execlp("sort", "sort", NULL); } 

Je suis un programmeur débutant, comme vous le savez probablement, et lorsque je programme quelque chose dont je ne sais pas grand chose, ceci étant évidemment le cas, j’aime commencer par quelque chose de vraiment simple et concret, puis construire à partir de là.

Donc, avant de pouvoir implémenter trois commandes différentes et plus dans le pipeline, je voudrais pouvoir calculer “ls names.txt | sort” ou quelque chose de similaire, dans lequel names.txt est un fichier de noms non ordonnés de manière aléatoire.

Code mis à jour, mais ne fonctionne toujours pas.

Merci.

Vous devez remplacer la sortie d’un enfant par la fin de l’écriture du tuyau et le stdin de l’autre enfant par la fin de la lecture:

 if (pid == 0) { close(fd[0]); //close read from pipe, in parent dup2(fd[1], STDOUT_FILENO); // Replace stdout with the write end of the pipe close(fd[1]); // Don't need another copy of the pipe write end hanging about execlp("cat", "cat", "names.txt", NULL); } else { close(fd[1]); //close write to pipe, in child dup2(fd[0], STDIN_FILENO); // Replace stdin with the read end of the pipe close(fd[0]); // Don't need another copy of the pipe read end hanging about execlp("sort", "sort", NULL); } 

Recherchez dans l’appel de bibliothèque standard pipe() . Ceci est utilisé pour créer un tuyau. Vous devez bien entendu faire une partie du travail avant de lancer fork() , afin que le processus fils hérite correctement du descripteur de fichier.

Notez également l’ordre des arguments à dup2() :

 int dup2(int oldfd, int newfd); 

dup2 () fait de newfd la copie de oldfd, fermant d’abord newfd si nécessaire