1

I wrote 2 programs that normally 1.create the named pipe(server) and 2. pass the string from the shell to the server part.

I understand how to hand over a string from the terminal to the server part of the named pipe.But, i don't have any idea how to pass files as arguments into the 2 program so that the file's content should be read and therefore passed out to ( likely the server part of the named pipe) another file. The idea is to copy the first file's content to the second file. Unfortunately, i don't have any idea how to implement this.

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

#define FIFO_NAME "myfifo"
#define BUF_SIZE 512
int main (void)
{
  FILE * fifo;
  char * buf;
  if (mkfifo ("myfifo", 0640) == -1) {
    fprintf (stderr, "Can't create fifo\n");
    return 1;
  }
  fifo = fopen (FIFO_NAME, "r");
  if (fifo == NULL) {
    fprintf (stderr, "Cannot open fifo\n");
    return 1;
  }
  buf = (char *) malloc (BUF_SIZE);
  if (buf == NULL) {
    fprintf (stderr, "malloc () error\n");
    return 1;
  }
  fscanf (fifo, "%s", buf);
  printf ("%s\n", buf);
  fclose (fifo);
  free (buf);
  unlink (FIFO_NAME);
  return 0;
}


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

#define FIFO_NAME "myfifo"

int main (int argc, char ** argv)
{
  int fifo;
  
  if (argc < 2) {
    fprintf (stderr, "Too few arguments\n");
    return 1;
  }
  fifo = open (FIFO_NAME, O_WRONLY);
  if (fifo == -1) {
    fprintf (stderr, "Cannot open fifo\n");
    return 1;
  }
  if (write (fifo, argv[1], strlen (argv[1])) == -1) {
    fprintf (stderr, "write() error\n");
    return 1;
  }
  close (fifo);
  return 0;
}

1 Answer 1

0

I'm not totally sure that I understand what you're asking. My interpretation is that instead of sending a message supplied to the client on the command line, you want to give a filename, then send the content of that file to the server over the pipe. If so, something like this might work for you:

Here's the server:

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

#define FIFO_NAME "myfifo"
#define BUF_SIZE 512

int main(void)
{
    if (mkfifo("myfifo", 0640) == -1) {
        fprintf(stderr, "Can't create fifo\n");
        return EXIT_FAILURE;
    }

    FILE *fifo = fopen(FIFO_NAME, "r");
    if (fifo == NULL) {
        fprintf(stderr, "Cannot open fifo\n");
        return EXIT_FAILURE;

    }

    char *line = NULL;
    size_t line_length = 0;

    while (getline(&line, &line_length, fifo) != EOF) {
        printf("%s", line);
    }

    free(line);
    fclose(fifo);
    unlink(FIFO_NAME);

    return EXIT_SUCCESS;
}

And here's the client:

#include <stdio.h>
#include <fcntl.h>
#include <stdlib.h>
#include <unistd.h>

#define FIFO_NAME "myfifo"

int main(int argc, char **argv)
{
    if (argc < 2) {
        fprintf(stderr, "Too few arguments\n");
        return EXIT_FAILURE;
    }

    const int input_fd = open(argv[1], O_RDONLY);
    if (input_fd < 0) {
        perror("open");
    }

    const int fifo_fd = open(FIFO_NAME, O_WRONLY);
    if (fifo_fd < 0) {
        perror("open");
        return EXIT_FAILURE;
    }

    char buffer[4096];
    int bytes_used;

    while ((bytes_used = read(input_fd, buffer, sizeof(buffer))) > 0) {
        if (write(fifo_fd, buffer, bytes_used) < 0) {
            perror("write");
            return EXIT_FAILURE;
        }
    }

    close(fifo_fd);
    close(input_fd);

    return EXIT_SUCCESS;
}

This extends your sample code so that the client

  • Uses the command line option as a filename
  • Opens that file
  • In a loop, reads from the file and writes to the pipe

Similarly, I modified the server to be able to read more than one string from the pipe. Currently it prints everything it reads from standard output. Consider a sample run:

First I start the server:

$ gcc -o server server.c
$ ./server

Next, I run the client with a input file

$ cat message
this is a file
it has multiple lines
$ ./client message

Then I see the following output from the server:

this is a file
it has multiple lines

If you want to write that to a file instead of standard output, that'd be a fairly simple change.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .