with Stringpack, Ada.Calendar;
use Stringpack, Ada.Calendar;

procedure Shared_Demo3 is

   Start_Work, End_Work: Time;

   N: Integer := 0;  --shared variable
   Anz: Positive := 1_000_000;

   task Binary_Semaphore is
      entry Wait;
      entry Signal;
   end Binary_Semaphore;

   task body Binary_Semaphore is
   begin
      loop
         accept Wait;
         accept Signal;
      end loop;
   end Binary_Semaphore;

   task Up is
      entry Start;
      entry Finish;
   end Up;

   task body Up is
      My_N: Integer;
   begin
      accept Start;
      for I in 1..Anz loop
         Binary_Semaphore.Wait;
         My_N := N;
         My_N := My_N+1;
         N := My_N;
         Binary_Semaphore.Signal;
      end loop;
      accept Finish;
   end Up;

   task Down is
      entry Start;
      entry Finish;
   end Down;

   task body Down is
      My_N: Integer;
   begin
      accept Start;
      for I in 1..Anz loop
         Binary_Semaphore.Wait;
         My_N := N;
         My_N := My_N-1;
         N := My_N;
         Binary_Semaphore.Signal;
      end loop;
      accept Finish;
   end Down;

begin
   Start_Work := Clock;  -- Zeiterfassung
   Up.Start; Down.Start;
   Up.Finish; Down.Finish;
   Print("n= " & N);
   End_Work := Clock;    -- Zeiterfassung
   Print("time spent= " & Float(Ada.Calendar."-"(End_Work, Start_Work)));
   abort Binary_Semaphore;  -- sehr schlechter Stil !!!!!!!!!!!!!!!
end Shared_Demo3;


