8105

Синхронизация процессов при помощи семафоров

Лабораторная работа

Информатика, кибернетика и программирование

Синхронизация процессов при помощи семафоров Цель работы: получить представление о синхронизации процессов в ОС UNIX при помощи флагов в разделяемой памяти и процессных семафоров. Иcпользуемые средства: ОС Linux, графическая оболочка KDE, среда разр...

Русский

2013-02-03

48 KB

5 чел.

Синхронизация процессов при помощи семафоров

Цель работы: получить представление о синхронизации процессов в ОС UNIX при помощи флагов в разделяемой памяти и процессных семафоров.

Иcпользуемые средства: ОС Linux, графическая оболочка KDE, среда разработки Anjuta, терминал.

1. Создать два процесса: приемник и передатчик. Передатчик увеличивает на единицу переменную целого типа в разделяемой памяти, а приемник выводит ее значение на экран. Для синхронизации использовать переменные в разделяемой памяти. Задать 100 повторений цикла обмена.

Передатчик:

#include <stdio.h>
#include <signal.h>
#include <sys/time.h>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <sys/types.h>
#include <sys/stat.h>
#define mem 0xABCD

int* c;
int dmem;
char* pmem;
int* f_t;
int* f_r;
int* end;
int main()
{
 dmem=shmget(mem,getpagesize(),IPC_CREAT|S_IRUSR|S_IWUSR);
 pmem=(
char*)shmat(dmem,0,0);
    c=(
int*)pmem;
  f_t=(
int*)(pmem+sizeof(int));
  f_r=(
int*)(pmem+sizeof(int)+sizeof(int));
  end=(
int*)(pmem+sizeof(int)+sizeof(int)+sizeof(int));
 printf(
"Go-o-o-o !!!\n\t");

 
while(!*end){
   *f_t=
1;               
   
while(!*f_r);         
   (*c)++;               
   printf(
"%d\n\t",*c);  
   *f_t=
0;               
   
while(*f_r);          
 }
 
if(!shmdt(pmem)) printf("MEMORY CLOSE ALL RIGHT\n");
   
else printf("MEMORY ERROR!!!\n");
 
return 0;
}

Приемник:

#include <stdio.h>
#include <signal.h>
#include <sys/time.h>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <sys/types.h>
#include <sys/stat.h>
#define mem 0xABCD

int* c;
int dmem;
char* pmem;
int* f_t;
int* f_r;
int* end;
int main()
{
 dmem=shmget(mem,getpagesize(),IPC_CREAT|S_IRUSR|S_IWUSR);
 pmem=(
char*)shmat(dmem,0,0);
    c=(
int*)pmem;
  f_t=(
int*)(pmem+sizeof(int));
  f_r=(
int*)(pmem+sizeof(int)+sizeof(int));
  end=(
int*)(pmem+sizeof(int)+sizeof(int)+sizeof(int));
 *c=
0;*f_t=0;*f_r=0;*end=0;
 printf(
"Priemnic on start\n\t");
 
while(*c<20)
   {
   
while(!*f_t);             
   *f_r=
1;                       
   
while(*f_t);                  
   printf(
"%d\n\t",*c);          
   *f_r=
0;                       
   }
 *end=
1;
 
return 0;
}

2. Выполнить обмен данными между процессами как в пункте 1, но для синхронизации использовать процессный семафор.

Передатчик:

#include <stdio.h>
#include <signal.h>
#include <sys/time.h>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/sem.h>
#define mem 0xABCD
#define sem 0x1234

int* c;
int dmem;
char* pmem;
int* end;
int idsem;
union semun {
 
int val;
 
struct semid_ds *buf;
 
unsigned short *array;
 
struct seminfo *__buf;
} semini;
struct sembuf smb;
int main()
{
 idsem=semget(sem,
1,IPC_CREAT|S_IRUSR|S_IWUSR);
 semini.val=
0;
 smb.sem_num=
0;
 semctl(idsem,
0,SETVAL,semini);
 dmem=shmget(mem,getpagesize(),IPC_CREAT|S_IRUSR|S_IWUSR);
 pmem=(
char*)shmat(dmem,0,0);
    c=(
int*)pmem;
  end=(
int*)(pmem+sizeof(int));
 printf(
"Go-o-o-o !!!\n");
 
while(!*end){
   smb.sem_op=
1;
   semop(idsem,&smb,
1);
   smb.sem_op=
0;
   semop(idsem,&smb,
1);
   (*c)++; printf(
"%d\n",*c);
   smb.sem_op=
1;
   semop(idsem,&smb,
1);
   smb.sem_op=
0;
   semop(idsem,&smb,
1);
 }
 
if(!shmdt(pmem)) printf("MEMORY CLOSE ALL RIGHT\n");
   
else printf("MEMORY ERROR!!!\n");
 semctl(idsem,
0,IPC_RMID,semini);
 
return 0;
}

