------------------------------------------------------------------------------
--                                                                          --
--                         GNAT RUN-TIME COMPONENTS                         --
--                                                                          --
--                    A D A . S E Q U E N T I A L _ I O                     --
--                                                                          --
--                                 B o d y                                  --
--                                                                          --
--          Copyright (C) 1992-2021, Free Software Foundation, Inc.         --
--                                                                          --
-- GNAT is free software;  you can  redistribute it  and/or modify it under --
-- terms of the  GNU General Public License as published  by the Free Soft- --
-- ware  Foundation;  either version 3,  or (at your option) any later ver- --
-- sion.  GNAT is distributed in the hope that it will be useful, but WITH- --
-- OUT ANY WARRANTY;  without even the  implied warranty of MERCHANTABILITY --
-- or FITNESS FOR A PARTICULAR PURPOSE.                                     --
--                                                                          --
-- As a special exception under Section 7 of GPL version 3, you are granted --
-- additional permissions described in the GCC Runtime Library Exception,   --
-- version 3.1, as published by the Free Software Foundation.               --
--                                                                          --
-- You should have received a copy of the GNU General Public License and    --
-- a copy of the GCC Runtime Library Exception along with this program;     --
-- see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see    --
-- <http://www.gnu.org/licenses/>.                                          --
--                                                                          --
-- GNAT was originally developed  by the GNAT team at  New York University. --
-- Extensive contributions were provided by Ada Core Technologies Inc.      --
--                                                                          --
------------------------------------------------------------------------------

--  This is the generic template for Sequential_IO, i.e. the code that gets
--  duplicated. We absolutely minimize this code by either calling routines
--  in System.File_IO (for common file functions), or in System.Sequential_IO
--  (for specialized Sequential_IO functions)

with Ada.Unchecked_Conversion;

with System;
with System.Byte_Swapping;
with System.CRTL;
with System.File_Control_Block;
with System.File_IO;
with System.Storage_Elements;

with Interfaces.C_Streams; use Interfaces.C_Streams;

