diff mbox

[Ada] 'Type_Key on subtypes and derived types

Message ID 20170427095714.GA48360@adacore.com
State New
Headers show

Commit Message

Arnaud Charlet April 27, 2017, 9:57 a.m. UTC
This patch fixes a bug in which 'Type_Key on a subtype or derived type
could sometimes access the wrong source buffer. The following test
should compile and run silently.

package P is
   type My_Int is range 1 .. 10;
   for My_Int'Size use 10;
end P;
with P; use P;
package Q is
   type New_My_Int is new My_Int;
   for New_My_Int'Size use 20;
end Q;
with Q; use Q;
package R is
   subtype S is New_My_Int;
end R;
with R; use R;
procedure Main is
   Key : constant String := S'Type_Key;
begin
   null;
end Main;

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

2017-04-27  Bob Duff  <duff@adacore.com>

	* sem_attr.adb (Compute_Type_Key): Don't walk
	representation items for irrelevant types, which could be in a
	different source file.
diff mbox

Patch

Index: sem_attr.adb
===================================================================
--- sem_attr.adb	(revision 247296)
+++ sem_attr.adb	(working copy)
@@ -6310,21 +6310,28 @@ 
                end;
             end if;
 
-            --  Fold in representation aspects for the type, which appear in
-            --  the same source buffer.
+            if Is_First_Subtype (T) then
 
-            Rep := First_Rep_Item (T);
+               --  Fold in representation aspects for the type, which appear in
+               --  the same source buffer. If the representation aspects are in
+               --  a different source file, then skip them; they apply to some
+               --  other type, perhaps one we're derived from.
 
-            while Present (Rep) loop
-               if Comes_From_Source (Rep) then
-                  Sloc_Range (Rep, P_Min, P_Max);
-                  pragma Assert (SFI = Get_Source_File_Index (P_Min));
-                  pragma Assert (SFI = Get_Source_File_Index (P_Max));
-                  Process_One_Declaration;
-               end if;
+               Rep := First_Rep_Item (T);
 
-               Rep := Next_Rep_Item (Rep);
-            end loop;
+               while Present (Rep) loop
+                  if Comes_From_Source (Rep) then
+                     Sloc_Range (Rep, P_Min, P_Max);
+
+                     if SFI = Get_Source_File_Index (P_Min) then
+                        pragma Assert (SFI = Get_Source_File_Index (P_Max));
+                        Process_One_Declaration;
+                     end if;
+                  end if;
+
+                  Rep := Next_Rep_Item (Rep);
+               end loop;
+            end if;
          end Compute_Type_Key;
 
       --  Start of processing for Type_Key