简体   繁体   中英

getting SEGFAULT when reading an array from shared memory

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)
                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.

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[];
};

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM