/**
@file shmUse.c
@author Mitch Richling <http://www.mitchr.me/>
@Copyright Copyright 1998 by Mitch Richling. All rights reserved.
@brief How to use a shared memory segment@EOL
@Keywords UNIX shared memory
@Std ISOC
This C program is intended to illustrate how one can
attach to an already existing shared memory segment,
read it's contents, and write new data into it.
@Tested
- Solaris 2.8
- MacOS X.2
- Linux (RH 7.3)
*/
#include <stdlib.h> /* Standard Lib ISOC */
#include <stdio.h> /* I/O lib ISOC */
#include <string.h> /* Strings ISOC */
#include <unistd.h> /* UNIX std stf POSIX */
#include <errno.h> /* error stf POSIX */
#include <sys/types.h> /* UNIX types POSIX */
#include <sys/ipc.h> /* Need for IPC POSIX */
#include <sys/shm.h> /* Shared Mem POSIX */
#include <ctype.h> /* Char classes ISOC */
int main(int argc, char *argv[]);
int main(int argc, char *argv[]) {
int shmId;
void *shmAdd;
int i;
key_t shmKey;
/* ftok generates a shared memory segment key. For more info about
ftok(), see the shmMake.c example program. */
shmKey = ftok("/tmp", 'm');
if (shmKey < 0) {
switch(errno) {
case EACCES: printf("ftok failed: Search permission denied for a component of the path prefix.\n");
break;
case ELOOP: printf("ftok failed: A loop exists in symbolic links in path argument or too many symlinks found.\n");
break;
case ENAMETOOLONG: printf("ftok failed: The length of path exceeds {PATH_MAX} or pathname component longer than {NAME_MAX}.\n");
break;
case ENOENT: printf("ftok failed: A component of path does not name an existing file or path is an empty string.\n");
break;
case ENOTDIR: printf("ftok failed: A component of the path not a directory.\n");
break;
default: printf("ftok failed: Duno why! (errno: %d)\n", errno);
break;
} /* end switch */
exit(1);
} /* end if */
/* We get a segment ID for our fixed key (see ftok for a SysV'ism for
generating shared memory segment keys. */
shmId = shmget(shmKey, 1024, 0);
if(shmId < 0) {
/* See shmMake.c for a more complete set of errno values to check.
We only check what is important in this case. */
switch(errno) {
case EACCES: printf("shmget failed: key already in use permission denied\n");
break;
case ENOENT: printf("shmget failed: IPC_CREAT was not set and segment doesn't already exist.\n");
break;
default: printf("shmget failed: Duno why!\n");
break;
} /* end switch */
exit(1);
} /* end if */
printf("shmget result: %d\n", shmId);
/* We have the shared segment ID, now we map it into our address space. */
shmAdd = shmat(shmId, NULL, 0);
if(((long)shmAdd) == -1) {
printf("ERROR: Could not attach to shared memory segment. Error code: %d\n", errno);
exit(1);
} else {
printf("Attached to shared mem segment: %ld\n", (long)shmAdd);
} /* end if */
/* Just print the printable chars in case the segment has binary junk in it... */
printf("The segment content: \n");
for(i=0;(i<1024)&&(((char *)shmAdd)[i]!=0);i++)
if(isalpha(((char *)shmAdd)[i]) || isdigit(((char *)shmAdd)[i]))
printf("%c", ((char *)shmAdd)[i]);
printf("\n");
/* Now we put other stuff into the segment. */
strcpy(shmAdd, "World");
/* One should detach from segments when done with them. */
if(shmdt(shmAdd)) {
printf("ERROR: shmdt failure. Error code: %d\n", errno);
} else {
printf("Detached from shared mem segment.\n");
} /* end if */
return 0;
} /* end func main() */
Generated by GNU Enscript 1.6.5.2.