with Instrument;
use Instrument;

------------------------------------------------
-- Unconstrained Parameter Association 01 MEDIUM
------------------------------------------------

-- This test evaluates the code efficiency of a call to a procedure
-- that has a single formal in out parameter of an unconstrained array
-- type.  The bounds of the unconstrained formal parameter are not
-- known at compilation time but are derived at execution time from
-- those of the actual parameter Outer.  Outer is an object of the
-- constrained subtype MEDIUM_T.  (The test Unconstrained Parameter
-- Association 01 TINY uses the smaller subtype TINY_T.)

-- The procedure Param_Assoc_Test is called in the test version.  The
-- formal parameter is of the unconstrained type T_ARRAY.  The actual
-- parameter Outer is referenced inside the procedure through the formal
-- parameter to ensure that the required parameter passing is performed.
-- In the noise version, the procedure Param_Assoc_Noise is called, and
-- both the formal and actual parameters are constrained.  The metric
-- provided by this test is, therefore, the cost of passing an
-- unconstrained array minus the cost of passing a constrained array.

-- The conditional statement contains a never-executed else part to
-- ensure that the compiler must generate code for the procedure that is
-- not used in the then part.

procedure Uapab1 is
    package Pc_Cs is new Procs (Integer);
    use Pc_Cs;

    -- Array types

    type T_Array is array (Integer range <>) of T; -- unconstrained

    subtype Tiny_T is T_Array (-1 .. 1);           -- constrained
    subtype Medium_T is T_Array (-31 .. 31);         -- constrained


    Outer : Medium_T := (others => Init);
    Not_Used : Medium_T := (others => Init);

    procedure Param_Assoc_Test (Formal : in out T_Array) is
    begin
        Let (Global, Ident (Formal (Formal'First)));
    end Param_Assoc_Test;

    procedure Param_Assoc_Noise (Formal : in out Medium_T) is
    begin
        Let (Global, Ident (Formal (Formal'First)));
    end Param_Assoc_Noise;

begin
    Start ("UAPAB1",
           "Unconstrained Array Param. Assoc. w/63 elements (control)");
    for I in 1 .. 10000 loop

        Let (Global, Ident (Init));
        if Global = Ident (Init) then
            -- always TRUE
            --Param_Assoc_Test (Formal => Outer); -- included in test version
            Param_Assoc_Noise (Formal => Outer); -- included in noise version
        else
            Param_Assoc_Test (Formal => Not_Used);
            Param_Assoc_Noise (Formal => Outer);
        end if;

    end loop;
    Stop;

end Uapab1;