This change affects only back-end inlining and is two-fold: 1. It lifts in a 3rd place the limitation associated with nested subprograms as well as with a couple of other constructs. After it is applied, the only significant limitation left are the nested packages.
2. It makes sure the errors associated with pragma Inline_Always are issued whatever the optimization level, which is in keeping with its semantics. It makes it possible to inline/reject consistently at all optimization levels subprograms marked with pragma Inline_Always, for example: package Q is procedure Test (I : Integer); pragma Inline_Always (Test); end Q; package body Q is procedure Test (I : Integer) is -- Uncomment to make it compile -- function F (J : Integer) return Integer; -- pragma Inline_Always (F); function F (J : Integer) return Integer is begin return I - J; end; begin if I /= F (I) then raise Program_Error; end if; end; end Q; Tested on x86_64-pc-linux-gnu, committed on trunk 2014-10-31 Eric Botcazou <ebotca...@adacore.com> * inline.adb (Has_Excluded_Declaration): With back-end inlining, only return true for nested packages. (Cannot_Inline): Issue errors/warnings whatever the optimization level for back-end inlining and remove assertion.
Index: inline.adb =================================================================== --- inline.adb (revision 216960) +++ inline.adb (working copy) @@ -1225,10 +1225,8 @@ Error_Msg_NE (Msg & "p?", N, Subp); end if; - return; + -- New semantics relying on back end inlining - -- New semantics - elsif Is_Serious then -- Remove last character (question mark) to make this into an error. @@ -1242,10 +1240,8 @@ Set_Is_Inlined_Always (Subp, False); Error_Msg_NE (Msg & "p?", N, Subp); - -- Do not issue errors/warnings when compiling with optimizations + else - elsif Optimization_Level = 0 then - -- Do not emit warning if this is a predefined unit which is not -- the main unit. This behavior is currently provided for backward -- compatibility but it will be removed when we enforce the @@ -1281,24 +1277,13 @@ Error_Msg_NE (Msg (Msg'First .. Msg'Last - 1), N, Subp); - else pragma Assert (Front_End_Inlining); + else Set_Is_Inlined (Subp, False); - -- When inlining cannot take place we must issue an error. - -- For backward compatibility we still report a warning. - if Ineffective_Inline_Warnings then Error_Msg_NE (Msg & "p?", N, Subp); end if; end if; - - -- Compiling with optimizations enabled it is too early to report - -- problems since the backend may still perform inlining. In order - -- to report unhandled inlinings the program must be compiled with - -- -Winline and the error is reported by the backend. - - else - null; end if; end Cannot_Inline; @@ -3327,12 +3312,26 @@ D := First (Decls); while Present (D) loop - if Nkind (D) = N_Subprogram_Body then + -- First declarations universally excluded + + if Nkind (D) = N_Package_Declaration then Cannot_Inline - ("cannot inline & (nested subprogram)?", + ("cannot inline & (nested package declaration)?", D, Subp); return True; + elsif Nkind (D) = N_Package_Instantiation then + Cannot_Inline + ("cannot inline & (nested package instantiation)?", + D, Subp); + return True; + end if; + + -- Then declarations excluded only for front end inlining + + if Back_End_Inlining then + null; + elsif Nkind (D) = N_Task_Type_Declaration or else Nkind (D) = N_Single_Task_Declaration then @@ -3349,9 +3348,9 @@ D, Subp); return True; - elsif Nkind (D) = N_Package_Declaration then + elsif Nkind (D) = N_Subprogram_Body then Cannot_Inline - ("cannot inline & (nested package declaration)?", + ("cannot inline & (nested subprogram)?", D, Subp); return True; @@ -3368,12 +3367,6 @@ ("cannot inline & (nested procedure instantiation)?", D, Subp); return True; - - elsif Nkind (D) = N_Package_Instantiation then - Cannot_Inline - ("cannot inline & (nested package instantiation)?", - D, Subp); - return True; end if; Next (D);