]> gcc.gnu.org Git - gcc.git/commitdiff
exp_ch6.adb (Expand_Call): Add comment on handling of back end intrinsic
authorArnaud Charlet <charlet@gcc.gnu.org>
Wed, 8 Dec 2004 11:27:00 +0000 (12:27 +0100)
committerArnaud Charlet <charlet@gcc.gnu.org>
Wed, 8 Dec 2004 11:27:00 +0000 (12:27 +0100)
* exp_ch6.adb (Expand_Call): Add comment on handling of back end
intrinsic

* exp_intr.adb (Expand_Intrinsic_Call): Ignore unrecognized intrinsic,
leaving call unchanged.
This deals with the case where the pragma Import specified
an external name, to be handled by the back end.

* sem_prag.adb (Process_Import_Or_Interface): Do not check validity of
subprogram which is Imported with convention Intrinsic if an
External_Name argument is specified.
(Process_Import_Or_Interface): Properly diagnose link name argument.
(Inlining_Not_Possible): New name for Cannot_Inline, to avoid confusion
with Sem_Ch6.Cannot_Inline.
(Process_Inline): Provide separate warning for inapplicable inline
pragma.
(Cannot_Inline): Reject subprograms that have an at_end handler, so that
treatment is uniform on different targets.

From-SVN: r91882

gcc/ada/exp_ch6.adb
gcc/ada/exp_intr.adb
gcc/ada/sem_prag.adb

index be9463ba1a201b25c2f7be9edbadacefca4f3659..0b6447aad4ee142e26976636f10d8e4e15936d9e 100644 (file)
@@ -1051,7 +1051,7 @@ package body Exp_Ch6 is
          end if;
       end if;
 
-      --  The call node itself is re-analyzed in Expand_Call.
+      --  The call node itself is re-analyzed in Expand_Call
 
    end Expand_Actuals;
 
@@ -1974,6 +1974,10 @@ package body Exp_Ch6 is
       --  appropriate expansion to the corresponding tree node and we
       --  are all done (since after that the call is gone!)
 
+      --  In the case where the intrinsic is to be processed by the back end,
+      --  the call to Expand_Intrinsic_Call will do nothing, which is fine,
+      --  since the idea in this case is to pass the call unchanged.
+
       if Is_Intrinsic_Subprogram (Subp) then
          Expand_Intrinsic_Call (N, Subp);
          return;
@@ -2300,7 +2304,7 @@ package body Exp_Ch6 is
       Temp_Typ : Entity_Id;
 
       procedure Make_Exit_Label;
-      --  Build declaration for exit label to be used in Return statements.
+      --  Build declaration for exit label to be used in Return statements
 
       function Process_Formals (N : Node_Id) return Traverse_Result;
       --  Replace occurrence of a formal with the corresponding actual, or
@@ -2331,7 +2335,7 @@ package body Exp_Ch6 is
 
       procedure Make_Exit_Label is
       begin
-         --  Create exit label for subprogram, if one doesn't exist yet.
+         --  Create exit label for subprogram if one does not exist yet
 
          if No (Exit_Lab) then
             Lab_Id := Make_Identifier (Loc, New_Internal_Name ('L'));
@@ -2509,15 +2513,13 @@ package body Exp_Ch6 is
          elsif Nkind (N) = N_Identifier
            and then Nkind (Parent (Entity (N))) = N_Object_Declaration
          then
-
-            --  The block assigns the result of the call to the temporary.
+            --  The block assigns the result of the call to the temporary
 
             Insert_After (Parent (Entity (N)), Blk);
 
          elsif Nkind (Parent (N)) = N_Assignment_Statement
            and then Is_Entity_Name (Name (Parent (N)))
          then
-
             --  Replace assignment with the block
 
             declare
@@ -2660,7 +2662,7 @@ package body Exp_Ch6 is
          Set_Declarations (Blk, New_List);
       end if;
 
-      --  If this is a derived function, establish the proper return type.
+      --  If this is a derived function, establish the proper return type
 
       if Present (Orig_Subp)
         and then Orig_Subp /= Subp
