A compilation unit that is a subprogram is rewritten as a package (the wrapper package) containing the body of the actual subprogram instance. The wrapping happens when the unit is compiled upon its appearance in the context of some unit. If it appears in several such contexts, and the subprogram is marked Inline, some units only see the wrapper package. Each unit in a context is made into a visible library unit, and when the unit is the wrapper package, it is the related instance (the subprogram) that must be made visible. Prior to this patch, only the converse was done, namely the visible library unit flag was reset on exit from a given context, but not set when isntalling context.
Executing gnatmake -q -gnato -gnatn -gnatwa -gnatQ main main must yield: OK --- with GNAT.IO; use GNAT.IO; with Case_Handling_J; procedure main is begin Put_Line (Case_Handling_J.Get); end main; --- with Ada.Containers.Indefinite_Hashed_Maps; with Ada.Strings.Wide_Wide_Hash; package Case_Handling is S : Wide_Wide_String := ""; private type W_Node is record Read_Only : Boolean; end record; package Casing_Exception_Table is new Ada.Containers.Indefinite_Hashed_Maps (Key_Type => Wide_Wide_String, Element_Type => W_Node, Hash => Ada.Strings.Wide_Wide_Hash, Equivalent_Keys => "="); use Casing_Exception_Table; end Case_Handling; --- with Ada.Containers; package Case_Handling_J is function JNI_For_Body_Elaboration return Ada.Containers.Hash_Type; function Get return String; end Case_Handling_J; --- with Ada.Strings.Wide_Wide_Hash; with Case_Handling; package body Case_Handling_J is function JNI_For_Body_Elaboration return Ada.Containers.Hash_Type is begin return Ada.Strings.Wide_Wide_Hash (Case_Handling.S); end; function Get return String is begin return "OK"; end; end Case_Handling_J; Tested on x86_64-pc-linux-gnu, committed on trunk 2014-01-21 Ed Schonberg <schonb...@adacore.com> * sem_ch10.adb (Install_Withed_Unit): If the unit is a subprogram instance that is inlined, it may have been rewritten as a wrapper package. In that case the unit that must be made visible is the related instance of the package.
Index: sem_ch10.adb =================================================================== --- sem_ch10.adb (revision 206813) +++ sem_ch10.adb (working copy) @@ -5156,6 +5156,14 @@ Set_Is_Visible_Lib_Unit (Uname); + -- If the unit is a wrapper package for a compilation unit that is + -- a subprogrm instance, indicate that the instance itself is a + -- visible unit. This is necessary if the instance is inlined. + + if Is_Wrapper_Package (Uname) then + Set_Is_Visible_Lib_Unit (Related_Instance (Uname)); + end if; + -- If the child unit appears in the context of its parent, it is -- immediately visible. @@ -6447,6 +6455,7 @@ -- If the unit is a wrapper package, the subprogram instance is -- what must be removed from visibility. + -- Should we use Related_Instance instead??? if Is_Wrapper_Package (Unit_Name) then Set_Is_Immediately_Visible (Current_Entity (Unit_Name), False);