File : a-coboho.ads


   1 ------------------------------------------------------------------------------
   2 --                                                                          --
   3 --                         GNAT LIBRARY COMPONENTS                          --
   4 --                                                                          --
   5 --       A D A . C O N T A I N E R S . B O U N D E D _ H O L D E R S        --
   6 --                                                                          --
   7 --                                 S p e c                                  --
   8 --                                                                          --
   9 --            Copyright (C) 2015, Free Software Foundation, Inc.            --
  10 --                                                                          --
  11 -- This specification is derived from the Ada Reference Manual for use with --
  12 -- GNAT. The copyright notice above, and the license provisions that follow --
  13 -- apply solely to the  contents of the part following the private keyword. --
  14 --                                                                          --
  15 -- GNAT is free software;  you can  redistribute it  and/or modify it under --
  16 -- terms of the  GNU General Public License as published  by the Free Soft- --
  17 -- ware  Foundation;  either version 3,  or (at your option) any later ver- --
  18 -- sion.  GNAT is distributed in the hope that it will be useful, but WITH- --
  19 -- OUT ANY WARRANTY;  without even the  implied warranty of MERCHANTABILITY --
  20 -- or FITNESS FOR A PARTICULAR PURPOSE.                                     --
  21 --                                                                          --
  22 --                                                                          --
  23 --                                                                          --
  24 --                                                                          --
  25 --                                                                          --
  26 -- You should have received a copy of the GNU General Public License and    --
  27 -- a copy of the GCC Runtime Library Exception along with this program;     --
  28 -- see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see    --
  29 -- <http://www.gnu.org/licenses/>.                                          --
  30 ------------------------------------------------------------------------------
  31 
  32 private with System;
  33 
  34 generic
  35    type Element_Type (<>) is private;
  36    Max_Size_In_Storage_Elements : Natural :=
  37      Element_Type'Max_Size_In_Storage_Elements;
  38    with function "=" (Left, Right : Element_Type) return Boolean is <>;
  39 
  40 package Ada.Containers.Bounded_Holders is
  41    pragma Annotate (CodePeer, Skip_Analysis);
  42 
  43    --  This package is patterned after Ada.Containers.Indefinite_Holders. It is
  44    --  used to treat indefinite subtypes as definite, but without using heap
  45    --  allocation. For example, you might like to say:
  46    --
  47    --     type A is array (...) of T'Class; -- illegal
  48    --
  49    --  Instead, you can instantiate this package with Element_Type => T'Class,
  50    --  and say:
  51    --
  52    --     type A is array (...) of Holder;
  53    --
  54    --  Each object of type Holder is allocated Max_Size_In_Storage_Elements
  55    --  bytes. If you try to create a holder from an object of type Element_Type
  56    --  that is too big, an exception is raised (assuming assertions are
  57    --  enabled). This applies to To_Holder and Set. If you pass an Element_Type
  58    --  object that is smaller than Max_Size_In_Storage_Elements, it works fine,
  59    --  but some space is wasted.
  60    --
  61    --  NOTE: If assertions are disabled, and you try to use an Element that is
  62    --  too big, execution is erroneous, and anything can happen, such as
  63    --  overwriting arbitrary memory locations.
  64    --
  65    --  Element_Type must not be an unconstrained array type. It can be a
  66    --  class-wide type or a type with non-defaulted discriminants.
  67    --
  68    --  The 'Size of each Element_Type object must be a multiple of
  69    --  System.Storage_Unit; e.g. creating Holders from 5-bit objects won't
  70    --  work.
  71 
  72    type Holder is private;
  73 
  74    function "=" (Left, Right : Holder) return Boolean;
  75 
  76    function To_Holder (New_Item : Element_Type) return Holder;
  77    function "+" (New_Item : Element_Type) return Holder renames To_Holder;
  78 
  79    function Get (Container : Holder) return Element_Type;
  80 
  81    procedure Set (Container : in out Holder; New_Item  : Element_Type);
  82 
  83 private
  84 
  85    --  The implementation uses low-level tricks (Address clauses and unchecked
  86    --  conversions of access types) to treat the elements as storage arrays.
  87 
  88    pragma Assert (Element_Type'Alignment <= Standard'Maximum_Alignment);
  89    --  This prevents elements with a user-specified Alignment that is too big
  90 
  91    type Storage_Element is mod System.Storage_Unit;
  92    type Storage_Array is array (Positive range <>) of Storage_Element;
  93    type Holder is record
  94       Data : Storage_Array (1 .. Max_Size_In_Storage_Elements);
  95    end record
  96      with Alignment => Standard'Maximum_Alignment;
  97    --  We would like to say "Alignment => Element_Type'Alignment", but that
  98    --  is illegal because it's not static, so we use the maximum possible
  99    --  (default) alignment instead.
 100 
 101    type Element_Access is access all Element_Type;
 102    pragma Assert (Element_Access'Size = Standard'Address_Size,
 103                   "cannot instantiate with an array type");
 104    --  If Element_Access is a fat pointer, Element_Type must be an
 105    --  unconstrained array, which is not allowed. Arrays won't work, because
 106    --  the 'Address of an array points to the first element, thus losing the
 107    --  bounds.
 108 
 109    pragma No_Strict_Aliasing (Element_Access);
 110    --  Needed because we are unchecked-converting from Address to
 111    --  Element_Access (see package body), which is a violation of the
 112    --  normal aliasing rules enforced by gcc.
 113 
 114 end Ada.Containers.Bounded_Holders;