OSDN Git Service

2008-04-08 Robert Dewar <dewar@adacore.com>
[pf3gnuchains/gcc-fork.git] / gcc / ada / a-wtdeau.adb
1 ------------------------------------------------------------------------------
2 --                                                                          --
3 --                         GNAT RUN-TIME COMPONENTS                         --
4 --                                                                          --
5 --         A D A . W I D E _ T E X T _ I O . D E C I M A L _ A U X          --
6 --                                                                          --
7 --                                 B o d y                                  --
8 --                                                                          --
9 --          Copyright (C) 1992-2008, Free Software Foundation, Inc.         --
10 --                                                                          --
11 -- GNAT is free software;  you can  redistribute it  and/or modify it under --
12 -- terms of the  GNU General Public License as published  by the Free Soft- --
13 -- ware  Foundation;  either version 2,  or (at your option) any later ver- --
14 -- sion.  GNAT is distributed in the hope that it will be useful, but WITH- --
15 -- OUT ANY WARRANTY;  without even the  implied warranty of MERCHANTABILITY --
16 -- or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License --
17 -- for  more details.  You should have  received  a copy of the GNU General --
18 -- Public License  distributed with GNAT;  see file COPYING.  If not, write --
19 -- to  the  Free Software Foundation,  51  Franklin  Street,  Fifth  Floor, --
20 -- Boston, MA 02110-1301, USA.                                              --
21 --                                                                          --
22 -- As a special exception,  if other files  instantiate  generics from this --
23 -- unit, or you link  this unit with other files  to produce an executable, --
24 -- this  unit  does not  by itself cause  the resulting  executable  to  be --
25 -- covered  by the  GNU  General  Public  License.  This exception does not --
26 -- however invalidate  any other reasons why  the executable file  might be --
27 -- covered by the  GNU Public License.                                      --
28 --                                                                          --
29 -- GNAT was originally developed  by the GNAT team at  New York University. --
30 -- Extensive contributions were provided by Ada Core Technologies Inc.      --
31 --                                                                          --
32 ------------------------------------------------------------------------------
33
34 with Ada.Wide_Text_IO.Generic_Aux; use Ada.Wide_Text_IO.Generic_Aux;
35 with Ada.Wide_Text_IO.Float_Aux;   use Ada.Wide_Text_IO.Float_Aux;
36
37 with System.Img_Dec; use System.Img_Dec;
38 with System.Img_LLD; use System.Img_LLD;
39 with System.Val_Dec; use System.Val_Dec;
40 with System.Val_LLD; use System.Val_LLD;
41
42 package body Ada.Wide_Text_IO.Decimal_Aux is
43
44    -------------
45    -- Get_Dec --
46    -------------
47
48    function Get_Dec
49      (File  : File_Type;
50       Width : Field;
51       Scale : Integer) return Integer
52    is
53       Buf  : String (1 .. Field'Last);
54       Ptr  : aliased Integer;
55       Stop : Integer := 0;
56       Item : Integer;
57
58    begin
59       if Width /= 0 then
60          Load_Width (File, Width, Buf, Stop);
61          String_Skip (Buf, Ptr);
62       else
63          Load_Real (File, Buf, Stop);
64          Ptr := 1;
65       end if;
66
67       Item := Scan_Decimal (Buf, Ptr'Access, Stop, Scale);
68       Check_End_Of_Field (Buf, Stop, Ptr, Width);
69       return Item;
70    end Get_Dec;
71
72    -------------
73    -- Get_LLD --
74    -------------
75
76    function Get_LLD
77      (File  : File_Type;
78       Width : Field;
79       Scale : Integer) return Long_Long_Integer
80    is
81       Buf  : String (1 .. Field'Last);
82       Ptr  : aliased Integer;
83       Stop : Integer := 0;
84       Item : Long_Long_Integer;
85
86    begin
87       if Width /= 0 then
88          Load_Width (File, Width, Buf, Stop);
89          String_Skip (Buf, Ptr);
90       else
91          Load_Real (File, Buf, Stop);
92          Ptr := 1;
93       end if;
94
95       Item := Scan_Long_Long_Decimal (Buf, Ptr'Access, Stop, Scale);
96       Check_End_Of_Field (Buf, Stop, Ptr, Width);
97       return Item;
98    end Get_LLD;
99
100    --------------
101    -- Gets_Dec --
102    --------------
103
104    function Gets_Dec
105      (From  : String;
106       Last  : not null access Positive;
107       Scale : Integer) return Integer
108    is
109       Pos  : aliased Integer;
110       Item : Integer;
111
112    begin
113       String_Skip (From, Pos);
114       Item := Scan_Decimal (From, Pos'Access, From'Last, Scale);
115       Last.all := Pos - 1;
116       return Item;
117
118    exception
119       when Constraint_Error =>
120          Last.all := Pos - 1;
121          raise Data_Error;
122
123    end Gets_Dec;
124
125    --------------
126    -- Gets_LLD --
127    --------------
128
129    function Gets_LLD
130      (From  : String;
131       Last  : not null access Positive;
132       Scale : Integer) return Long_Long_Integer
133    is
134       Pos  : aliased Integer;
135       Item : Long_Long_Integer;
136
137    begin
138       String_Skip (From, Pos);
139       Item := Scan_Long_Long_Decimal (From, Pos'Access, From'Last, Scale);
140       Last.all := Pos - 1;
141       return Item;
142
143    exception
144       when Constraint_Error =>
145          Last.all := Pos - 1;
146          raise Data_Error;
147
148    end Gets_LLD;
149
150    -------------
151    -- Put_Dec --
152    -------------
153
154    procedure Put_Dec
155      (File  : File_Type;
156       Item  : Integer;
157       Fore  : Field;
158       Aft   : Field;
159       Exp   : Field;
160       Scale : Integer)
161    is
162       Buf : String (1 .. Field'Last);
163       Ptr : Natural := 0;
164
165    begin
166       Set_Image_Decimal (Item, Buf, Ptr, Scale, Fore, Aft, Exp);
167       Put_Item (File, Buf (1 .. Ptr));
168    end Put_Dec;
169
170    -------------
171    -- Put_LLD --
172    -------------
173
174    procedure Put_LLD
175      (File  : File_Type;
176       Item  : Long_Long_Integer;
177       Fore  : Field;
178       Aft   : Field;
179       Exp   : Field;
180       Scale : Integer)
181    is
182       Buf : String (1 .. Field'Last);
183       Ptr : Natural := 0;
184
185    begin
186       Set_Image_Long_Long_Decimal (Item, Buf, Ptr, Scale, Fore, Aft, Exp);
187       Put_Item (File, Buf (1 .. Ptr));
188    end Put_LLD;
189
190    --------------
191    -- Puts_Dec --
192    --------------
193
194    procedure Puts_Dec
195      (To    : out String;
196       Item  : Integer;
197       Aft   : Field;
198       Exp   : Field;
199       Scale : Integer)
200    is
201       Buf  : String (1 .. Field'Last);
202       Fore : Integer;
203       Ptr  : Natural := 0;
204
205    begin
206       --  Compute Fore, allowing for Aft digits and the decimal dot
207
208       Fore := To'Length - Field'Max (1, Aft) - 1;
209
210       --  Allow for Exp and two more for E+ or E- if exponent present
211
212       if Exp /= 0 then
213          Fore := Fore - 2 - Exp;
214       end if;
215
216       --  Make sure we have enough room
217
218       if Fore < 1 then
219          raise Layout_Error;
220       end if;
221
222       --  Do the conversion and check length of result
223
224       Set_Image_Decimal (Item, Buf, Ptr, Scale, Fore, Aft, Exp);
225
226       if Ptr > To'Length then
227          raise Layout_Error;
228       else
229          To := Buf (1 .. Ptr);
230       end if;
231    end Puts_Dec;
232
233    --------------
234    -- Puts_Dec --
235    --------------
236
237    procedure Puts_LLD
238      (To    : out String;
239       Item  : Long_Long_Integer;
240       Aft   : Field;
241       Exp   : Field;
242       Scale : Integer)
243    is
244       Buf  : String (1 .. Field'Last);
245       Fore : Integer;
246       Ptr  : Natural := 0;
247
248    begin
249       if Exp = 0 then
250          Fore := To'Length - 1 - Aft;
251       else
252          Fore := To'Length - 2 - Aft - Exp;
253       end if;
254
255       if Fore < 1 then
256          raise Layout_Error;
257       end if;
258
259       Set_Image_Long_Long_Decimal (Item, Buf, Ptr, Scale, Fore, Aft, Exp);
260
261       if Ptr > To'Length then
262          raise Layout_Error;
263       else
264          To := Buf (1 .. Ptr);
265       end if;
266    end Puts_LLD;
267
268 end Ada.Wide_Text_IO.Decimal_Aux;