package body Ada.Sequential_IO is

   package FIO renames System.File_IO;
   package FCB renames System.File_Control_Block;
   package SIO renames System.Sequential_IO;
   package SSE renames System.Storage_Elements;

   SU : constant := System.Storage_Unit;

   subtype AP is FCB.AFCB_Ptr;
   subtype FP is SIO.File_Type;

   function To_FCB is new Ada.Unchecked_Conversion (File_Mode, FCB.File_Mode);
   function To_SIO is new Ada.Unchecked_Conversion (FCB.File_Mode, File_Mode);

   use type System.Bit_Order;
   use type System.CRTL.size_t;

   procedure Byte_Swap (Siz : in out size_t);
   --  Byte swap Siz

   ---------------
   -- Byte_Swap --
   ---------------

   procedure Byte_Swap (Siz : in out size_t) is
      use System.Byte_Swapping;
   begin
      case size_t'Size is
         when 32     => Siz := size_t (Bswap_32 (U32 (Siz)));
         when 64     => Siz := size_t (Bswap_64 (U64 (Siz)));
         when others => raise Program_Error;
      end case;
   end Byte_Swap;

   -----------
   -- Close --
   -----------

   procedure Close (File : in out File_Type) is
   begin
      FIO.Close (AP (File)'Unrestricted_Access);
   end Close;

   ------------
   -- Create --
   ------------

   procedure Create
     (File : in out File_Type;
      Mode : File_Mode := Out_File;
      Name : String := "";
      Form : String := "")
   is
   begin
      SIO.Create (FP (File), To_FCB (Mode), Name, Form);
   end Create;

   ------------
   -- Delete --
   ------------

   procedure Delete (File : in out File_Type) is
   begin
      FIO.Delete (AP (File)'Unrestricted_Access);
   end Delete;

   -----------------
   -- End_Of_File --
   -----------------

   function End_Of_File (File : File_Type) return Boolean is
   begin
      return FIO.End_Of_File (AP (File));
   end End_Of_File;

   -----------
   -- Flush --
   -----------

   procedure Flush (File : File_Type) is
   begin
      FIO.Flush (AP (File));
   end Flush;

   ----------
   -- Form --
   ----------

   function Form (File : File_Type) return String is
   begin
      return FIO.Form (AP (File));
   end Form;

   -------------
   -- Is_Open --
   -------------

   function Is_Open (File : File_Type) return Boolean is
   begin
      return FIO.Is_Open (AP (File));
   end Is_Open;

   ----------
   -- Mode --
   ----------

   function Mode (File : File_Type) return File_Mode is
   begin
      return To_SIO (FIO.Mode (AP (File)));
   end Mode;

   ----------
   -- Name --
   ----------

   function Name (File : File_Type) return String is
   begin
      return FIO.Name (AP (File));
   end Name;

   ----------
   -- Open --
   ----------

   procedure Open
     (File : in out File_Type;
      Mode : File_Mode;
      Name : String;
      Form : String := "")
   is
   begin
      SIO.Open (FP (File), To_FCB (Mode), Name, Form);
   end Open;

   ----------
   -- Read --
   ----------

   procedure Read (File : File_Type; Item : out Element_Type) is
      Siz  : constant size_t := (Item'Size + SU - 1) / SU;
      Rsiz : size_t;

   begin
      FIO.Check_Read_Status (AP (File));

      --  For non-definite type or type with discriminants, read size and
      --  raise Program_Error if it is larger than the size of the item.

      if not Element_Type'Definite
        or else Element_Type'Has_Discriminants
      then
         FIO.Read_Buf
           (AP (File), Rsiz'Address, size_t'Size / System.Storage_Unit);

         --  If item read has non-default scalar storage order, then the size
         --  will have been written with that same order, so byte swap it.

         if Element_Type'Scalar_Storage_Order /= System.Default_Bit_Order then
            Byte_Swap (Rsiz);
         end if;

         --  For a type with discriminants, we have to read into a temporary
         --  buffer if Item is constrained, to check that the discriminants
         --  are correct.

         if Element_Type'Has_Discriminants and then Item'Constrained then
            declare
               RsizS : constant SSE.Storage_Offset :=
                         SSE.Storage_Offset (Rsiz - 1);

               type SA is new SSE.Storage_Array (0 .. RsizS);

               for SA'Alignment use Standard'Maximum_Alignment;
               --  We will perform an unchecked conversion of a pointer-to-SA
               --  into pointer-to-Element_Type. We need to ensure that the
               --  source is always at least as strictly aligned as the target.

               type SAP   is access all SA;
               type ItemP is access all Element_Type;

               pragma Warnings (Off);
               --  We have to turn warnings off for function To_ItemP,
               --  because it gets analyzed for all types, including ones
               --  which can't possibly come this way, and for which the
               --  size of the access types differs.

               function To_ItemP is new Ada.Unchecked_Conversion (SAP, ItemP);

               pragma Warnings (On);

               Buffer : aliased SA;

               pragma Unsuppress (Discriminant_Check);

            begin
               FIO.Read_Buf (AP (File), Buffer'Address, Rsiz);
               Item := To_ItemP (Buffer'Access).all;
               return;
            end;
         end if;

         --  In the case of a non-definite type, make sure the length is OK.
         --  We can't do this in the variant record case, because the size is
         --  based on the current discriminant, so may be apparently wrong.

         if not Element_Type'Has_Discriminants and then Rsiz > Siz then
            raise Program_Error;
         end if;

         FIO.Read_Buf (AP (File), Item'Address, Rsiz);

      --  For definite type without discriminants, use actual size of item

      else
         FIO.Read_Buf (AP (File), Item'Address, Siz);
      end if;
   end Read;

   -----------
   -- Reset --
   -----------

   procedure Reset (File : in out File_Type; Mode : File_Mode) is
   begin
      FIO.Reset (AP (File)'Unrestricted_Access, To_FCB (Mode));
   end Reset;

   procedure Reset (File : in out File_Type) is
   begin
      FIO.Reset (AP (File)'Unrestricted_Access);
   end Reset;

   -----------
   -- Write --
   -----------

   procedure Write (File : File_Type; Item : Element_Type) is
      Siz : constant size_t := (Item'Size + SU - 1) / SU;
      --  Size to be written, in native representation

      Swapped_Siz : size_t := Siz;
      --  Same, possibly byte swapped to account for Element_Type endianness

   begin
      FIO.Check_Write_Status (AP (File));

      --  For non-definite types or types with discriminants, write the size

      if not Element_Type'Definite
        or else Element_Type'Has_Discriminants
      then
         --  If item written has non-default scalar storage order, then the
         --  size is written with that same order, so byte swap it.

         if Element_Type'Scalar_Storage_Order /= System.Default_Bit_Order then
            Byte_Swap (Swapped_Siz);
         end if;

         FIO.Write_Buf
           (AP (File), Swapped_Siz'Address, size_t'Size / System.Storage_Unit);
      end if;

      FIO.Write_Buf (AP (File), Item'Address, Siz);
   end Write;

end Ada.Sequential_IO;
