As explained in the head comment of Compatible_Types_In_Predicate,
anomalies involving private and full views can occur when a call
to a predicate or invariant function is generated by the compiler.

The function uses the child function Common_Type to reconcile the
various views of a private type, but this latter function does not
consider the Underlying_Full_View of private types, so it can miss
some cases like this one.

Tested on x86_64-pc-linux-gnu, committed on trunk

2020-06-16  Eric Botcazou  <ebotca...@adacore.com>

gcc/ada/

        * sem_ch4.adb (Common_Type): Go to Underlying_Full_View, if any.
--- gcc/ada/sem_ch4.adb
+++ gcc/ada/sem_ch4.adb
@@ -3291,20 +3291,30 @@ package body Sem_Ch4 is
          T2 : Entity_Id) return Boolean
       is
          function Common_Type (T : Entity_Id) return Entity_Id;
-         --  Find non-private full view if any, without going to ancestor type
-         --  (as opposed to Underlying_Type).
+         --  Find non-private underlying full view if any, without going to
+         --  ancestor type (as opposed to Underlying_Type).
 
          -----------------
          -- Common_Type --
          -----------------
 
          function Common_Type (T : Entity_Id) return Entity_Id is
+            CT : Entity_Id;
+
          begin
-            if Is_Private_Type (T) and then Present (Full_View (T)) then
-               return Base_Type (Full_View (T));
-            else
-               return Base_Type (T);
+            CT := T;
+
+            if Is_Private_Type (CT) and then Present (Full_View (CT)) then
+               CT := Full_View (CT);
             end if;
+
+            if Is_Private_Type (CT)
+              and then Present (Underlying_Full_View (CT))
+            then
+               CT := Underlying_Full_View (CT);
+            end if;
+
+            return Base_Type (CT);
          end Common_Type;
 
       --  Start of processing for Compatible_Types_In_Predicate

Reply via email to