Question

I am trying to write a C++ program to delete the shared memory segments. I know it can be done from cmd prompt using

ipcs -m | awk '{ print $2 }' | xargs ipcrm -m

But I am trying to do it using C++ so that I create a shared memory garbage collector.

The idea is to delete shared memory segments that are not attached to any process( nattach ==0) or the status == NULL

Was it helpful?

Solution

I finally have the the answer to my own question. It can be done using shmctl flags. shmctl(0,SHM_INFO,&shm_info); gives number of segments currently present.

shmctl(i , SHM_STAT , &shm_segment) gives the segment id

it can also be accessed by shm_segment.shm_id

#include <sys/shm.h>     

int delete_segment(int seg_id){
    if ((shmctl(seg_id,IPC_RMID,0))==-1){
    std::cout<<" ERROR(C++)with shmctl(IPC_RMID): "<<strerror(errno)<<std::endl;
    return -1;
    }else//on success
        return 0;
}

void clean_segments(){

    struct shmid_ds shm_info;
    struct shmid_ds shm_segment;
    int max_id = shmctl(0,SHM_INFO,&shm_info);
    if (max_id>=0){
        for (int i=0;i<=max_id;++i) {
                int shm_id = shmctl(i , SHM_STAT , &shm_segment);
                if (shm_id<=0)
                    continue;
                else if (shm_segment.shm_nattch==0){
                    delete_segment(shm_id);
                }
        }
    }
    return result;
}

OTHER TIPS

According to a source code of the ipcrm, it calls shmctl.

shmctl(id, IPC_RMID, NULL)

I would suggest executing strace ipcrm -m <your-arguments> and see what system calls it performs. In most cases that should be suficient (at least it will point you in the right direction), if not - look at the source code of ipcrm. I'm pretty sure you do not need any special privileges (ipcrm on my system does not have SUID or SGID bits set).

The code below use I:

    void clean_segments(int startId, int endId) {
    for (int i=startId; i<=endId; ++i) {
        struct shmid_ds shm_segment;
        int shm_id = shmctl(i, SHM_STAT, &shm_segment);
        delete_segment(shm_id);
        printf("Segment %d has been deleted\n", shm_id);
    }}

clean_segments(1146894, 6357160);// example of using the code above

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top