2013-02-07 1 views
0

У меня возникли проблемы со следующим кодом. Я выполняю лабораторное задание при использовании forks (создание процессов). Его простая программа, которая должна читать ввод с клавиатуры, а затем читать/записывать ее в fifo и отображать ее содержимое и записанные байты.Ошибка моего кода fork fifo c

Когда я запускаю его, все кажется прекрасным, пока я не введу какой-либо текст. Родительское сообщение печати отображается нормально, но дочернее сообщение печати никогда не появляется, пока я не ввел свое второе сообщение, в котором он всегда говорит, что он написал 80 байтов, хотя я знаю, что это не так, и theres - это странный специальные символы повсюду.

Вот исполняемый о том, как программа должна быть: Linux: http://www.mediafire.com/?6806v24q6lz7dpc QNX: http://www.mediafire.com/?a9dhiwmrlx2ktkp

И мой код до сих пор:

#include<stdio.h> 
#include<stdlib.h> 
#include <sys/stat.h> 
#include <unistd.h> 
#include <sys/types.h> 
#include <fcntl.h> 
#include <string.h> 

int main(int argc, char *argv[]) { 

    char FifoName[] = "fifoDan"; 
    int fd; 
    pid_t retval; 
    int size_read; 
    char buff[80]; 
    int size_written; 

    mknod(FifoName, S_IFIFO | 0666, 0); 

    // Check if its not equal to zero (ie: child process = 0) 
    if (retval = fork()) { 

      printf ("Parent: Waiting for writers \n"); 

      if(fd = open(FifoName, O_RDONLY) == -1) { 
          perror("Could not read the FIFO"); 
        return EXIT_FAILURE; 
      } 

      printf ("Parent: Received a writer \n"); 

      do { 

          int strsize; 

          size_read = read(fd, buff, sizeof(buff)); 

          printf("Parent: read %d bytes: %s \n", size_read, buff); 
          fflush(stdout); 

          strsize = strlen(buff); 

          // put a '\0' at the end of the data 
          buff[strsize] = '\0'; 


        } while(size_read > 0); 


        close(fd); 
        waitpid(retval, NULL, NULL); 

        if(unlink(FifoName) != -1) { 
          return EXIT_SUCCESS; 
        } else { 
          return EXIT_FAILURE; 
        } 


    } else { 


     printf ("Child pid %d waiting for readers \n", getpid()); 
     fflush(stdout); 

     if(fd = open(FifoName, O_WRONLY) == -1) { 
          perror("Could not read the FIFO"); 
        return EXIT_FAILURE; 
      } 

     printf ("Child: Got a reader, enter some stuff:\n"); 
     fflush(stdout); 

     while(fgets(buff, 80, stdin) != NULL) { 

        int strsize; 

        strsize = strlen(buff); 

        if(strsize < 80) { 
          buff[strsize] = '\0'; 
        } 

        size_written = write(fd, buff, sizeof(buff)); 

        printf ("Child: wrote %d bytes \n", size_written); 
        fflush(stdout); 

      } 

      close(fd); 

    } 


} 

ответ

4

Эта линия (к примеру) не будет делать то, что вы думаете, что он:

if(fd = open(FifoName, O_WRONLY) == -1) 

Оператор равенства имеет более высокий precedence, чем оператор присваивания, так что вы делаете на самом деле это:

if(fd = (open(FifoName, O_WRONLY) == -1)) 

когда вы хотите:

if((fd = open(FifoName, O_WRONLY)) == -1) 

Проблема с чтением буфера/записи, потому что вы написать весь буфер:

size_written = write(fd, buff, sizeof(buff)); 

Изменить писать только фактическую строку, используя strsize вместо этого.

+0

+1. Это был мой опыт написания C в течение 27 лет, что, хотя законно писать задания внутри операторов if, это также прекрасный способ создания ошибок. Дополнительная строка кода для простого назначения не замедлит компиляцию. :) –

+0

Спасибо за помощь. Он исправил проблему, с которой я столкнулся. Но теперь он говорит, что как родительский, так и дочерний ядро ​​читают/записывают 80 байт каждый раз, когда я что-то ввожу, вместо подсчета количества байтов, которые я вводил с моей клавиатуры. Может, я ошибаюсь? – user1930558

+0

@ user1930558 Это потому, что вы _write_ 80 байт. Вы пишете весь буфер, так как вы используете 'sizeof (buff)' в вызове 'write'. –