@@ -2797,7 +2799,7 @@ package body Exp_Ch6 is
             Targ := Name (Parent (N));
 
          else
-            --  Replace call with temporary, and create its declaration.
+            --  Replace call with temporary and create its declaration
 
             Temp :=
               Make_Defining_Identifier (Loc, New_Internal_Name ('C'));
@@ -2815,7 +2817,7 @@ package body Exp_Ch6 is
          end if;
       end if;
 
-      --  Traverse the tree and replace  formals with actuals or their thunks.
+      --  Traverse the tree and replace formals with actuals or their thunks.
       --  Attach block to tree before analysis and rewriting.
 
       Replace_Formals (Blk);
@@ -2879,7 +2881,7 @@ package body Exp_Ch6 is
 
       Restore_Env;
 
-      --  Cleanup mapping between formals and actuals, for other expansions.
+      --  Cleanup mapping between formals and actuals for other expansions
 
       F := First_Formal (Subp);
 
@@ -3493,9 +3495,9 @@ package body Exp_Ch6 is
             end loop;
          end if;
 
-      --  For a function, we must deal with the case where there is at
-      --  least one missing return. What we do is to wrap the entire body
-      --  of the function in a block:
+      --  For a function, we must deal with the case where there is at least
+      --  one missing return. What we do is to wrap the entire body of the
+      --  function in a block:
 
       --    begin
       --      ...
@@ -3732,7 +3734,7 @@ package body Exp_Ch6 is
       if Is_Subprogram (Proc)
         and then Proc /= Corr
       then
-         --  Protected function or procedure.
+         --  Protected function or procedure
 
          Set_Entity (Rec, Param);
 
index 7f99eb5ad0bddd65849a1683654a990e20aa305e..8f4170495207715e80edef2550a16992688c6a80 100644 (file)
@@ -281,12 +281,21 @@ package body Exp_Intr is
       then
          Expand_Source_Info (N, Nam);
 
-      else
-         --  Only other possibility is a renaming, in which case we expand
-         --  the call to the original operation (which must be intrinsic).
+         --  If we have a renaming, expand the call to the original operation,
+         --  which must itself be intrinsic, since renaming requires matching
+         --  conventions and this has already been checked.
 
-         pragma Assert (Present (Alias (E)));
+      elsif Present (Alias (E)) then
          Expand_Intrinsic_Call (N,  Alias (E));
+
+         --  The only other case is where an external name was specified,
+         --  since this is the only way that an otherwise unrecognized
+         --  name could escape the checking in Sem_Prag. Nothing needs
+         --  to be done in such a case, since we pass such a call to the
+         --  back end unchanged.
+
+      else
+         null;
       end if;
    end Expand_Intrinsic_Call;
 
index e21038f054d2bfde45fce5a88d0567cee276b2e3..9691ebbc1db7ea01e32f0e29766726d199413784 100644 (file)
@@ -2965,13 +2965,34 @@ package body Sem_Prag is
                else
                   Set_Imported (Def_Id);
 
-                  --  If Import intrinsic, set intrinsic flag and verify
-                  --  that it is known as such.
+                  --  Special processing for Convention_Intrinsic
 
                   if C = Convention_Intrinsic then
+
+                     --  Link_Name argument not allowed for intrinsic
+
+                     if Present (Arg3)
+                       and then Chars (Arg3) = Name_Link_Name
+                     then
+                        Arg4 := Arg3;
+                     end if;
+
+                     if Present (Arg4) then
+                        Error_Pragma_Arg
+                          ("Link_Name argument not allowed for " &
+                           "Import Intrinsic",
+                           Arg4);
+                     end if;
+
                      Set_Is_Intrinsic_Subprogram (Def_Id);
-                     Check_Intrinsic_Subprogram
-                       (Def_Id, Expression (Arg2));
+
+                     --  If no external name is present, then check that
+                     --  this is a valid intrinsic subprogram. If an external
+                     --  name is present, then this is handled by the back end.
+
+                     if No (Arg3) then
+                        Check_Intrinsic_Subprogram (Def_Id, Expression (Arg2));
+                     end if;
                   end if;
 
                   --  All interfaced procedures need an external symbol