Приемник:

#include <stdio.h>
#include <signal.h>
#include <sys/time.h>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/sem.h>
#define mem 0xABCD
#define sem 0x1234

int* c;
int dmem;
char* pmem;
int* end;
int idsem;
union semun {
 
int val;
 
struct semid_ds *buf;
 
unsigned short *array;
 
struct seminfo *__buf;
} semini;
struct sembuf smb;

int main()
{
 
idsem=semget(sem,1,IPC_CREAT|S_IRUSR|S_IWUSR);
 
semini.val=0;
 
smb.sem_num=0;
 
semctl(idsem,0,SETVAL,semini);
 
dmem=shmget(mem,getpagesize(),IPC_CREAT|S_IRUSR|S_IWUSR);
 
pmem=(char*)shmat(dmem,0,0);
    
c=(int*)pmem;
  
end=(int*)(pmem+sizeof(int));
 *
c=0;*end=0;
 
printf("Priemnic on start\n\t");
 
while(*c<1000)
   {
     
smb.sem_op=-1;
     
semop(idsem,&smb,1);
     
smb.sem_op=-1;
     
semop(idsem,&smb,1);
     
printf("%d\n",*c);
   }
 *
end=1;
 
return 0;
}

3. Создать 3 процесса: диспетчер, регулятор и модель и обеспечить их синхронизацию при помощи процессных семафоров таким образом, чтобы на каждые 5 шагов модели приходился один шаг регулятора. Модель на каждом шаге увеличивает на единицу переменную целого типа в разделяемой памяти, а регулятор выводит значение этой переменной на экран.

 

Диспетчер:

#include <stdio.h>
#include <signal.h>
#include <sys/time.h>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/sem.h>
#define mem 0xAAAA
#define sem 0x4567

int* c;
int* ch;
int dmem;
char* pmem;
int* end;
int idsem;
union semun {
 
int val;
 
struct semid_ds *buf;
 
unsigned short *array;
 
struct seminfo *__buf;
} semini;
struct sembuf smb;

int main()
{
 idsem=semget(sem,
3,IPC_CREAT|S_IRUSR|S_IWUSR);
 semini.val=
0;
 smb.sem_num=
0;
 semctl(idsem,
0,SETVAL,semini);
 smb.sem_num=
1;
 semctl(idsem,
1,SETVAL,semini);
 smb.sem_num=
2;
 semctl(idsem,
2,SETVAL,semini);

 dmem=shmget(mem,getpagesize(),IPC_CREAT|S_IRUSR|S_IWUSR);
 pmem=(
char*)shmat(dmem,0,0);
    c=(
int*)pmem;
  end=(
int*)(pmem+sizeof(int));
   ch=(
int*)(pmem+sizeof(int)+sizeof(int));

 printf(
"Dispetcher on start\n\n");

 smb.sem_num=
0;
 smb.sem_op=
2;
 semop(idsem,&smb,
1);

 
while(*c<500)
   {
   smb.sem_num=
1;
   smb.sem_op=
5;
   semop(idsem,&smb,
1);
   smb.sem_op=
0;
   semop(idsem,&smb,
1);


   smb.sem_num=
2;
   smb.sem_op=
1;
   semop(idsem,&smb,
1);
   smb.sem_op=
0;
   semop(idsem,&smb,
1);

   fprintf(stderr,
"\t| %d\t| %d\t|\n",*c,*ch);
   }
 *end=
1;
 printf(
"\t|_______|_______|\n\n");

 
if(!shmdt(pmem)) printf("MEMORY CLOSE ALL RIGHT\n");
   
else printf("MEMORY ERROR!!!\n");
 
if(!semctl(idsem,0,IPC_RMID,semini)) printf("SEMAFORS CLOSE ALL RIGHT\n");
   
else printf("SEMAFORS ERROR!!!\n");
 
return 0;
}

Передатчик:

#include <stdio.h>
#include <signal.h>
#include <sys/time.h>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/sem.h>
#define mem 0xAAAA
#define sem 0x4567

int* c;
int* ch;
int dmem;
char* pmem;
int* end;
int idsem;
union semun {
 
int val;
 
struct semid_ds *buf;
 
unsigned short *array;
 
struct seminfo *__buf;
} semini;
struct sembuf smb;

int main()
{
 idsem=semget(sem,
3,IPC_CREAT|S_IRUSR|S_IWUSR);
 semini.val=
0;
 smb.sem_num=
1;
 semctl(idsem,
1,SETVAL,semini);

 dmem=shmget(mem,getpagesize(),IPC_CREAT|S_IRUSR|S_IWUSR);
 pmem=(
char*)shmat(dmem,0,0);
    c=(
int*)pmem;
  end=(
int*)(pmem+sizeof(int));
   ch=(
int*)(pmem+sizeof(int)+sizeof(int));

 printf(
"Peredatchic on start\n\n");

 smb.sem_num=
0;
 smb.sem_op=-
1;
 semop(idsem,&smb,
1);


 
while(!*end)
   {
   smb.sem_num=
1;
   smb.sem_op=-
1;
   semop(idsem,&smb,
1);
   (*c)++;
   printf(
"\t| %d\t|\n",*c);
   }
 
return 0;
}

