Простое межпроцессное взаимодействие - PullRequest
1 голос
/ 08 апреля 2019

Я хотел бы знать, какие функции Ada предлагает для реализации (простой) формы межпроцессного взаимодействия между двумя исполняемыми исполняемыми файлами (не задачами)? Я предполагаю, что оба исполняемых файла написаны на Аде.

Представьте себе, что один исполняемый файл считывает данные с датчика с регулярным интервалом a, а другой исполняемый файл заинтересован в обработке этих значений с регулярным интервалом b. Я думаю, что пакет Ada.Streams.Stream_IO можно использовать для сериализации и записи данных датчика в файл, но я не уверен, как можно синхронизировать операции записи (первый исполняемый файл) и чтения (второй исполняемый файл). Может ли прагма Shared_Passive быть использована для решения такого рода проблем?

Ответы [ 3 ]

4 голосов
/ 14 апреля 2019

Это моё решение для моего собственного вопроса. Я нашел это Ada Gem # 20 , описывающее использование прагмы Shared_Passive. Справочное руководство по GNAT предоставляет больше подробной информации .

Следующий исходный код демонстрирует обмен случайно сгенерированными данными датчика между записывающим устройством и программой датчика.

Файл: memory.ads

package Memory is

   pragma Shared_Passive;

   type Sensor_Storage_Type is
      record
         Sequence_Numer : Natural := 0;
         Humidity       : Float   := 0.0;
      end record;

   protected Shared is
      function Read return Sensor_Storage_Type;

      procedure Write (Humidity : Float);
   private
      Current_Value : Sensor_Storage_Type;
   end Shared;

end Memory;

Файл: memory.adb

package body Memory is

   protected body Shared is
      function Read return Sensor_Storage_Type is
      begin
         return Current_Value;
      end Read;

      procedure Write (Humidity : Float) is
      begin
         Current_Value.Sequence_Numer := Current_Value.Sequence_Numer + 1;

         Current_Value.Humidity := Humidity;
      end Write;
   end Shared;

end Memory;

Файл: sensor_writer.adb

with Ada.Text_IO;
with Ada.Numerics.Float_Random;

with Memory;

procedure Sensor_Writer is
   Generator : Ada.Numerics.Float_Random.Generator;

   package Float_IO is new Ada.Text_IO.Float_IO (Num => Float);

   Random_Humidity : Float;
begin
   while True loop
      Random_Humidity := Ada.Numerics.Float_Random.Random (Generator) * 100.0;

      Memory.Shared.Write (Random_Humidity);

      Ada.Text_IO.Put ("Wrote sensor value: ");
      Float_IO.Put (Random_Humidity, Exp => 0);
      Ada.Text_IO.New_Line;

      delay 5.0;
   end loop;
end Sensor_Writer;

Файл: sensor_reader.adb

with Ada.Text_IO;

with Memory;

procedure Sensor_Reader is
   Sensor_Value : Memory.Sensor_Storage_Type;
begin
   while True loop
      Sensor_Value := Memory.Shared.Read;

      Ada.Text_IO.Put_Line ("Read sensor values:");
      Ada.Text_IO.Put_Line ("    Sequence number: " & Sensor_Value.Sequence_Numer'Image);
      Ada.Text_IO.Put_Line ("    Humidity: " & Sensor_Value.Humidity'Image);

      delay 1.0;
   end loop;
end Sensor_Reader;
1 голос
/ 08 апреля 2019

Я думаю, что Приложение E может помочь вам, а точнее, E.2.3. Библиотеки интерфейса удаленного вызова .

Просто имейте в виду, что не все компиляторы реализуют спецификации Приложения,GNAT делает, но для другого компилятора я не знаю.

0 голосов
/ 10 апреля 2019

Другое решение для выполнения IPC между процессами заключается в использовании старого доброго POSIX IPC, такого как семафоры , общих запоминающих устройств и каналов , как реализовано в Флорист (я не нашел Флорист на сайте Adacore, поэтому мне интересно, сохраняется ли это до сих пор).

Плюсы:

  • Создание двух программ, говорящих друг с другом без сетевого стека
  • Программы могут быть на разных языках
  • Стандарт на ОС POSIX *

Минусы:

  • Довольно низкоуровневое программирование
  • Требуется выполнить синхронизацию вручную с использованием семафора

Пакеты для просмотра в Флорист POSIX.Generic_Shared_Memory , POSIX.IO и POSIX.Semaphores .

Примеры вы найдете на страницах Якоба Спарре Андерсена по POSIX

...