home *** CD-ROM | disk | FTP | other *** search
/ Programmer's ROM - The Computer Language Library / programmersrom.iso / ada / test / bnchdhry.ada < prev    next >
Encoding:
Text File  |  1988-05-03  |  18.0 KB  |  572 lines

  1. -------------------------------------------------------------------------------
  2. --                                                                           --
  3. --                   "DHRYSTONE" Benchmark Program                           --
  4. --                  --------------------------------                         --
  5. --                                                                           --
  6. --     Version: ADA/1                                                        --
  7. --                                                                           --
  8. --     Date:    04/15/84                                                     --
  9. --                                                                           --
  10. --     Author:  Reinhold P. Weicker                                          --
  11. --                                         --
  12. --     Filename:  DHRYADAA.DEC                             --
  13. --                                         --
  14. --     History:                                     --
  15. --                                         --
  16. --       CHANGE MADE                 BY WHOM               DATE             --
  17. --     -----------            ---------              -------           --
  18. --                                                                           --
  19. --       added timing calls         D. Sayon           13 Feb 85         --
  20. --        to write to file                                                   --
  21. --                                                                           --
  22. -------------------------------------------------------------------------------
  23. --                                                                           --
  24. --  The following program contains statements of a high-level programming    --
  25. --  language (Ada) in a distribution considered representative:              --
  26. --                                                                           --
  27. --    assignments                53%                                         --
  28. --    control statements         32%                                         --
  29. --    procedure, function calls  15%                                         --
  30.  
  31. --                                                                           --
  32. --  100 statements are dynamically executed.  The program is balanced with   --
  33. --  respect to the three aspects:                                            --
  34. --                                                                           --
  35. --    -statement type                                                        --
  36. --    -operand type (for simple data types)                                  --
  37. --    -operand access                                                        --
  38. --        operand global, local, parameter, or constant.                     --
  39. --                                                                           --
  40. --  The combination of these three aspects is balanced only approximately.   --
  41. --                                                                           --
  42. --  The program does not compute anything meaningful, but it is syntacially  --
  43. --  and semantically correct.  All variables have a value assigned to them   --
  44. --  before they are used as a source operand.                                --
  45. -------------------------------------------------------------------------------
  46. package Global_Def is
  47. ------------------
  48. --  Global type definitions
  49.  
  50. type Enumeration is (Ident_1,Ident_2,Ident_3,Ident_4,Ident_5);
  51.  
  52. subtype One_To_Thirty is integer range 1..30;
  53. subtype One_To_Fifty is integer range 1..50;
  54. subtype Capital_Letter is character range 'A'..'Z';
  55.  
  56. type String_30 is array(One_To_Thirty)of character;
  57.   pragma Pack(String_30);
  58.  
  59. type Array_1_Dim_Integer is array(One_To_Fifty)of integer;
  60. type Array_2_Dim_Integer is array(One_To_Fifty,
  61.                                   One_To_Fifty)of integer;
  62.  
  63. type Record_Type(Discr:Enumeration := Ident_1);
  64.  
  65. type Record_Pointer is access Record_Type;
  66.  
  67. type Record_Type(Discr:Enumeration := Ident_1)is
  68.     record
  69.       Pointer_Comp:      Record_Pointer;
  70.       case Discr is
  71.       when Ident_1 =>     -- only this variant is used,
  72.                           -- but in some cases discriminant
  73.                           -- checks are necessary
  74.  
  75.         Enum_Comp:       Enumeration;
  76.         Int_Comp:        One_To_Fifty;
  77.         String_Comp:     String_30;
  78.       when Ident_2 =>
  79.         Enum_Comp_2:     Enumeration;
  80.         String_Comp_2:   String_30;
  81.       when others =>
  82.         Char_Comp_1,
  83.         Char_Comp_2:     character;
  84.       end case;
  85.     end record;
  86.  
  87. end Global_Def;
  88.  
  89.   with Global_Def,Calendar;
  90.   use Global_Def,Calendar;
  91.  
  92. package Pack_1 is
  93. -------------
  94.  
  95.   procedure Proc_0(cycles: in integer; start_time, stop_time: out Float);
  96.   procedure Proc_1(Pointer_Par_in:  in      Record_Pointer);
  97.   procedure Proc_2(Int_Par_In_Out:  in out  One_To_Fifty);
  98.   procedure Proc_3(Pointer_Par_Out: out     Record_Pointer);
  99.  
  100.   Int_Glob:        integer;
  101.  
  102. end Pack_1;
  103.  
  104. with Global_Def;
  105. use Global_Def;
  106.  
  107. package Pack_2 is
  108. --------------
  109.  
  110.   procedure Proc_6 (Enum_Par_In:         in      Enumeration;
  111.                     Enum_Par_Out:        out     Enumeration);
  112.   procedure Proc_7 (Int_Par_In_1,
  113.                     Int_Par_In_2:        in      One_To_Fifty;
  114.                     Int_Par_Out:         out     One_To_Fifty);
  115.   procedure Proc_8 (Array_Par_In_Out_1:  in out  Array_1_Dim_Integer;
  116.                     Array_Par_In_Out_2:  in out  Array_2_Dim_Integer;
  117.                     Int_Par_In_1,
  118.                     Int_Par_In_2:        in      integer);
  119.   function Func_1  (Char_Par_In_1,
  120.                     Char_Par_In_2:       in      Capital_Letter)
  121.                                                  return Enumeration;
  122.   function Func_2  (String_Par_In_1,
  123.                     String_Par_In_2:     in      String_30)
  124.                                                    return boolean;
  125.  
  126. end Pack_2;      
  127.  
  128. with Global_Def,Pack_1,Text_IO, Help_Tools;
  129. use Global_Def, Text_IO, Help_Tools; 
  130.  
  131. procedure Dhryadaa is
  132. --------------
  133.  
  134. package real_io is new float_io(float); 
  135. use real_io;
  136.  
  137. package int_io is new integer_io(integer); 
  138. use int_io;
  139.  
  140. filename:    string (1..13);
  141.  
  142. int_rating,
  143. No_of_Cycles,
  144. No_of_Runs :    integer;
  145.  
  146. mean_rating,
  147. rating,
  148. mean_time,
  149. elapsed_time,
  150. start_time,
  151. stop_time:    float;
  152.  
  153. data_file:    file_type;
  154.  
  155. begin
  156.  
  157.  mean_time := 0.0;
  158.  mean_rating := 0.0;
  159.  No_of_Runs := 5;
  160.  
  161.  time_filename (filename);
  162.  filename(1) := 'D';
  163.  create (data_file,out_file,filename,"");
  164.  
  165.  read_environ(data_file);
  166.  
  167.  put("ADA Dhrystone Benchmark (DHRYADAA.DEC)"); new_line;
  168.  put(data_file,"ADA Dhrystone Benchmark (DHRYADAA.DEC)");new_line(data_file); 
  169.  
  170.  for N in 1..No_of_Runs loop  
  171.  
  172.   No_of_Cycles := N*100;  
  173.  
  174.   Pack_1.Proc_0(No_of_Cycles,start_time,stop_time);
  175.         -- Proc_0 is actually the main program, but it is part
  176.                 -- of a package, and a program within a package can
  177.                 -- not be designated as the Dhryadaa program for execution.
  178.                 -- Therefore Proc_0 is activated by a call from "Dhryadaa".
  179.  
  180. --
  181. --  WRITE OUT TIMING RESULTS
  182. --
  183. --
  184. --  write out start time
  185. --
  186.  
  187.   new_line; put (" Dhrystone start time: ");put (start_time, 5, 2, 0);
  188.   put (" seconds"); new_line;
  189.   new_line(data_file); put (data_file," Dhrystone start time: ");
  190.   put (data_file,start_time, 5, 2, 0);
  191.   put (data_file," seconds"); new_line(data_file);
  192.  
  193. --
  194. --  write out stop time
  195. --
  196.  
  197.   put (" Dhrystone stop time: ");put (stop_time, 5, 2, 0);
  198.   put (" seconds");new_line; 
  199.   put (data_file," Dhrystone stop time: ");
  200.   put (data_file,stop_time, 5, 2, 0);
  201.   put (data_file," seconds");
  202.   new_line(data_file);
  203.  
  204. --
  205. --  write out elapsed time
  206. --
  207.  
  208.   elapsed_time := stop_time - start_time;
  209.   put (" Elapsed time for ");put (no_of_cycles, 3);
  210.   put (" cycles: ");put(elapsed_time, 5,2,0); put(" seconds ");
  211.   new_line;
  212.   put (data_file," Elapsed time for ");
  213.   put (data_file,no_of_cycles, 3);
  214.   put (data_file," cycles: ");put(data_file,elapsed_time, 5,2,0); 
  215.   put (data_file," seconds ");
  216.   new_line(data_file);
  217.  
  218. --
  219. --  Sum the time in millisecs per cycle 
  220. --
  221.  
  222.   mean_time := mean_time + (elapsed_time*1000.0)/float(no_of_cycles);
  223.  
  224. --
  225. --  Compute the Dhrystone rating based on the time for the number
  226. --    of cycles just executed and write 
  227. --
  228. --   RATING =  (100 statements/cycle * number of cycles)/elapsed time
  229. --
  230.  
  231.   rating := (100.0*FLOAT(NO_OF_CYCLES))/ELAPSED_TIME;
  232.  
  233. --
  234. --  Sum Dhrystone rating
  235. --
  236.  
  237.   mean_rating := mean_rating + rating;
  238.   int_rating := integer(rating);
  239.   put (" Dhrystone rating:  "); put(int_rating);
  240.   put (" statement execution per unit time "); new_line;
  241.   put(data_file," Dhrystone rating:  ");
  242.   put(data_file, int_rating);
  243.   put(data_file," statement execution per unit time ");
  244.   new_line(data_file);
  245.  
  246.  end loop;
  247.  
  248. --
  249. --  Calculate the average time in millisecs per cycle
  250. --
  251.  
  252.  mean_time := mean_time/float(no_of_runs);
  253.  new_line; put (" Average time per cycle: "); put (mean_time,5,2,0);
  254.  put_line (" millisecs ");
  255.  new_line (data_file);
  256.  put (data_file," Average time per cycle: "); put (data_file,mean_time,5,2,0);
  257.  put (data_file," millisecs ");
  258.  
  259. --
  260. --  Calculate the average Dhrystone ratings
  261. --
  262.  
  263.  mean_rating := mean_rating/float(no_of_runs);
  264.  int_rating :=    integer(mean_rating);
  265.  
  266.  new_line; put(" Average Dhrystone rating: ");
  267.  put (int_rating);  put (" statement execution per unit time ");
  268.  new_line(data_file); put (data_file," Average Dhrystone rating: ");
  269.  put (data_file,int_rating);
  270.  put (data_file," statement execution per unit time ");
  271.  
  272.  close (data_file);
  273.  
  274. end Dhryadaa;
  275.  
  276. with Global_Def,Calendar,Pack_2;
  277. use Global_Def,Calendar;
  278.  
  279. package body Pack_1 is
  280. -----------
  281.  
  282.   Bool_Glob:         boolean;
  283.   Char_Glob_1,
  284.   Char_Glob_2:       character;
  285.   Array_Glob_1:      Array_1_Dim_Integer;
  286.   Array_Glob_2:      Array_2_Dim_Integer;
  287.   Pointer_Glob,
  288.   Pointer_Glob_Next: Record_Pointer;
  289.  
  290.   procedure Proc_4;
  291.   procedure Proc_5;
  292.  
  293. procedure Proc_0 (cycles: in integer;start_time,stop_time: out float)
  294. is
  295.   Int_Loc_1,
  296.   Int_Loc_2,
  297.   Int_Loc_3:     One_To_Fifty;
  298.   Char_Loc:      character;
  299.   Enum_Loc:      Enumeration;
  300.   String_Loc_1,
  301.   String_Loc_2: String_30; 
  302.  
  303.  
  304. begin
  305.   -- Initializations
  306.  
  307.   Pack_1.Pointer_Glob_Next := new Record_Type;
  308.   Pack_1.Pointer_Glob := new Record_Type
  309.                          '(
  310.                          Pointer_Comp =>Pack_1.Pointer_Glob_Next,
  311.                          Discr        =>Ident_1,
  312.                          Enum_Comp    =>Ident_3,
  313.                          Int_Comp     =>40,
  314.                          String_Comp  =>"DHRYSTONE PROGRAM, SOME STRING"
  315.                      );
  316.   String_Loc_1 := "DHRYSTONE PROGRAM, 1'ST STRING";
  317. -----------------
  318.  
  319. -- Start timer --
  320.  
  321.    Start_Time := float (seconds (clock));
  322. -----------------
  323. for N in 1..cycles loop
  324.   Proc_5;
  325.   Proc_4;
  326.     -- Char_Glob_1 = 'A',Char_Glob_2 = 'B',Bool_Glob = false
  327.   Int_Loc_1 := 2;
  328.   Int_Loc_2 := 3;
  329.   String_Loc_2 := "DHRYSTONE PROGRAM, 2'ND STRING";
  330.   Enum_Loc := Ident_2;
  331.   Bool_Glob := not Pack_2.Func_2(String_Loc_1,String_Loc_2);
  332.    -- Bool_Glob = true
  333.   while Int_Loc_1 < Int_Loc_2 loop --loop body executed once
  334.    Int_Loc_3 := 5 * Int_Loc_1 - Int_Loc_2;
  335.      -- Int_Loc_3 = 7
  336.    Pack_2.Proc_7 (Int_Loc_1,Int_Loc_2,Int_Loc_3);
  337.      -- Int_Loc_3 = 7
  338.    Int_Loc_1 := Int_Loc_1 + 1;
  339.   end loop;
  340.     -- Int_Loc_1 = 3
  341.   Pack_2.Proc_8(Array_Glob_1,Array_Glob_2,Int_Loc_1,Int_Loc_3);
  342.     -- Int_Glob = 5
  343.   Proc_1 (Pointer_Glob);
  344.   for Char_Index in 'A'..Char_Glob_2 loop --loop body executed twice
  345.     if Enum_Loc=Pack_2.Func_1(Char_Index,'C')
  346.     then--not executed
  347.       Pack_2.Proc_6(Ident_1,Enum_Loc);
  348.     end if;
  349.   end loop;
  350.     -- Enum_Loc = Ident_1
  351.     -- Int_Loc_1 = 3,Int_Loc_2 = 3,Int_Loc_3 = 7
  352.   Int_Loc_3 := Int_Loc_2 * Int_Loc_1;
  353.   Int_Loc_2 := Int_Loc_3 / Int_Loc_1;
  354.   Int_Loc_2 := 7 * (Int_Loc_3 - Int_Loc_2) - Int_Loc_1;
  355.   Proc_2(Int_Loc_1);
  356.  
  357. end loop;
  358. -----------------
  359.  
  360. -- Stop timer --
  361.  
  362.    Stop_Time := float (seconds(clock));
  363. -----------------
  364.  
  365. end Proc_0;
  366.  
  367. procedure Proc_1 (Pointer_Par_In: in Record_Pointer)
  368. is--executed once
  369.   Next_Record: Record_Type
  370.     renames Pointer_Par_In.Pointer_Comp.all;--=Pointer_Glob_Next.all
  371. begin
  372.   Next_Record := Pointer_Glob.all;
  373.   Pointer_Par_In.Int_Comp := 5;
  374.   Next_Record.Int_Comp := Pointer_Par_In.Int_Comp;
  375.   Next_Record.Pointer_Comp := Pointer_Par_In.Pointer_Comp;
  376.   Proc_3 (Next_Record.Pointer_Comp);
  377.     -- Next_Record.Pointer_Comp = Pointer_Glob.Pointer_Comp = Pointer_Glob_Next
  378.   if Next_Record.Discr = Ident_1
  379.   then -- executed
  380.      Next_Record.Int_Comp := 6;
  381.      Pack_2.Proc_6(Pointer_Par_In.Enum_Comp,Next_Record.Enum_Comp);
  382.      Next_Record.Pointer_Comp := Pointer_Glob.Pointer_Comp;
  383.      Pack_2.Proc_7(Next_Record.Int_Comp, 10, Next_Record.Int_Comp);
  384.   else  -- not executed
  385.      Pointer_Par_In.all := Next_Record;
  386.   end if;
  387. end Proc_1;
  388.  
  389. procedure Proc_2 (Int_Par_In_Out:in out One_To_Fifty)
  390. is -- executed once
  391.    -- In_Par_In_Out = 3,becomes 7
  392.   Int_Loc: One_To_Fifty;
  393.   Enum_Loc: Enumeration;
  394. begin
  395.   Int_Loc := Int_Par_In_Out + 10;
  396.   loop -- executed once
  397.     if Char_Glob_1 = 'A'
  398.     then -- executed
  399.       Int_Loc := Int_Loc - 1;
  400.       Int_Par_In_Out := Int_Loc - Int_Glob;
  401.       Enum_Loc := Ident_1;
  402.     end if;
  403.   exit when Enum_Loc = Ident_1; -- true
  404.   end loop;
  405. end Proc_2;
  406.  
  407. procedure Proc_3 (Pointer_Par_Out: out Record_Pointer)
  408. is -- executed once
  409.    -- Pointer_Par_Out becomes Pointer_Glob
  410. begin
  411.   if Pointer_Glob /= null
  412.   then -- executed
  413.     Pointer_Par_Out := Pointer_Glob.Pointer_Comp;
  414.   else -- not executed
  415.     Int_Glob := 100;
  416.   end if;
  417.   Pack_2.Proc_7(10,Int_Glob,Pointer_Glob.Int_Comp);
  418. end Proc_3;
  419.  
  420. procedure Proc_4 -- without parameters
  421. is -- executed once
  422.   Bool_Loc: boolean;
  423. begin
  424.   Bool_Loc := Char_Glob_1 = 'A';
  425.   Bool_Loc := Bool_Loc or Bool_Glob;
  426.   Char_Glob_2 := 'B';
  427. end Proc_4;
  428.  
  429. procedure Proc_5 -- without parameters
  430. is--executed once
  431. begin
  432.   Char_Glob_1 := 'A';
  433.   Bool_Glob := false;
  434. end Proc_5;
  435.  
  436. end Pack_1;
  437.  
  438. with Global_Def,Pack_1;
  439. use Global_Def;
  440.  
  441. package body Pack_2 is
  442. -------------------
  443. function Func_3(Enum_Par_In: in Enumeration)return boolean;
  444.          -- forward declaration
  445.  
  446. procedure Proc_6(Enum_Par_In:   in Enumeration;
  447.                  Enum_Par_Out:  out Enumeration)
  448. is -- executed once
  449.    -- Enum_Par_In = Ident_3,Enum_Par_Out becomes Ident_2
  450. begin
  451.   Enum_Par_Out := Enum_Par_In;
  452.   if not Func_3(Enum_Par_In)
  453.   then -- not executed
  454.     Enum_Par_Out := Ident_4;
  455.   end if;
  456.   case Enum_Par_In is
  457.     when Ident_1 => Enum_Par_Out := Ident_1;
  458.     when Ident_2 => if Pack_1.Int_Glob > 100
  459.                     then Enum_Par_Out := Ident_1;
  460.                     else Enum_Par_Out := Ident_4;
  461.                     end if;
  462.     when Ident_3 => Enum_Par_Out := Ident_2; -- executed
  463.     when Ident_4 => null;
  464.     when Ident_5 => Enum_Par_Out := Ident_3;
  465.   end case;
  466. end Proc_6;
  467. procedure Proc_7(Int_Par_In_1,
  468.                   Int_Par_In_2: in One_To_Fifty;
  469.                   Int_Par_Out:  out One_To_Fifty)
  470. is -- executed three times
  471.    -- first call:     Int_Par_In_1 = 2,Int_Par_In_2 = 3,
  472.    --                 Int_Par_Out becomes 7
  473.    -- second call:    Int_Par_In_1 = 6,Int_Par_In_2 = 10,
  474.    --                 Int_Par_Out becomes 18
  475.    -- third call:     Int_Par_In_1 = 10,Int_par_In_2 = 5,
  476.    --                 Int_Par_Out becomes 17
  477.   Int_Loc: One_To_Fifty;
  478. begin
  479.   Int_Loc := Int_Par_In_1 + 2;
  480.   Int_Par_Out := Int_Par_In_2 + Int_Loc;   
  481. end Proc_7;
  482. procedure Proc_8 (Array_Par_In_Out_1:in out Array_1_Dim_Integer;
  483.                   Array_Par_In_Out_2:in out Array_2_Dim_Integer;
  484.                   Int_Par_In_1,
  485.                   Int_Par_In_2:      in     integer)
  486. is -- executed once
  487.    -- Int_Par_In_1 = 3
  488.    -- Int_Par_In_2 = 7
  489.   Int_Loc:One_To_Fifty;
  490. begin
  491.   Int_Loc := Int_par_In_1 + 5;
  492.   Array_Par_In_Out_1(Int_Loc) := Int_Par_In_2;
  493.   Array_Par_In_Out_1(Int_Loc+1) :=
  494.                          Array_Par_In_Out_1 (Int_Loc);
  495.   Array_Par_In_Out_1(Int_Loc+30) := Int_Loc;
  496.   for Int_Index in Int_Loc .. Int_Loc+1 loop -- loop body executed twice
  497.     Array_Par_In_Out_2(Int_Loc,Int_Index) := Int_Loc;
  498.   end loop;
  499.   Array_Par_In_Out_2(Int_Loc,Int_Loc-1) :=
  500.                          Array_Par_In_Out_2(Int_Loc,Int_Loc-1)+1;
  501.   Array_Par_In_Out_2(Int_Loc+20,Int_Loc) :=
  502.                          Array_Par_In_Out_1(Int_Loc);
  503.   Pack_1.Int_Glob := 5;
  504. end Proc_8;
  505. function Func_1(Char_Par_In_1,
  506.                 Char_Par_In_2:in Capital_Letter)
  507.                                                return Enumeration
  508. is -- executed three times, returns Ident_1 each time
  509.    -- first call:  Char_Par_In_1 = 'H', Char_Par_In_2 = 'R'
  510.    -- second call: Char_Par_In_1 = 'A', Char_Par_In_2 = 'C'
  511.    -- third call:  Char_Par_In_1 = 'B', Char_Par_In_2 = 'C'
  512.   Char_Loc_1,Char_Loc_2:Capital_Letter;
  513. begin
  514.   Char_Loc_1 := Char_Par_In_1;
  515.   Char_Loc_2 := Char_Loc_1;
  516.   if Char_Loc_2 /= Char_Par_In_2
  517.   then-- executed
  518.     return Ident_1;
  519.   else-- not executed
  520.     return Ident_2;
  521.   end if;
  522.   end Func_1;
  523. function Func_2(String_Par_In_1,
  524.                 String_Par_In_2:in String_30)return boolean
  525. is -- executed once, returns false
  526.    -- String_Par_In_1 = "DHRYSTONE, 1'ST STRING"
  527.    -- String_Par_In_2 = "DHRYSTONE, 2'ND STRING"
  528.    Int_Loc:  One_To_Thirty;
  529.    Char_Loc: Capital_Letter;
  530. begin
  531.   Int_Loc := 2;
  532.   while Int_Loc<=2 Loop -- loop body executed once
  533.     if Func_1(String_Par_In_1(Int_Loc),
  534.               String_Par_In_2(Int_Loc+1)) = Ident_1
  535.     then-- executed
  536.       Char_Loc := 'A';
  537.       Int_Loc := Int_Loc + 1;
  538.     end if;
  539. end loop;
  540. if Char_Loc >= 'W' and Char_Loc < 'Z'
  541. then-- not executed
  542.    Int_Loc := 7;
  543. end if;
  544. if Char_Loc = 'X'
  545. then-- not executed
  546.       return true;
  547.     else -- executed
  548.       if String_Par_In_1 > String_Par_In_2
  549.       then -- not executed
  550.         Int_Loc := Int_Loc + 7;
  551.         return true;
  552.     else -- executed
  553.       return false;
  554.     end if;
  555.   end if;
  556. end Func_2;
  557.  
  558. function Func_3(Enum_Par_In: in Enumeration)return boolean
  559. is -- executed once, returns true
  560.    -- Enum_Par_In = Ident_3
  561.   Enum_Loc: Enumeration;
  562. begin
  563.   Enum_Loc := Enum_Par_In;
  564.   if Enum_Loc = Ident_3
  565.   then -- executed
  566.     return true;
  567.   end if;
  568. end Func_3;
  569.  
  570. end Pack_2;
  571.  
  572.