/* Программа иллюстрирует
возможности системных вызовов shmat() и shmdt()
(операции над разделяемыми сегментами памяти) */
#include <stdio.h>
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/shm.h>
main ()
{
extern int errno;
int shmid, shmaddr, shmflg;
int flags, attach, detach, rtrn, i;
/* Цикл присоединений для данного процесса */
printf ("\nВведите число присоединений ");
printf ("для процесса (1-4): ");
scanf ("%d", &attach);
printf ("\nЧисло присоединений = %d\n", attach);
for (i = 0; i < attach; i++) {
/* Ввести идентификатор разделяемого сегмента */
printf ("\nВведите ид-р разделяемого сегмента,\n");
printf ("над которым нужно выполнить операции: ");
scanf ("%d", &shmid);
printf ("\nИд-р сегмента = %d\n", shmid);
/* Ввести адрес присоединения */
printf ("\nВведите адрес присоединения ");
printf ("в шестнадцатеричной записи: ");
scanf ("%x", &shmaddr);
printf ("\nАдрес присоединения = 0x%x\n", shmaddr);
/* Выбрать требуемые флаги */
printf ("\nВведите номер нужной комбинации флагов:\n");
printf (" SHM_RND = 1\n");
printf (" SHM_RDONLY = 2\n");
printf (" SHM_RND и SHM_RDONLY = 3\n");
printf (" Выбор = ");
scanf ("%d", &flags);
switch (flags) {
case 1:
shmflg = SHM_RND;
break;
case 2:
shmflg = SHM_RDONLY;
break;
case 3:
shmflg = SHM_RND | SHM_RDONLY;
break;
}
printf ("\nФлаги = 0%o", shmflg);
/* Выполнить системный вызов shmat */
rtrn = shmat (shmid, shmaddr, shmflg);
if (rtrn == -1) {
printf ("\nshmat завершился неудачей!\n");
printf ("\Код ошибки = %d\n", errno);
}
else {
printf ("\nshmat завершился успешно.\n");
printf ("Идентификатор shmid = %d\n", shmid);
printf ("Адрес = 0x%x\n", rtrn);
}
}
/* Цикл отсоединений для данного процесса */
printf ("\nВведите число отсоединений ");
printf ("для процесса (1-4): ");
scanf ("%d", &detach);
printf ("\nЧисло отсоединений = %d\n", detach);
for (i = 0; i < detach; i++) {
/* Ввести адрес отсоединения */
printf ("\nВведите адрес отсоединяемого сегмента ");
printf ("в шестнадцатеричной записи: ");
scanf ("%x", &shmaddr);
printf ("\nАдрес отсоединения = 0x%x\n", shmaddr);
/* Выполнить системный вызов shmdt */
rtrn = shmdt (shmaddr);
if (rtrn == -1) {
printf ("\nshmdt завершился неудачей!\n");
printf ("\Код ошибки = %d\n", errno);
}
else {
printf ("\nshmdt завершился успешно,\n");
printf ("идентификатор shmid = %d\n", shmid);
}
}
exit (0);
}