-------------------------------------------------------------------------------
-- (C) Altran Praxis Limited
-------------------------------------------------------------------------------
--
-- The SPARK toolset is free software; you can redistribute it and/or modify it
-- under terms of the GNU General Public License as published by the Free
-- Software Foundation; either version 3, or (at your option) any later
-- version. The SPARK toolset is distributed in the hope that it will be
-- useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
-- Public License for more details. You should have received a copy of the GNU
-- General Public License distributed with the SPARK toolset; see file
-- COPYING3. If not, go to http://www.gnu.org/licenses for a complete copy of
-- the license.
--
--=============================================================================

package SPARK_IO
--# own File_Sys;
--# initializes File_Sys;
is
   type File_Type is private;
   type File_Mode is (In_File, Out_File, Append_File);
   type File_Status is (
                        Ok,
                        Status_Error,
                        Mode_Error,
                        Name_Error,
                        Use_Error,
                        Device_Error,
                        End_Error,
                        Data_Error,
                        Layout_Error);

   subtype Number_Base is Integer range 2 .. 16;

   function Standard_Input return File_Type;
   --# global in File_Sys;
   function Standard_Output return File_Type;
   --# global in File_Sys;
   Null_File : constant File_Type;

   ------------------
   -- File Management
   ------------------

   procedure Create
     (File         : in out File_Type;
      Name_Length  : in     Natural;
      Name_Of_File : in     String;
      Form_Of_File : in     String;
      Status       :    out File_Status);
   --# global in out File_Sys;
   --# derives File,
   --#         File_Sys,
   --#         Status   from File,
   --#                       File_Sys,
   --#                       Form_Of_File,
   --#                       Name_Length,
   --#                       Name_Of_File;

   procedure Open
     (File         : in out File_Type;
      Mode_Of_File : in     File_Mode;
      Name_Length  : in     Natural;
      Name_Of_File : in     String;
      Form_Of_File : in     String;
      Status       :    out File_Status);
   --# global in out File_Sys;
   --# derives File,
   --#         File_Sys,
   --#         Status   from File,
   --#                       File_Sys,
   --#                       Form_Of_File,
   --#                       Mode_Of_File,
   --#                       Name_Length,
   --#                       Name_Of_File;

   procedure Close (File   : in out File_Type;
                    Status :    out File_Status);
   --# global in out File_Sys;
   --# derives File,
   --#         File_Sys from *,
   --#                       File &
   --#         Status   from File,
   --#                       File_Sys;

   procedure Delete (File   : in out File_Type;
                     Status :    out File_Status);
   --# global in out File_Sys;
   --# derives File,
   --#         File_Sys from *,
   --#                       File &
   --#         Status   from File,
   --#                       File_Sys;

   procedure Reset (File         : in out File_Type;
                    Mode_Of_File : in     File_Mode;
                    Status       :    out File_Status);
   --# global in out File_Sys;
   --# derives File,
   --#         File_Sys from *,
   --#                       File,
   --#                       Mode_Of_File &
   --#         Status   from File,
   --#                       File_Sys,
   --#                       Mode_Of_File;

   function Valid_File (File : File_Type) return Boolean;
   --# global in File_Sys;

   function Mode (File : File_Type) return File_Mode;
   --# global in File_Sys;

   procedure Name (File         : in     File_Type;
                   Name_Of_File :    out String;
                   Stop         :    out Natural);
   --# global in File_Sys;
   --# derives Name_Of_File,
   --#         Stop         from File,
   --#                           File_Sys;

   procedure Form (File         : in     File_Type;
                   Form_Of_File :    out String;
                   Stop         :    out Natural);
   --# global in File_Sys;
   --# derives Form_Of_File,
   --#         Stop         from File,
   --#                           File_Sys;

   function Is_Open (File : File_Type) return Boolean;
   --# global in File_Sys;

   --------------------------------------------
   -- Control of default input and output files
   --------------------------------------------

   --
   -- Not supported in SPARK_IO
   --

   -----------------------------------------
   -- Specification of line and page lengths
   -----------------------------------------

   --
   -- Not supported in SPARK_IO
   --

   --------------------------------
   -- Column, Line and Page Control
   --------------------------------

   procedure New_Line (File    : in File_Type;
                       Spacing : in Positive);
   --# global in out File_Sys;
   --# derives File_Sys from *,
   --#                       File,
   --#                       Spacing;

   procedure Skip_Line (File    : in File_Type;
                        Spacing : in Positive);
   --# global in out File_Sys;
   --# derives File_Sys from *,
   --#                       File,
   --#                       Spacing;

   procedure New_Page (File : in File_Type);
   --# global in out File_Sys;
   --# derives File_Sys from *,
   --#                       File;

   function End_Of_Line (File : File_Type) return Boolean;
   --# global in File_Sys;

   function End_Of_File (File : File_Type) return Boolean;
   --# global in File_Sys;

   procedure Set_Col (File : in File_Type;
                      Posn : in Positive);
   --# global in out File_Sys;
   --# derives File_Sys from *,
   --#                       File,
   --#                       Posn;

   function Col (File : File_Type) return Positive;
   --# global in File_Sys;

   function Line (File : File_Type) return Positive;
   --# global in File_Sys;

   -------------------------
   -- Character Input-Output
   -------------------------

   procedure Get_Char (File : in     File_Type;
                       Item :    out Character);
   --# global in out File_Sys;
   --# derives File_Sys,
   --#         Item     from File,
   --#                       File_Sys;

   procedure Put_Char (File : in File_Type;
                       Item : in Character);
   --# global in out File_Sys;
   --# derives File_Sys from *,
   --#                       File,
   --#                       Item;

   ----------------------
   -- String Input-Output
   ----------------------

   procedure Get_String (File : in     File_Type;
                         Item :    out String;
                         Stop :    out Natural);
   --# global in out File_Sys;
   --# derives File_Sys,
   --#         Item,
   --#         Stop     from File,
   --#                       File_Sys;

   procedure Put_String (File : in File_Type;
                         Item : in String;
                         Stop : in Natural);
   --# global in out File_Sys;
   --# derives File_Sys from *,
   --#                       File,
   --#                       Item,
   --#                       Stop;

   procedure Get_Line (File : in     File_Type;
                       Item :    out String;
                       Stop :    out Natural);
   --# global in out File_Sys;
   --# derives File_Sys,
   --#         Item,
   --#         Stop     from File,
   --#                       File_Sys;

   procedure Put_Line (File : in File_Type;
                       Item : in String;
                       Stop : in Natural);
   --# global in out File_Sys;
   --# derives File_Sys from *,
   --#                       File,
   --#                       Item,
   --#                       Stop;

   -----------------------
   -- Integer Input-Output
   -----------------------

   -- SPARK_IO only supports input-output of
   -- the built-in integer type Integer

   procedure Get_Integer
     (File  : in     File_Type;
      Item  :    out Integer;
      Width : in     Natural;
      Read  :    out Boolean);
   --# global in out File_Sys;
   --# derives File_Sys,
   --#         Item,
   --#         Read     from File,
   --#                       File_Sys,
   --#                       Width;

   procedure Put_Integer
     (File  : in File_Type;
      Item  : in Integer;
      Width : in Natural;
      Base  : in Number_Base);
   --# global in out File_Sys;
   --# derives File_Sys from *,
   --#                       Base,
   --#                       File,
   --#                       Item,
   --#                       Width;

   procedure Get_Int_From_String
     (Source    : in     String;
      Item      :    out Integer;
      Start_Pos : in     Positive;
      Stop      :    out Natural);
   --# derives Item,
   --#         Stop from Source,
   --#                   Start_Pos;

   ---------------------
   -- Float Input-Output
   ---------------------

   -- SPARK_IO only supports input-output of
   -- the built-in real type Float

   procedure Get_Float
     (File  : in     File_Type;
      Item  :    out Float;
      Width : in     Natural;
      Read  :    out Boolean);
   --# global in out File_Sys;
   --# derives File_Sys,
   --#         Item,
   --#         Read     from File,
   --#                       File_Sys,
   --#                       Width;

   procedure Put_Float
     (File : in File_Type;
      Item : in Float;
      Fore : in Natural;
      Aft  : in Natural;
      Exp  : in Natural);
   --# global in out File_Sys;
   --# derives File_Sys from *,
   --#                       Aft,
   --#                       Exp,
   --#                       File,
   --#                       Fore,
   --#                       Item;

   procedure Get_Float_From_String
     (Source    : in     String;
      Item      :    out Float;
      Start_Pos : in     Positive;
      Stop      :    out Natural);
   --# derives Item,
   --#         Stop from Source,
   --#                   Start_Pos;

   procedure Put_Float_To_String
     (Dest      : in out String;
      Item      : in     Float;
      Start_Pos : in     Positive;
      Aft       : in     Natural;
      Exp       : in     Natural);
   --# derives Dest from *,
   --#                   Aft,
   --#                   Exp,
   --#                   Item,
   --#                   Start_Pos;

   pragma Inline (Valid_File, End_Of_Line, End_Of_File, Get_Char);

private
   --# hide SPARK_IO;

   type File_Descriptor;
   type File_Type is access all File_Descriptor;

   Null_File : constant File_Type := null;

end SPARK_IO;
