Thread: passing int values and *double values through message queues

  1. #1
    Registered User
    Join Date
    Mar 2012
    Posts
    20

    passing int values and *double values through message queues

    hello .. can anybody explain me how i can pass integer and *double pointers through message queues
    i have no idea how i can do that ...

  2. #2
    Technical Lead QuantumPete's Avatar
    Join Date
    Aug 2007
    Location
    London, UK
    Posts
    894
    You'll need to give us a bit more to go on. Show us the code where you want to add message queues (I assume the program is multi-threaded?)
    "No-one else has reported this problem, you're either crazy or a liar" - Dogbert Technical Support
    "Have you tried turning it off and on again?" - The IT Crowd

  3. #3
    Registered User
    Join Date
    Mar 2012
    Posts
    20
    i need to pass the double *b from the child process to the parent process ... using message queues
    but since it's a pointer i am getting a segmentation fault at the compute() function that is in the second process(parent)

    Code:
    #include <unistd.h>
    #include <stdio.h>
    #include <sys/types.h>
    #include <sys/ipc.h>
    #include <sys/msg.h>
    #include <stdlib.h>
    #include <string.h>
    
    
    void main(int argc,char *argv[]) {
    
        if(argc != 2) {
        } else {
           
           int n = atoi(argv[1]);
           int i = 0;
           struct msgbuf {
                  long mtype;
            char message[100];
            double b;
           };
    
           switch(fork()) {
               case -1:
                printf("Erro de fork");
                break;
               case 0:
                printf("Oi");            
                double *b;
                int msgflg = IPC_CREAT | 0666;
                b = malloc(1000*1000*sizeof(double));
                    struct msgbuf a;
                a.mtype = 1;
                   strcpy(a.message,"1");
                   a.b = *b;
                key_t key = 123;
                size_t buflen = sizeof(a) - sizeof(long);
                int msqid = msgget(key,msgflg);
                msgsnd(msqid, &a,buflen, IPC_NOWAIT);
                printf("Processo 1\n");
                break;
               default: 
                wait();
                printf("Chego aqui\n");
                execlp("/home/hyper/Documents/SO2/TP3-4/rec","rec",0);
                /*
                    printf("Entro aqui\n");
                 for(i = 0;i < n;i++) {
                  switch(fork()) {
                      case -1:
                       printf("Erro de fork");
                    case 0:
                       exit(0);
                       break;
                    default:
                        printf("Processo 2\n");
                        break;
                  }
                     }*/
                 break;          
            }              
        }    
    
    };

    Code:
    #include <unistd.h>
    #include <stdio.h>
    #include <sys/types.h>
    #include <sys/ipc.h>
    #include <sys/msg.h>
    #include <stdlib.h>
    #include <string.h>
    
    int max_iterations = 256;
    
    double compute_point(double ci, double cr) { 
      int iterations = 0; 
      double zi = 0; 
      double zr = 0; 
       
      while ((zr*zr + zi*zi < 4) && (iterations < max_iterations)) { 
        double nr, ni;  
     
        /* Z <-- Z^2 + C */ 
        
        nr = zr*zr - zi*zi + cr; 
        ni = 2*zr*zi + ci; 
         
        zi = ni; 
        zr = nr; 
     
        iterations ++; 
      }   
      return iterations;   
    } 
     
    /* The "compute" function computes the Mandelbrot function over every 
       point on a grid that is "nx" points wide by "ny" points tall, where 
       (xmin,ymin) and (xmax,ymax) give two corners of the region the  
       complex plane. 
    */ 
     
    void compute(double *buffer, int nx, int ny, double xmin, double xmax,  
             double ymin, double ymax) { 
      double delta_x, delta_y; 
      int x, y; 
     
      delta_x = (xmax - xmin)/nx; 
      delta_y = (ymax - ymin)/ny; 
     
      for (y=0;  y<ny; y++) { 
        double y_value = ymin + delta_y * y; 
        for (x=0; x<nx; x++) { 
          double x_value = xmin + delta_x * x; 
          buffer[y*nx + x] = compute_point(x_value, y_value);
          printf("Chego aqui %d \n",x); 
        } 
      } 
    } 
     
    /* Output the data contained in the buffer to a Portable Greymap format 
       image file.  The parameter "max" should be an upper bound for the 
       data values in the buffer.  
    */ 
     
    void output_pgm(char *filename,double *buffer, int nx, int ny, double max) { 
      int i; 
      FILE *file; 
      file = fopen(filename,"w"); 
      fprintf(file,"P2\n"); 
      fprintf(file,"%d %d\n",nx,ny); 
      fprintf(file,"%d\n",(int)max); 
      for (i=0; i<nx*ny; i++) { 
        if (!(i%nx)) fprintf(file,"\n"); 
        fprintf(file,"%d ",(int)buffer[i]); 
      } 
      fclose(file); 
    } 
    
    int main() 
    {
            printf("Chego aqui(2)\n");
        int msqid;
        struct msgbuf {
                  long mtype;
            char message[100];
            double b;
           };
    
         struct msgbuf a;
         size_t len = sizeof(a) - sizeof(long);
         key_t key = 123;
         printf("Chego aqui(2)\n");
         msqid = msgget(key, 0666);
         printf("Chego aqui(2)\n");
         msgrcv(msqid, &a, len, 1, 0);
         printf("Chego aqui(2)\n");
         double *b = malloc(1000*1000*sizeof(double));
         b = &(a.b);
         printf("Chego aqui(3)\n");
         compute( b, 1000, 1000, -1.0, 1.0, -1.0, 1.0);
         printf("Chego aqui(4)\n");
             output_pgm( "mandel.pgm", b, 1000, 1000, 255);
    }
    Somehow it gives me a segmentation fault in the other process ...

  4. #4
    Novice
    Join Date
    Jul 2009
    Posts
    568
    Processes don't share their address space. Any pointer passed between them is highly likely to be invalid on the receiving end and trying to dereference it will lead to segfault.
    Disclaimer: This post shows my ignorance at the time of its making. I claim ownership of but not responsibility for all errors in it. Reference at your own peril.

  5. #5
    Registered User
    Join Date
    Mar 2012
    Posts
    20
    but then how can i share data between the two processes ... ? since the compute function needs a *double value ?!?!
    I could use an alternative way but i need to share the data between the two processes :S

  6. #6
    - - - - - - - - oogabooga's Avatar
    Join Date
    Jan 2008
    Posts
    2,808
    Threads run in the same address space. Can you use threads instead of processes?
    The cost of software maintenance increases with the square of the programmer's creativity. - Robert D. Bliss

  7. #7
    Technical Lead QuantumPete's Avatar
    Join Date
    Aug 2007
    Location
    London, UK
    Posts
    894
    You could create a shared memory block and instead of passing around a double* you could index into that shared memory block
    "No-one else has reported this problem, you're either crazy or a liar" - Dogbert Technical Support
    "Have you tried turning it off and on again?" - The IT Crowd

  8. #8
    Novice
    Join Date
    Jul 2009
    Posts
    568
    Quote Originally Posted by QuantumPete View Post
    You could create a shared memory block and instead of passing around a double* you could index into that shared memory block
    I'd recommend doing this over threads. It should be easier to do then threading and more appropriate for the task; which looks more like an exercise in IPC then parallel processing.

    Note to OP: Don't abandon message passing entirely. You'll still need it for communication between processes.
    Disclaimer: This post shows my ignorance at the time of its making. I claim ownership of but not responsibility for all errors in it. Reference at your own peril.

  9. #9
    Registered User
    Join Date
    May 2012
    Posts
    505
    The function probably needs a list of doubles. If you are not allowed to share pointers, you have two options. 1 is to pass the doubles themselves. You might have to send several messages and reaasemble the list if it more than a few numbers long. 2 is to keep parent and child in synch and pass an identifier. This might be trivially easy if the listd are in read only memory, it will be harder if the lists are generated before the fork, very hard is the lists are generated after the fork, and impossible if the lists rely on separate data.

  10. #10
    Registered User
    Join Date
    Mar 2012
    Posts
    20
    Hi can you give me an example on how to pass an identifier ?
    I have already made it work with threads and shared memory before
    i would like the communication between processes to be done exclusively with message queues

  11. #11
    Novice
    Join Date
    Jul 2009
    Posts
    568
    Quote Originally Posted by Hyp3rTension View Post
    i would like the communication between processes to be done exclusively with message queues
    Why would you want to do that?
    Disclaimer: This post shows my ignorance at the time of its making. I claim ownership of but not responsibility for all errors in it. Reference at your own peril.

  12. #12
    Registered User
    Join Date
    Mar 2012
    Posts
    20
    Because i am trying to see if a program works with every kind of inter process communication

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 6
    Last Post: 04-04-2010, 11:48 AM
  2. Passing function pointer using message queues
    By LxRz in forum Linux Programming
    Replies: 4
    Last Post: 05-05-2008, 10:41 AM
  3. Storing int and double type values under one variable name
    By Thanuja91 in forum C++ Programming
    Replies: 10
    Last Post: 10-30-2007, 04:15 AM
  4. Assigning values to double vars
    By Levia8an in forum C Programming
    Replies: 7
    Last Post: 11-23-2006, 12:15 PM
  5. comparing two matrices or double values
    By collymitch in forum C Programming
    Replies: 4
    Last Post: 04-17-2005, 08:16 AM