我在C中练习并发,我编写了一个小而简单的程序,其中父进程创建了两个子节点,发送者和接收者。 发件人将从stdin中读取一个字符串,然后继续以某种方式将其发送给接收者(不相关)。
这里的真正问题是,当我运行程序时,它会执行fork,两个孩子将会出生,发送者应该等待一个字符串作为输入,但我无法找到插入任何东西的方法使用终端。 该程序似乎挂在scanf上,但我找不到引入任何输入的方法。终端,一旦程序启动,就不会让我插入任何东西。
我正在使用Xcode 6.3.2
#include <stdio.h>
#include <sys/wait.h>
#include <signal.h>
#include <unistd.h>
#include <string.h>
#include <stdlib.h>
#include <ctype.h>
#define FILE_NAME "conteggio"
#define MAX_CHAR 25
void receiver();
void sender();
void receiver_operation();
void sender_operation();
void to_maiusc(char s[], char* r);
int readline(int fd, char *str);
void nothing() {}
typedef enum {FALSE, TRUE} boolean;
int sender_pid, receiver_pid;
int main(int argc, const char * argv[]) {
FILE *f_in;
int status, num, sender_pid, receiver_pid;
// create the two childs
if ( (sender_pid = fork()) != 0 ) {
// I'm the father
if ( (receiver_pid = fork()) != 0 ) {
// wait until the two processes return
wait(&status);
wait(&status);
// read the number of interactions
if ( (f_in = fopen(FILE_NAME, "rb")) != NULL ) {
fread(&num, sizeof(int), 1, f_in);
printf("Il numero di interazioni è: %d", num);
fclose(f_in);
}
return 0;
}
else {
// Sono il receiver
receiver_operation();
}
}
else {
// sono il sender
sender_operation();
}
}
int readline(int fd, char *str) {
char c = '\0';
int i = 0;
while (c != '\n') {
read(fd, &c, 1);
str[i] = c; i++;
}
str[i] = '\0';
return i;
}
void sender_operation() {
FILE *fin;
int r_pid, count = 0;
char stringa[MAX_CHAR+1];
boolean finito = FALSE;
signal(SIGUSR1, nothing);
// aspetto che il receiver scriva sul file il pid e lo apro
pause();
if ( (fin = fopen("pid", "rb")) == NULL ) {
printf("Impossibile aprire file 'pid'.\n");
return;
}
// leggo il pid
fread(&r_pid, sizeof(int), 1, fin);
fclose(fin);
while (!finito) {
// leggo una stringa da tastiera
kill(0, SIGSTOP);
printf("Insert a string: ");
scanf("%s", stringa);
// controllo se è 'end'
if ( strcmp(stringa, "end") == 0 ) {
finito = TRUE;
}
// scrivo su file
if ( (fin = fopen("stringa.txt", "w")) == NULL ) {
printf("Impossibile aprire file 'stringa.txt'.\n");
}
fprintf(fin, "%s", stringa);
fclose(fin);
// segnalo al receiver che il file e' pronto
kill(r_pid, SIGUSR1);
// aspetto il risultato
pause();
// leggo il risultato
if ( (fin = fopen("stringa.txt", "r")) == NULL ) {
printf("Impossibile aprire file 'stringa.txt'.\n");
return;
}
fscanf(fin, "%s", stringa);
// stampo il risultato
printf("Stringa processata: %s", stringa);
fclose(fin);
// incremento numero iterazioni
count++;
}
// stampo su un file il numero di iterazioni
if ( (fin = fopen(FILE_NAME, "wb")) == NULL) {
printf("Impossibile creare il file %s\n", FILE_NAME);
return;
}
fwrite(&count, sizeof(int), 1, fin);
fclose(fin);
exit(0);
}
void receiver_operation() {
FILE *fout;
int pid;
boolean finito = FALSE;
char stringa[MAX_CHAR+1], result[MAX_CHAR+1];
signal(SIGUSR1, nothing);
// scrivo il mio pid su un file
if ( (fout = fopen("pid", "wb")) == NULL ) {
printf("Impossibile creare il file 'pid'\n");
return;
}
pid = getpid();
fwrite(&pid, sizeof(int), 1, fout);
fclose(fout);
// segnalo il file pronto
kill(sender_pid, SIGUSR1);
while (!finito) {
// ora aspetto che il sender scriva una stringa sul file 'stringa.txt'
pause();
// leggo la stringa da processare
if ( (fout = fopen("stringa.txt", "r")) == NULL ) {
printf("Impossibile aprire il file 'stringa.txt'\n");
return;
}
fscanf(fout, "%s", stringa);
fclose(fout);
if ( strcmp(stringa, "end") == 0 ) {
finito = TRUE;
}
// processo la stringa
to_maiusc(stringa, result);
// scrivo sul file il risultato
if ( (fout = fopen("stringa.txt", "w")) == NULL ) {
printf("Impossibile scrivere il risultato su 'stringa.txt'\n");
return;
}
fprintf(fout, "%s", result);
fclose(fout);
// segnalo il risultato pronto
kill(sender_pid, SIGUSR1);
}
}
void to_maiusc(char s[], char* r) {
int i;
r = malloc( sizeof(char) * strlen(s) +1);
// converto la stringa da maiuscola a minuscola
for(i=0; i<strlen(s); i++) {
r[i] = toupper(s[i]);
}
return;
}
有人有线索吗?
答案 0 :(得分:1)
让我看看我是否做对了,你的问题是子进程无法阅读stdin
,对吧?您可以使用fscanf(stdin, stringa);
我已经使用一个简单的示例进行了测试并且正常工作(只需通过 fscanf 更改 scanf )。如果那是你的问题,请告诉我。