In order to create a new message queue, or access an existing queue, the shmget() system call is used.
SYSTEM CALL: shmget(); PROTOTYPE: int shmget ( key_t key, int size, int shmflg ); RETURNS: shared memory segment identifier on success -1 on error: errno = EINVAL (Invalid segment size specified) EEXIST (Segment exists, cannot create) EIDRM (Segment is marked for deletion, or was removed) ENOENT (Segment does not exist) EACCES (Permission denied) ENOMEM (Not enough memory to create segment) NOTES:
The first argument to shmget() is the key value (in our case returned by a call to ftok()). This key value is then compared to existing key values that exist within the kernel for other shared memory segments. At that point, the open or access operation is dependent upon the contents of the shmflg argument.
Create the segment if it doesn't already exist in the kernel.
When used with IPC_CREAT, fail if segment already exists.
If IPC_CREAT is used alone, shmget() either returns the segment identifier for a newly created segment, or returns the identifier for a segment which exists with the same key value. If IPC_EXCL is used along with IPC_CREAT, then either a new segment is created, or if the segment exists, the call fails with -1. IPC_EXCL is useless by itself, but when combined with IPC_CREAT, it can be used as a facility to guarantee that no existing segment is opened for access.
Once again, an optional octal mode may be OR'd into the mask.
Let's create a wrapper function for locating or creating a shared memory segment :
int open_segment( key_t keyval, int segsize ) { int shmid; if((shmid = shmget( keyval, segsize, IPC_CREAT | 0660 )) == -1) { return(-1); } return(shmid); }
Once a process has a valid IPC identifier for a given segment, the next step is for the process to attach or map the segment into its own addressing space.