Приемник:

#include <stdio.h>
#include <signal.h>
#include <sys/time.h>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/sem.h>
#define mem 0xAAAA
#define sem 0x4567

int* c;
int* ch;
int dmem;
char* pmem;
int* end;
int idsem;
union semun {
 
int val;
 
struct semid_ds *buf;
 
unsigned short *array;
 
struct seminfo *__buf;
} semini;
struct sembuf smb;
int main()
{
 idsem=semget(sem,
3,IPC_CREAT|S_IRUSR|S_IWUSR);
 semini.val=
0;
 smb.sem_num=
2;
 semctl(idsem,
2,SETVAL,semini);

 dmem=shmget(mem,getpagesize(),IPC_CREAT|S_IRUSR|S_IWUSR);
 pmem=(
char*)shmat(dmem,0,0);
    c=(
int*)pmem;
  end=(
int*)(pmem+sizeof(int));
   ch=(
int*)(pmem+sizeof(int)+sizeof(int));
 *c=
0;*end=0;*ch=0;

 printf(
"Priemnic on start\n\n");
 smb.sem_num=
0;
 smb.sem_op=-
1;
 semop(idsem,&smb,
1);

 
while(!*end){
   smb.sem_num=
2;
   smb.sem_op=-
1;
   semop(idsem,&smb,
1);
   (*ch)++;
   fprintf(stderr,
"\t| %d\t|\n",*ch);
 }
 *end=
1;
 
return 0;
}


 

А также другие работы, которые могут Вас заинтересовать

57898. Геометричні перетворення: паралельне перенесення, осьова симетрія, центральна симетрія 984.5 KB
  Навчити учнів виконувати перетворення фігур на площині застосовувати властивості геометричних перетворень до розвязування задач. Перетворення допомагають художникам правильно будувати композиції картин а хімікам досліджувати структуру кристалів.
57899. РОЗВ’ЯЗУВАННЯ РАЦІОНАЛЬНИХ РІВНЯНЬ 170 KB
  Мета: вдосконалити знання і вміння учнів розвязувати раціональні рівняння; розвивати різні види мислення самостійність творчість екологічну культуру; виховувати активність увагу наполегливість винахідливість; прищеплювати любов до рідного краю.
57900. Решение систем уравнений второй степени 185.5 KB
  Задание: При каких значениях параметра а система уравнений имеет три решения Решение: парабола y= x2 будет иметь с окружностью x2 y2 = 4 три общие точки только в случае а = 2. Теоретический опрос по вопросам: Что называется системой...
57901. Систематизація та узагальнення знань, вмінь і навичок 183.5 KB
  Мета уроку: навчальна складова: систематизувати та узагальнити знання учнів з вивченого навчального матеріалу вміння та навички учнів застосовувати вивчене до розвязування задач передбачених програмою...
57902. ПЛОЩІ + ІСТОРІЯ + ДИЗАЙН = КРАСА 312.5 KB
  Сьогодні на уроці ми познайомимося з професіями паркетник та дизайнер інтерєру Паркетник-фахівець з укладання паркету в приміщеннях. План уроку Знайомство з історичними фактами: а історія паркету; б історія візерунків Росія...
57903. Тригонометричні функції будь-якого кута 878 KB
  Повторити властивості тригонометричних функцій закріпити навички співвідносити градусну та радіанну міру кута та знаходити значення тригонометричних функцій будьякого кута при обчислюванні значень виразів що містять тригонометричні функції з урахуванням їх властивостей.
57904. Функції. Узагальнення і систематизація вивченого матеріалу 539 KB
  Мета: узагальнити і систематизувати знання учнів з теми Квадратична функція; закріпити вміння і навички учнів використовувати набуті під час вивчення теми знання для розвязування вправ і задач розвивати увагу учнів логічне мислення творчу активність...
57905. Показательная функция. Показательные уравнения и неравенства 854.5 KB
  Цели: Обобщить, расширить и углубить знания учащихся по изученной теме Развивать творческие способности, умения самостоятельно добывать знания, активизировать познавательную деятельность, формировать навыки коллективной работы.
57906. Розвязування задач на рух за допомогою рівнянь 125 KB
  Мета: навчитися розвязувати задачі на рух за допомогою рівнянь; відпрацьовувати навички розвязування рівнянь та виконання арифметичних дій з раціональними числами; виконувати охайні записи у зошиті...