Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
лекции иртегова / Лекция 10 - System V IPC.doc
Скачиваний:
49
Добавлен:
06.06.2015
Размер:
207.36 Кб
Скачать
      1. Операции над набором семафоров — Пример (продолжение)

Код, приведенный в этом примере, представляет собой часть той же программы, что и пре­дыдущий пример. Он демонстрирует, как оперировать с двумя семафорами в наборе од­новременно.

Фрагмент программы работает так:

... Имя команды определяет принтер, который нужно использовать.

56-61 Две командные структуры установлены так, чтобы уменьшить на 1 первый семафор и семафор, связанный с принтером с номером prnnum. Заметьте, что исполь­зуется флаг SEM_UNDO. Вспомните, что номер семафора, над которым должна быть выполнена операция, содержится в командной структуре.

62-66 Здесь выполняется операция над двумя семафорами одновременно. Эта операция захватит принтер, который должен быть использован. Другой процесс, ис­полняющий этот же код, будет заблокирован до тех пор, пока значение сема­фора не увеличится.

79-85 Командные структуры для обоих семафоров изменены так, чтобы увеличить значение семафоров на 1. Оба семафора изменяются "одновременно", т.е. ни один другой процесс не получит управления в промежутке между их изменениями.

Эта программа демонстрируется так:

$ ln printer lineprntr
$ ln printer laseprntr$ PRINTER1=/dev/tty05$ PRINTER2=/tmp/xyz$ export PRINTER1 PRINTER2$ lineprntr data & lineprntr data & wait390939101ABCDEFGHIJKLMNOPQRSTUVWXYZ2ABCDEFGHIJKLMNOPQRSTUVWXYZ3ABCDEFGHIJKLMNOPQRSTUVWXYZ4ABCDEFGHIJKLMNOPQRSTUVWXYZ1ABCDEFGHIJKLMNOPQRSTUVWXYZ2ABCDEFGHIJKLMNOPQRSTUVWXYZ3ABCDEFGHIJKLMNOPQRSTUVWXYZ4ABCDEFGHIJKLMNOPQRSTUVWXYZ$ ipcs -sIPC status from /dev/kmem as of Tue Mar  3 11:18:53 1987T     ID     KEY        MODE       OWNER    GROUPSemaphores:s    100 0x7304001a --ra-ra-ra-      jeg    unixc$ ipcrm -s 100Файл: printer.cОПЕРАЦИИ НАД НАБОРОМ СЕМАФОРОВ - ПРИМЕР1  #include <stdlib.h>2  #include <string.h>3  #include <unistd.h>4  #include <fcntl.h>5  #include <sys/types.h>6  #include <sys/ipc.h>7  #include <sys/sem.h>8  #include <stdio.h>9  #include "printer.h"1011  main(int argc, char *argv[])12  {...17      struct sembuf operation[2];...56      operation[1].sem_num = prntnum;57      operation[1].sem_op = ACQUIRE;58      operation[1].sem_flg = SEM_UNDO;59      operation[0].sem_num = 0;60      operation[0].sem_op = ACQUIRE;61      operation[0].sem_flg = SEM_UNDO;62      if(semop(semid, operation, 2) == -1) {63         sprintf(errmsg,"%s - ACQUIRE",argv[0]);64         perror(errmsg);65         exit(4);66      }...79      operation[1].sem_op = RELEASE;80      operation[0].sem_op = RELEASE;81      if(semop(semid, operation, 2) == -1) {82         sprintf(errmsg,"%s - RELEASE",argv[0]);83         perror(errmsg);84         exit(7);85      }...87  }

      1. Разделяемая память

Разделяемая память System V IPC позволяет двум или более процессам разделять память и, следовательно, находящиеся в ней данные. Это достигается помещением в виртуальное ад­ресное пространство процессов одной и той же физической памяти.

Того же эффекта можно достичь, отобразив в память при помощи mmap(2) доступный на за­пись файл в режиме MAP_SHARED. Как и в случае mmap(2), разделяемые сегменты не обя­зательно будут отображены на одни и те же адреса в разных процессах.

Главным практическим отличием разделяемой памяти System V IPC от mmap(2) является то, что для mmap(2) нужен файл, а память System V IPC ни к какому файлу не привязана. Кроме того, использование mmap(2) с флагом MAP_SHARED приводит к тому, что система синхро­низует содержимое памяти с диском, что может снизить общую производительность систе­мы. Если вам нужно сохранить содержимое разделяемой памяти после завершения работы всех процессов приложения, mmap(2) оказывается удобнее, но на практике такая потреб­ность возникает довольно редко. Поэтому разделяемая память System V IPC до сих пор ши­роко применяется многими приложениями.

В последние годы, разделяемая память вытесняется многопоточными программами. С опре­деленными оговорками, с точки зрения программиста, потоки можно рассматривать как про­цессы, у которых вся память разделяется.

Этот раздел показывает, как создавать и использовать сегмент разделяемой памяти. Это вы­полняется следующими системными вызовами.

. shmget

. shmat

. shmdt

. shmctl