Home > Blockchain >  Need help on message passing queue
Need help on message passing queue

Time:12-18

I'm still new to programming. I have been trying my best to finish this assignment. When I run the program it display: sent of total 0 bytes. It should display total bytes sending out. assignment prompt question:

The Sender:

  1. The sender shall be invoked as ./sender where is the name of the file to send to the receiver. For example, ./sender file.txt will send the file named file.txt.

  2. When invoked, the sender shall open the message queue named cpsc351messagequeue. If it does not exist, the sender shall terminate with an error.

  3. Otherwise, the sender shall open the file specified at the command line and proceed as follows:

(a) Read at most 4096 bytes from the file.

(b) Send the bytes read through the message queue using mq send() and a message priority of 1.

(c) Repeat the previous steps until the end of file is reached.

(d) When the end of the file is reached, send an empty message to the receiver with a priority of 2 to tell the receiver that the sending is done.

  1. Terminate.

my code:

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

#define MSQ_NAME "/cpsc351queue"


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

    // The file size
    int fileSize = -1;

    // The buffer used to store the message copied
    // copied from the shared memory
    char buff[4096];

    // The variable to hold the message queue ID
    int msqid = -1;

    // The total number of bytes written
    int totalBytesRead = 0;

    // The number of bytes 
    int bytesRead = 0;

    // Whether we are done reading  
    bool finishedReading = false;
    
    // TODO: Define a data structure
    // of type mq_attr to specify a
    // queue that can hold up to 10
    // messages with the maximum message
    // size being 4096 bytes
    mq_attr attr;

    attr.mq_flags = 0;
    attr.mq_maxmsg = 10;
    attr.mq_msgsize = 4096;
    attr.mq_curmsgs = 0;

    // Sanity checks -- make sure the user has provided a file
    if(argc < 2)
    {
        fprintf(stderr, "USAGE: %s <FILE NAME>\n", argv[0]);
        exit(1);
    }

    // Open the file for reading
    int fd = open(argv[1], O_RDONLY);
    
    // Make sure the file was opened
    if(fd < 0)
    {
        perror("open");
        exit(1);
    }
    
    
    // TODO: Gain access to the message queue
    // whose name is defined by the macro
    // MSQ_NAME macro above. We assume that
    // the receiver has allocated the message queue.
    mqd_t qid = mq_open("/cpsc351queue", O_RDWR, 0600, &attr);

    
    //TODO: Loop below attempts to read the 
    // file 4096 bytes at a time.
    // Modify the loop as necessary to send
    // each chunk of data read as message
    // through the message queue. You can use
    // 1 for the priority of the message.



    // Keep writing until all data has been written
    while((totalBytesRead < fileSize) && !finishedReading)
    {
        
        totalBytesRead = read(fd, buff, bytesRead);

        
        bytesRead = mq_send(qid, totalBytesRead, 4096, 1);
    

        // Something went wrong
        if(bytesRead < 0)
        {
            perror("read");
            exit(1);
        }
        // We are at the end of file
        else if(bytesRead == 0)
        {
            // We are at the end of file
            finishedReading = true;     
        }
        
        
        totalBytesRead  = bytesRead;
    }
    
    // TODO: Send a message with size of 0
    // to the receiver to tell it that the
    // transmission is done
        

    fprintf(stderr, "Sent a total of %d bytes\n", totalBytesRead);
    
    // TODO: Close the file     
    close(fd);
    return 0;
}

CodePudding user response:

  1. The program should open the message queue named /cpsc351queue, not /cpsc351messagequeue.

  2. The mq_send function should be called with the following arguments: qid, buff, bytesRead, 1. Currently, it is being called with totalBytesRead, 4096, and 1.

  3. The read function should be called with the following arguments: fd, buff, and 4096. Currently, it is being called with fd, buff, and bytesRead.

  4. The totalBytesRead variable should be updated after the read function is called, not before.

  5. The bytesRead variable should be updated after the mq_send function is called, not before.

  6. The loop should continue until the end of the file is reached, which can be determined by checking whether bytesRead is less than 0. Currently, the loop is continuing until bytesRead is equal to 0.

  7. After the loop finishes, the program should send an empty message to the receiver with a priority of 2 to tell the receiver that the sending is done. This can be done by calling the mq_send function with a message size of 0 and a priority of 2.

With these changes, the program should read the file in 4096-byte chunks, send each chunk through the message queue, and then send an empty message to the receiver when it reaches the end of the file.

CodePudding user response:

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

#define QUEUE_NAME "/cpsc351messagequeue"
#define MAX_MESSAGE_SIZE 4096
#define MAX_QUEUE_SIZE 8192

int main(int argc, char *argv[]) {
  if (argc < 2) {
    fprintf(stderr, "Usage: %s <file-name>\n", argv[0]);
    return 1;
  }

  // Open the message queue
  mqd_t queue = mq_open(QUEUE_NAME, O_WRONLY);
  if (queue == (mqd_t)-1) {
    perror("Error opening message queue");
    return 1;
  }

  // Open the file
  FILE *file = fopen(argv[1], "r");
  if (file == NULL) {
    perror("Error opening file");
    return 1;
  }

  // Read at most 4096 bytes from the file and send them through the message queue
  char buffer[MAX_MESSAGE_SIZE];
  size_t bytes_read;
  while ((bytes_read = fread(buffer, 1, MAX_MESSAGE_SIZE, file)) > 0) {
    if (mq_send(queue, buffer, bytes_read, 1) == -1) {
      perror("Error sending message");
      return 1;
    }
  }

  // Send an empty message to the receiver with a priority of 2 to indicate that the sending is done
  if (mq_send(queue, "", 0, 2) == -1) {
    perror("Error sending message");
    return 1;
  }

  // Close the file and message queue
  fclose(file);
  mq_close(queue);

  return 0;
}
  • Related