Newsgroup: it.comp.programmare
Titolo: Pipe e ridirezione standard input e output su linux

#include<stdio.h>
#include<unistd.h>
#include<sys/stat.h>
#include<sys/types.h>
#include<fcntl.h>
#include<stdlib.h>
#define SIZE 100
int main()
{
int pid;
int fd[2];
char str1[SIZE];
char str2[SIZE];
 
if (pipe(fd)==-1) {perror("Pipe non creata "); exit (1);}
pid=fork(); if(pid==-1) {perror("fork fallita");exit (1);}
if (!pid){
int i=dup(0);
close(0);
dup(fd[0]);
close(fd[1]);
close(fd[0]);
scanf("%s\n",str1);
close(0);
dup(i);
 
}
else {
int out=dup(1);
close(1);
dup(fd[1]);
close(fd[0]);
close(fd[1]);
printf("Ciao!\n");
close(1);
dup(out);
 
}
return 0;
}
 
 
Questo codice "dovrebbe" associare  lo standard input alla pipe in 
lettura e quello output sulla pipe in scrittura, in modo che scanf e 
printf leggano e scrivano dalla pipe in maniera trasparente.
 
E poi alla fine ripristinare standard input e output a quelli normali.
 
Peccato che non funziona, infatti il codice di sopra stampa "Ciao!", e 
non dovrebbe farlo, perch� quella stampa dovrebbe scrivere sulla pipe e 
non a video...
 
 
Dove sbaglio?
 

 Dove sbaglio?
 
Sembra che non hai ben presente cosa fa dup():
dup() prende come parametro il file descriptor da duplicare e ritorna il nuovo
file descriptor.
 
Ciao1

 file descriptor.
 
 
E infatti quando faccio(nel caso del padre):
 
int out=dup(1);
 
Adesso in "out" non trovo un file descriptor di backup per lo standard 
output?
 
 
Questo comunque � quello che voglio fare:
1)Salvo il file descriptor "1", duplicandolo in out(il nuovo file 
descriptor appena creato e ritornato da dup)
2)Chiudo "1"
3)Duplico fd[1] con dup, che trova come primo libero "1",  quindi viene 
  associato alla pipe in scrittura.
4)chiudo fd[0] e fd[1]
 
 
A questo punto printf non dovrebbe "stampare" sulla pipe?
 
 
Grazie e scusami se ho fatto confusione.
 
 

 
 
Hai ragione, my bad, avevi scritto tutto bene :D
 
Il problema è molto più semplice. Printf scrive su stdout, che è un file con il
suo stato interno, scambiargli il file descriptor in corsa non basta.
Se usi write() al posto di printf stai a posto, altrimenti devi usare le
funzioni di stdio (freopen(), per esempio) per avere uno stdout/stdin con
il nuovo stato pulito.
 
Ciao!


 
 
Vado cosi ad una prima veloce lettura, troppo confusionario quel codice
 
Se voglio direzionare una fd[0] (la pipe) su stdin basta fare cosi:
 
close(0);  // chiude stdin
 
if (dup(fd[0]) == -1)  {  ora stdin è uguale a fd[0] se non è in errore
   // gestisco l' errore
}
 
 
 
 
 


Grazie,mi hai tranquillizzato.
L'importante è che ho capito come funziona la pipe e dup, che è quello 
che più mi interessa al momento...
 

 }
 
In pratica è quello che faccio io su più linee di codice :-)
 
le linee che vedi in più erano solo per cercare di fare il backup delle 
associazioni standard per i file descriptor 1 e 0, cosa che in realtà 
nel codice di sopra non serve...
 
Capisco però che quel codice è comprensibile solo a me che l'ho pensato :-)
 
 
 
 

 Capisco però che quel codice è comprensibile solo a me che l'ho pensato :-)
 
Nah, è che di solito si usa dup2() che è più comoda:
 
dup2(fd[1], 1);
 
che chiude il descrittore target e associa il primo al secondo, anche se non è
il primo non aperto del processo.
 
Un po' più comodo di una serie di close e dup, no? ;)
 
Ciao!

 Un po' pi� comodo di una serie di close e dup, no? ;)
 
 
sicuramente :-)
 


Un altro modo (per di piu abbreviato) di fare le stesse cose