Программа client читает данные (числа) из файла и записывает их в область разделяемой памяти. Программа server читает данные из разделяемой памяти, суммирует их и записывает результат в файл. Внимание! Для получения ключа необходимо создать файл с именем “sem” в каталоге программы.
Текст программы
Файл server.c
#include"shmem.h" //описание структуры семафоров и памяти
FILE *fd; //дескриптор файла результатов
int i; //счетчик
float sum=0; //сумма чисел
mem_sh *memptr; //указатель на структуру разделяемой памяти
key_t key; //ключ доступа к семафору
int shmid; //дескриптор разделяемой памяти
int semid; //дескриптор семафора
int main(void)
{
printf("\n\t\t.:SERVER:.\n");
key=ftok("sem",'A'); //получаем ключ для сервера
shmid=shmget(key,100,IPC_CREAT|PERM); //получаем деск. разделяемой памяти
memptr=(mem_sh*) shmat (shmid,0,0);//присоединяем память к памяти сервера
semid=semget(key,1,IPC_CREAT|PERM); //получаем деск. семафоров сервера
semop(semid,&mem_trylock[0],1); //пытаемся опустить семафор памяти
//(пытаемся заблокировать доступ к памяти)
if ((fd=fopen("result.txt","w"))==NULL) //создаём файл результатов
{perror("\n\tError (server - fopen)\n");return 0;}
printf("\n\tOpen(Create) result file\n");
for(i=0;i<6;i++) sum=sum+memptr->cord[i]; //читаем содержимое памяти и
printf("\tResult = %f\n",sum); //накапливаем сумму
if ((fprintf(fd,"Sum=%f \n",sum))<=0) //записываем сумму в файл
{perror("\n\tError (server - fprintf)\n");return 0;}
printf("\tResult has writen to file\n");
fclose(fd); //закрываем дескриптор файла результатов
shmdt(memptr); //отсоединяем разделяемую память от сервера
shmctl(shmid,IPC_RMID,0); //удаляем дескриптор памяти
semctl(semid,0,IPC_RMID); //удаляем дескриптор семафоров сервера
return 0;
}
Файл client.c
#include"shmem.h" //описание структуры семафоров и памяти
FILE *fd; //дескриптор файла данных
int i; //счётчик
float mas[6]; //массив из шести вещественных чисел
mem_sh *memptr; //указатель на область разделяемой памяти
key_t key; //ключ семафора
int shmid; //дескриптор разделяемой памяти
int semid; //дескриптор семафора
int main(void)
{
printf("\n\t\t.:CLIENT:.\n");
key=ftok("sem",'A'); //получаем ключ
shmid=shmget(key,100,PERM); //получаем дескриптор разделяемой памяти
memptr=(mem_sh*) shmat (shmid,0,0);//присоединяем память к памяти клиента
semid=semget(key,1,PERM); //получаем деск. набора семафоров для сервера
if ((fd=fopen("data.txt","r+"))==NULL) //открываем файл для чтения
{perror("\n\tError (client - fopen)\n");return 0;}
printf("\n\tOpen data file\n");
while ((fscanf(fd,"%f %f %f %f %f %f ",&mas[0],&mas[1], //читаем числа
&mas[2],&mas[3],&mas[4],&mas[5]))!=EOF) //пока не конец файла
{
printf("\tContent of data file:\n");
printf("\t%f %f %f %f %f %f\n",mas[0],mas[1],mas[2],mas[3],mas[4],mas[5]);
for (i=0;i<6;i++) memptr->cord[i]=mas[i]; //заносим числа в массив
} //структуры которая находится в разделяемой памяти
semop(semid,&mem_unlock[0],1); //разблокируем память для сервера
shmdt(memptr); //отсоединяем разделяемую память от памяти клиента
shmctl(shmid,IPC_RMID,0); //закрываем дескриптор разделяемой памяти
semctl(semid,0,IPC_RMID); //закрываем дескриптор семафора
fclose(fd); //закрываем дескриптор файла данных
return 0;
}
Файл shmem.h
#include <stdio.h>
#include <sys/types.h>
#include <sys/sem.h>
#include <sys/shm.h>
#include <sys/ipc.h>
#define MAXBUF 80 //максимальный размер буфера
#define PERM 0777 //права доступа к памяти
typedef struct mem_msg //структура разделяемой памяти
{
float cord[6]; //массив из шести вещественных чисел
}mem_sh; //тип структуры
static struct sembuf mem_trylock[1]={0,-1,0}; //блокировка памяти
static struct sembuf mem_unlock[1]={0,1,0}; //разблокировка памяти
ЛАБОРАТОРНАЯ РАБОТА 9