0

I am writing a simple application on C that uses shared memory but I cannot run it anymore as it says:

shmat: Cannot allocate memory

I am using this script to free my memory but doesn't seem to work.

This is a screenshot of my processes:

enter image description here

This is the application code:

/* Shared Memory IPC creates a mamory space and send contendt to it while the other process can read from it.
Our implementation works like this:
    1. First run the application by passing as a argument the value you want to send to the shared memory. Example: ./ipc_sharedmem.o 4
    2. Run the appliation again to read from the shared memory (which is a new process, of course) wihout sending any arguments. Exmaple: ./ipc_sharedmem.o
*/

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/shm.h>

#define SHM_SIZE 1024  /* make it a 1K shared memory segment */

int main(int argc, char *argv[])
{
    key_t key;
    int shared_mem_mid;
    char *data;

    struct timeval t1, t2, t3, t4;

    if (argc > 2) {
        fprintf(stderr, "usage: shmdemo [data_to_write]\n");
        exit(1);
    }

    /* make the key: */
    if ((key = ftok("mach.c", 'R')) == -1) {
        perror("ftok");
        exit(1);
    }

    /* connect to (and possibly create) the segment: */
    if ((shared_mem_mid = shmget(key, SHM_SIZE, 0644 | IPC_CREAT)) == -1) {
        perror("shmget");
        exit(1);
    }

    /* attach to the segment to get a pointer to it: */
    gettimeofday(&t1, NULL);
    data = (char *) shmat(shared_mem_mid, (void *)0, 0);
    gettimeofday(&t2, NULL);
    if (data == (char *)(-1)) {
        perror("shmat");
        exit(1);
    }

    printf("Time to read the message from sharem memory: %g \n", (t2.tv_sec + t2.tv_usec/1000000.0)-(t1.tv_sec + t1.tv_usec/1000000.0));

    /* read or modify the segment, based on the command line: */
    if (argc == 2) {
        printf("writing to segment: \"%s\"\n", argv[1]);
        gettimeofday(&t3, NULL);
        strncpy(data, argv[1], SHM_SIZE);
        gettimeofday(&t4, NULL);
        printf("Time to send data to shared memory: %g \n", (t4.tv_sec + t4.tv_usec/1000000.0)-(t3.tv_sec + t3.tv_usec/1000000.0));
    } else{

        printf("segment contains: \"%s\"\n", data);
    }
    /* detach from the segment: */
    if (shmdt(data) == -1) {
        perror("shmdt");
        exit(1);
    }

    return 0;
}

Any idea?

Community
  • 1
  • 1
Elsban
  • 1,187
  • 2
  • 13
  • 24

2 Answers2

1

Your shared memory segments are marked as to be destroyed but still have process(es) attached to them.

Per the source code, the nattach column is 2 and the status is "dest", meaning the shared memory segments have 2 attachments and are marked to be destroyed once the last attached process detaches from the segment.

You need to either have the process(es) attached to the segments call shmdt() to detach from the shared memory segments, or you need kill those process(es). Once you do that the segments will be destroyed.

Andrew Henle
  • 32,625
  • 3
  • 24
  • 56
  • Can you give me a code example how I " either have the process(es) attached to the segments call shmdt() to detach from the shared memory segments". Thanks :) – Elsban Dec 02 '15 at 11:57
0

Have you tried (as root):

$ sync; echo 3 > /proc/sys/vm/drop_caches

Not sure this will free your shared memory, but you can try.

If you want to see an example, here goes a gist: https://gist.github.com/hudsantos/7fec7d9c34cc472b7f98

whoan
  • 8,143
  • 4
  • 39
  • 48
Hudson Santos
  • 155
  • 10
  • Could you please provide us with your 'simple application' source code? Not whole code, just key commands you are executing and getting that error. – Hudson Santos Dec 02 '15 at 11:02
  • I've executed your code and had no problem: hudson@vostrolab /tmp/c $ touch mach.c hudson@vostrolab /tmp/c $ ./a 4 Time to read the message from sharem memory: 1.38283e-05 writing to segment: "4" Time to send data to shared memory: 2.09808e-05 hudson@vostrolab /tmp/c $ ./a Time to read the message from sharem memory: 1.28746e-05 segment contains: "4" – Hudson Santos Dec 02 '15 at 12:40
  • That is normal, I have run this code many times before but now that shared memory is full I don't know how to free it. – Elsban Dec 02 '15 at 13:38