0

I'm new to using shared memory and for the first file the implementation is working fine but for the second file it is unable to read some of the structures from the shared memory . I think the problem is in my mmap but not quite sure what exactly

first file which works nicely:

  struct Sh_Mem* open_res(int nb_tables)
    {
        size_t mem_size = MEM_SIZE(nb_tables);
        int shm_fd=shm_open(MEM_NAME,O_RDWR|O_CREAT | O_TRUNC, 0600);
        if(shm_fd<0)
            raler("shm_open");
        
        ftruncate(shm_fd,mem_size);
        
        struct Sh_Mem * res=mmap(NULL,mem_size,PROT_READ| PROT_WRITE,MAP_SHARED,shm_fd,0);
        if(res == NULL)
            raler("mmap");
        res->nb_tables=nb_tables;
        res->size = mem_size;
        
        return res;
    }
int main(int argc, char const *argv[])
{

    if (argc < 3)
        raler("Usage : ./restaurant <duree_repas> <capacite_des_tables>");
    
    
    int dinner_time = atoi(argv[1]);
    int nb_tables = argc -2;
    int fermeture=0;
    struct table* tables=malloc(nb_tables*sizeof(struct table));
    
    if (dinner_time < 100 )
        raler("Duree de repas tres courte");

    struct Sh_Mem* res=open_res(nb_tables);
    res->table = malloc(nb_tables*sizeof(struct table));

    for(int i = 2; i < (argc); i++)
    {
        if(atoi(argv[i])>6 || atoi(argv[i])<1 )
        {
            printf("\nERROR : %s\n ",argv[i] ); 
            raler("Max Capacity of Tables is 6 ");
        }
        tables[i-2].size = atoi(argv[i]);
        
    }
    res->table=tables;
    shm_unlink(MEM_NAME);
    return 0;
}

Second file which give me a segmentation fault :

struct Sh_Mem* first_guest(char * nom)
{

    int shm_fd=shm_open(MEM_NAME,O_RDWR, 0600);
    if(shm_fd<0)
        raler("shm_open");
    struct stat stat;
    if(fstat(shm_fd, &stat) < 0) {
        perror("fstat");
        exit(1);
    }
    struct Sh_Mem * guests=mmap(NULL,stat.st_size,PROT_READ| PROT_WRITE,MAP_SHARED,shm_fd,0);
    if(guests == NULL)
        raler("mmap");  
return guests;
}
int main(int argc, char const *argv[])
{
    if (argc != 3)
        raler("Usage : ./convive <nom_du_convive> <nombres_de_personnes_dans_le_groupe/nom_du_premier_convive>");
    
    if(strlen(argv[1])>10)
        raler("Name has to be less or equal to 10 char ");
    
    if(isdigit(argv[1][0]))
        raler("First argument has to start with a character");

    if (isdigit(argv[2][0]))
    {
struct Sh_Mem* res=first_guest((char*)argv[1]);
        for (int i = 0; i < res->nb_tables; i++)
        {
            if(res->table[i].used==1)
            {

                continue;
            }
            if(res->table[i].size == atoi(argv[2]))
                {
                    found =1;

                    res->table[i].name=(char *)argv[1];
                    res->table[i].used =1;
                }
                printf("%s\n",res->table[i].name );
        }

the error happens whenever i pass by a res->tables. i tested if it was equal to null but it isn't also here is the struct:

void raler(char *msg)
{
    perror(msg);
    exit(1);
}
struct table
{
    int id;
    int size;
    char* name;
    int nb_left;
    int used;

};
struct Sh_Mem{

int nb_tables;
size_t size;
struct table* table;
};
#define MEM_NAME "/guest"
#define MEM_SIZE(nb_table) sizeof (struct Sh_Mem) + (nb_table)*sizeof (struct convive)+ (nb_table)*sizeof (struct table)

2 Answers 2

1
                res->table[i].name=(char *)argv[1];
            }
            printf("%s\n",res->table[i].name );

This doesn't work. You are putting a pointer into the current process' address space into shared memory. This means nothing to any other process.

You can fix this by making name a fixed-length array or by allocating some shared memory and having name point to that. Just be careful -- each process will have to compute the correct local pointer to the shared memory since different processes may map the same shared memory segment at different addresses.

Sign up to request clarification or add additional context in comments.

2 Comments

but the program doesn't even get to this point it returns segfault when it gets to if(res->table[i].used==1) is it the same problem and does that mean i have to allocate everything in the structure
Same problem. If you put pointers in shared memory, they have to be pointers to shared memory and every process has to figure out the correct pointer for their particular mapping of that shared memory. Likely, you just shouldn't be using shared memory this way.
0

All i had to do is change the struct from dynamic to static and it works fine

struct Sh_Mem{
int nb_tables;
size_t size;
struct table table[];
};

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.