From: Eric Botcazou Date: Thu, 13 Mar 2014 15:42:21 +0000 (+0000) Subject: re PR ada/51483 (cstand.adb:Register_Float_Type makes invalid assumption about FP... X-Git-Tag: releases/gcc-4.9.0~467 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=00c5acd39f33c335223428099d5427fad1557db9;p=thirdparty%2Fgcc.git re PR ada/51483 (cstand.adb:Register_Float_Type makes invalid assumption about FP modes) PR ada/51483 * cstand.adb (Register_Float_Type): Add 'precision' parameter and use it to set the RM size. Use directly 'size' for the Esize. (Create_Back_End_Float_Types): Adjust call to above. * get_targ.ads (Register_Type_Proc): Add 'precision' parameter. * set_targ.ads (FPT_Mode_Entry): Add 'precision' component. (Write_Target_Dependent_Values): Adjust comment. * set_targ.adb (Register_Float_Type): Add 'precision' parameter and deal with it. (Write_Target_Dependent_Values): Write the precision in lieu of size. (Initialization): Read the precision in lieu of size and compute the size from the precision and the alignment. * gcc-interface/gigi.h (enumerate_modes): Add integer parameter. * gcc-interface/misc.c (enumerate_modes): Likewise. Do not register types for vector modes, pass the size in addition to the precision. From-SVN: r208546 --- diff --git a/gcc/ada/ChangeLog b/gcc/ada/ChangeLog index 568f7e4e214a..cfb2c59156d6 100644 --- a/gcc/ada/ChangeLog +++ b/gcc/ada/ChangeLog @@ -1,3 +1,21 @@ +2014-03-13 Eric Botcazou + + PR ada/51483 + * cstand.adb (Register_Float_Type): Add 'precision' parameter and use + it to set the RM size. Use directly 'size' for the Esize. + (Create_Back_End_Float_Types): Adjust call to above. + * get_targ.ads (Register_Type_Proc): Add 'precision' parameter. + * set_targ.ads (FPT_Mode_Entry): Add 'precision' component. + (Write_Target_Dependent_Values): Adjust comment. + * set_targ.adb (Register_Float_Type): Add 'precision' parameter and + deal with it. + (Write_Target_Dependent_Values): Write the precision in lieu of size. + (Initialization): Read the precision in lieu of size and compute the + size from the precision and the alignment. + * gcc-interface/gigi.h (enumerate_modes): Add integer parameter. + * gcc-interface/misc.c (enumerate_modes): Likewise. Do not register + types for vector modes, pass the size in addition to the precision. + 2014-03-10 Eric Botcazou * gcc-interface/Make-lang.in (ADA_DEPFILES): Fix typo. diff --git a/gcc/ada/cstand.adb b/gcc/ada/cstand.adb index 322473e0f96a..4099a7d04579 100644 --- a/gcc/ada/cstand.adb +++ b/gcc/ada/cstand.adb @@ -6,7 +6,7 @@ -- -- -- B o d y -- -- -- --- Copyright (C) 1992-2013, Free Software Foundation, Inc. -- +-- Copyright (C) 1992-2014, 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- -- @@ -158,6 +158,7 @@ package body CStand is (Name : String; Digs : Positive; Float_Rep : Float_Rep_Kind; + Precision : Positive; Size : Positive; Alignment : Natural); -- Registers a single back end floating-point type (from FPT_Mode_Table in @@ -167,7 +168,8 @@ package body CStand is -- as a normal format (non-null-terminated) string. Digs is the number of -- digits, which is always non-zero, since non-floating-point types were -- filtered out earlier. Float_Rep indicates the kind of floating-point - -- type, and Size and Alignment are the size and alignment in bits. + -- type, and Precision, Size and Alignment are the precision, size and + -- alignment in bits. procedure Set_Integer_Bounds (Id : Entity_Id; @@ -480,7 +482,8 @@ package body CStand is E : FPT_Mode_Entry renames FPT_Mode_Table (J); begin Register_Float_Type - (E.NAME.all, E.DIGS, E.FLOAT_REP, E.SIZE, E.ALIGNMENT); + (E.NAME.all, E.DIGS, E.FLOAT_REP, E.PRECISION, E.SIZE, + E.ALIGNMENT); end; end loop; end Create_Back_End_Float_Types; @@ -2083,19 +2086,18 @@ package body CStand is (Name : String; Digs : Positive; Float_Rep : Float_Rep_Kind; + Precision : Positive; Size : Positive; Alignment : Natural) is - Ent : constant Entity_Id := New_Standard_Entity; - Esize : constant Pos := - Pos ((Size + Alignment - 1) / Alignment * Alignment); + Ent : constant Entity_Id := New_Standard_Entity; begin Set_Defining_Identifier (New_Node (N_Full_Type_Declaration, Stloc), Ent); Make_Name (Ent, Name); Set_Scope (Ent, Standard_Standard); - Build_Float_Type (Ent, Esize, Float_Rep, Pos (Digs)); - Set_RM_Size (Ent, UI_From_Int (Int (Size))); + Build_Float_Type (Ent, Int (Size), Float_Rep, Pos (Digs)); + Set_RM_Size (Ent, UI_From_Int (Int (Precision))); Set_Alignment (Ent, UI_From_Int (Int (Alignment / 8))); if No (Back_End_Float_Types) then diff --git a/gcc/ada/gcc-interface/gigi.h b/gcc/ada/gcc-interface/gigi.h index cf75bd62040e..b7092735c898 100644 --- a/gcc/ada/gcc-interface/gigi.h +++ b/gcc/ada/gcc-interface/gigi.h @@ -6,7 +6,7 @@ * * * C Header File * * * - * Copyright (C) 1992-2013, Free Software Foundation, Inc. * + * Copyright (C) 1992-2014, 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- * @@ -1044,7 +1044,7 @@ extern Nat get_target_double_scalar_alignment (void); /* This function is called by the front-end to enumerate all the supported modes for the machine, as well as some predefined C types. */ extern void enumerate_modes (void (*f) (const char *, int, int, int, int, int, - int)); + int, int)); #ifdef __cplusplus } diff --git a/gcc/ada/gcc-interface/misc.c b/gcc/ada/gcc-interface/misc.c index 5f135a063b20..a5f2881d697b 100644 --- a/gcc/ada/gcc-interface/misc.c +++ b/gcc/ada/gcc-interface/misc.c @@ -6,7 +6,7 @@ * * * C Implementation File * * * - * Copyright (C) 1992-2013, Free Software Foundation, Inc. * + * Copyright (C) 1992-2014, 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- * @@ -683,7 +683,7 @@ must_pass_by_ref (tree gnu_type) /* This function is called by the front-end to enumerate all the supported modes for the machine, as well as some predefined C types. F is a function which is called back with the parameters as listed below, first a string, - then six ints. The name is any arbitrary null-terminated string and has + then seven ints. The name is any arbitrary null-terminated string and has no particular significance, except for the case of predefined C types, where it should be the name of the C type. For integer types, only signed types should be listed, unsigned versions are assumed. The order of types should @@ -699,11 +699,12 @@ must_pass_by_ref (tree gnu_type) COMPLEX_P nonzero is this represents a complex mode COUNT count of number of items, nonzero for vector mode FLOAT_REP Float_Rep_Kind for FP, otherwise undefined - SIZE number of bits used to store data + PRECISION number of bits used to store data + SIZE number of bits occupied by the mode ALIGN number of bits to which mode is aligned. */ void -enumerate_modes (void (*f) (const char *, int, int, int, int, int, int)) +enumerate_modes (void (*f) (const char *, int, int, int, int, int, int, int)) { const tree c_types[] = { float_type_node, double_type_node, long_double_type_node }; @@ -777,28 +778,26 @@ enumerate_modes (void (*f) (const char *, int, int, int, int, int, int)) /* First register any C types for this mode that the front end may need to know about, unless the mode should be skipped. */ - - if (!skip_p) + if (!skip_p && !vector_p) for (nameloop = 0; nameloop < ARRAY_SIZE (c_types); nameloop++) { - tree typ = c_types[nameloop]; - const char *nam = c_names[nameloop]; + tree type = c_types[nameloop]; + const char *name = c_names[nameloop]; - if (TYPE_MODE (typ) == i) + if (TYPE_MODE (type) == i) { - f (nam, digs, complex_p, - vector_p ? GET_MODE_NUNITS (i) : 0, float_rep, - TYPE_PRECISION (typ), TYPE_ALIGN (typ)); + f (name, digs, complex_p, 0, float_rep, TYPE_PRECISION (type), + TREE_INT_CST_LOW (TYPE_SIZE (type)), TYPE_ALIGN (type)); skip_p = true; } } /* If no predefined C types were found, register the mode itself. */ - if (!skip_p) f (GET_MODE_NAME (i), digs, complex_p, vector_p ? GET_MODE_NUNITS (i) : 0, float_rep, - GET_MODE_PRECISION (i), GET_MODE_ALIGNMENT (i)); + GET_MODE_PRECISION (i), GET_MODE_BITSIZE (i), + GET_MODE_ALIGNMENT (i)); } } diff --git a/gcc/ada/get_targ.ads b/gcc/ada/get_targ.ads index 19f5385e12f3..98be7c9a771a 100644 --- a/gcc/ada/get_targ.ads +++ b/gcc/ada/get_targ.ads @@ -6,7 +6,7 @@ -- -- -- S p e c -- -- -- --- Copyright (C) 1992-2013, Free Software Foundation, Inc. -- +-- Copyright (C) 1992-2014, 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- -- @@ -28,8 +28,8 @@ -- exp_dbug and the elaboration of ttypes, via the Set_Targs package. -- It also contains the routine for registering floating-point types. --- NOTE: Any changes in this package must be reflected in jgettarg.ads --- and aa_getta.ads and any other versions of this package. +-- NOTE: Any changes in this package must be reflected in aa_getta.adb +-- and any other version in the various back ends. -- Note that all these values return sizes of C types with corresponding -- names. This allows GNAT to define the corresponding Ada types to have @@ -134,6 +134,7 @@ package Get_Targ is Complex : Boolean; -- True iff type has real and imaginary parts Count : Natural; -- Number of elements in vector, 0 otherwise Float_Rep : Float_Rep_Kind; -- Representation used for fpt type + Precision : Positive; -- Precision of representation in bits Size : Positive; -- Size of representation in bits Alignment : Natural); -- Required alignment in bits pragma Convention (C, Register_Type_Proc); diff --git a/gcc/ada/set_targ.adb b/gcc/ada/set_targ.adb index a4a811d6bdb2..d6268c823332 100755 --- a/gcc/ada/set_targ.adb +++ b/gcc/ada/set_targ.adb @@ -6,7 +6,7 @@ -- -- -- B o d y -- -- -- --- Copyright (C) 2013, Free Software Foundation, Inc. -- +-- Copyright (C) 2013-2014, 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- -- @@ -140,6 +140,7 @@ package body Set_Targ is Complex : Boolean; Count : Natural; Float_Rep : Float_Rep_Kind; + Precision : Positive; Size : Positive; Alignment : Natural); pragma Convention (C, Register_Float_Type); @@ -151,7 +152,8 @@ package body Set_Targ is -- non-zero if the type has real and imaginary parts (also ignored during -- registration). Count is the number of elements in a vector type (zero = -- not a vector, registration ignores vectors). Float_Rep shows the kind of - -- floating-point type, and Size/Alignment are the size/alignment in bits. + -- floating-point type, and Precision, Size and Alignment are the precision + -- size and alignment in bits. -- -- So to summarize, the only types that are actually registered have Digs -- non-zero, Complex zero (false), and Count zero (not a vector). @@ -179,6 +181,7 @@ package body Set_Targ is Complex : Boolean; Count : Natural; Float_Rep : Float_Rep_Kind; + Precision : Positive; Size : Positive; Alignment : Natural) is @@ -244,13 +247,24 @@ package body Set_Targ is else Write_Str ("mod 2**"); - Write_Int (Int (Size / Positive'Max (1, Count))); + Write_Int (Int (Precision / Positive'Max (1, Count))); Write_Line (";"); end if; - Write_Str ("for " & T (1 .. Last) & "'Size use "); - Write_Int (Int (Size)); - Write_Line (";"); + if Precision = Size then + Write_Str ("for " & T (1 .. Last) & "'Size use "); + Write_Int (Int (Size)); + Write_Line (";"); + + else + Write_Str ("for " & T (1 .. Last) & "'Value_Size use "); + Write_Int (Int (Precision)); + Write_Line (";"); + + Write_Str ("for " & T (1 .. Last) & "'Object_Size use "); + Write_Int (Int (Size)); + Write_Line (";"); + end if; Write_Str ("for " & T (1 .. Last) & "'Alignment use "); Write_Int (Int (Alignment / 8)); @@ -286,6 +300,7 @@ package body Set_Targ is (NAME => new String'(T (1 .. Last)), DIGS => Digs, FLOAT_REP => Float_Rep, + PRECISION => Precision, SIZE => Size, ALIGNMENT => Alignment); end if; @@ -448,7 +463,7 @@ package body Set_Targ is AddC (' '); - AddN (E.SIZE); + AddN (E.PRECISION); AddC (' '); AddN (E.ALIGNMENT); @@ -826,7 +841,7 @@ begin N := N + 1; Check_Spaces; - E.SIZE := Get_Nat; + E.PRECISION := Get_Nat; Check_Spaces; E.ALIGNMENT := Get_Nat; @@ -835,6 +850,11 @@ begin FailN ("junk at end of line for"); end if; + -- ??? We do not read E.SIZE, see Write_Target_Dependent_Values + + E.SIZE := + (E.PRECISION + E.ALIGNMENT - 1) / E.ALIGNMENT * E.ALIGNMENT; + N := N + 1; end; end loop; diff --git a/gcc/ada/set_targ.ads b/gcc/ada/set_targ.ads index 62008cd5b4e0..d3ae3d838ffc 100755 --- a/gcc/ada/set_targ.ads +++ b/gcc/ada/set_targ.ads @@ -6,7 +6,7 @@ -- -- -- S p e c -- -- -- --- Copyright (C) 2013, Free Software Foundation, Inc. -- +-- Copyright (C) 2013-2014, 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- -- @@ -94,6 +94,7 @@ package Set_Targ is NAME : String_Ptr; -- Name of mode (no null character at end) DIGS : Natural; -- Digits for floating-point type FLOAT_REP : Float_Rep_Kind; -- Float representation + PRECISION : Natural; -- Precision in bits SIZE : Natural; -- Size in bits ALIGNMENT : Natural; -- Alignment in bits end record; @@ -130,7 +131,7 @@ package Set_Targ is -- -- One line per registered mode -- - -- name digs float_rep size alignment + -- name digs float_rep precision alignment -- -- where name is the string name of the type (which can have single -- spaces embedded in the name (e.g. long double). The name is followed @@ -138,5 +139,12 @@ package Set_Targ is -- for a Mode_Entry (where float_rep is I/V/A for IEEE-754-Binary, -- Vax_Native, AAMP), fields are separated by at least one blank, and -- a LF character immediately follows the alignment field. + -- + -- ??? We do not write the size for backward compatibility reasons, + -- which means that target.atp will not be a complete description for + -- the very peculiar cases where the size cannot be computed from the + -- precision and the alignment by the formula: + -- + -- size := (precision + alignment - 1) / alignment * alignment end Set_Targ;