@@ -3073,24 +3094,29 @@ package body Sem_Prag is
          procedure Set_Inline_Flags (Subp : Entity_Id);
          --  Sets Is_Inlined and Has_Pragma_Inline flags for Subp
 
-         function Cannot_Inline (Subp : Entity_Id) return Boolean;
-         --  Do not set the inline flag if body is available and contains
-         --  exception handlers, to prevent undefined symbols at link time.
-         --  Emit warning if front-end inlining is enabled and the pragma
-         --  appears too late.
+         function Inlining_Not_Possible (Subp : Entity_Id) return Boolean;
+         --  Returns True if it can be determined at this stage that inlining
+         --  is not possible, for examle if the body is available and contains
+         --  exception handlers, we prevent inlining, since otherwise we can
+         --  get undefined symbols at link time. This function also emits a
+         --  warning if front-end inlining is enabled and the pragma appears
+         --  too late.
+         --  ??? is business with link symbols still valid, or does it relate
+         --  to front end ZCX which is being phased out ???
 
-         -------------------
-         -- Cannot_Inline --
-         -------------------
+         ---------------------------
+         -- Inlining_Not_Possible --
+         ---------------------------
 
-         function Cannot_Inline (Subp : Entity_Id) return Boolean is
-            Decl : constant Node_Id := Unit_Declaration_Node (Subp);
+         function Inlining_Not_Possible (Subp : Entity_Id) return Boolean is
+            Decl  : constant Node_Id := Unit_Declaration_Node (Subp);
+            Stats : Node_Id;
 
          begin
             if Nkind (Decl) = N_Subprogram_Body then
-               return
-                 Present
-                   (Exception_Handlers (Handled_Statement_Sequence (Decl)));
+               Stats := Handled_Statement_Sequence (Decl);
+               return Present (Exception_Handlers (Stats))
+                 or else Present (At_End_Proc (Stats));
 
             elsif Nkind (Decl) = N_Subprogram_Declaration
               and then Present (Corresponding_Body (Decl))
@@ -3112,18 +3138,22 @@ package body Sem_Prag is
                   return False;
 
                else
+                  Stats :=
+                    Handled_Statement_Sequence
+                        (Unit_Declaration_Node (Corresponding_Body (Decl)));
+
                   return
-                    Present (Exception_Handlers
-                      (Handled_Statement_Sequence
-                        (Unit_Declaration_Node (Corresponding_Body (Decl)))));
+                    Present (Exception_Handlers (Stats))
+                      or else Present (At_End_Proc (Stats));
                end if;
+
             else
                --  If body is not available, assume the best, the check is
                --  performed again when compiling enclosing package bodies.
 
                return False;
             end if;
-         end Cannot_Inline;
+         end Inlining_Not_Possible;
 
          -----------------
          -- Make_Inline --
@@ -3137,8 +3167,10 @@ package body Sem_Prag is
             if Etype (Subp) = Any_Type then
                return;
 
-            elsif Cannot_Inline (Subp) then
-               Applies := True;    --  Do not treat as an error.
+            --  If inlining is not possible, for now do not treat as an error
+
+            elsif Inlining_Not_Possible (Subp) then
+               Applies := True;
                return;
 
             --  Here we have a candidate for inlining, but we must exclude
@@ -3277,8 +3309,13 @@ package body Sem_Prag is
             elsif not Effective
               and then Warn_On_Redundant_Constructs
             then
-               Error_Msg_NE ("pragma Inline for& is redundant?",
-                 N, Entity (Subp_Id));
+               if Inlining_Not_Possible (Subp) then
+                  Error_Msg_NE
+                    ("pragma Inline for& is ignored?", N, Entity (Subp_Id));
+               else
+                  Error_Msg_NE
+                    ("pragma Inline for& is redundant?", N, Entity (Subp_Id));
+               end if;
             end if;
 
             Next (Assoc);
This page took 0.079973 seconds and 5 git commands to generate.