From 002bdd685cc819e9a1609c97d5f2281f6109b297 Mon Sep 17 00:00:00 2001 From: Arnaud Charlet Date: Tue, 2 Aug 2011 15:00:21 +0200 Subject: [PATCH] [multiple changes] 2011-08-02 Geert Bosch * gcc-interface/gigi.h, gcc-interface/misc.c (enumerate_modes): New function. * gcc-interface/Make-lang.in: Update dependencies. 2011-08-02 Olivier Hainque * gcc-interface/trans.c (Subprogram_Body_to_gnu): Set the function end_locus. From-SVN: r177141 --- gcc/ada/ChangeLog | 11 +++ gcc/ada/gcc-interface/Make-lang.in | 17 +++-- gcc/ada/gcc-interface/gigi.h | 5 ++ gcc/ada/gcc-interface/misc.c | 119 +++++++++++++++++++++++++++++ gcc/ada/gcc-interface/trans.c | 6 ++ 5 files changed, 150 insertions(+), 8 deletions(-) diff --git a/gcc/ada/ChangeLog b/gcc/ada/ChangeLog index 0d78dae154e..d249de0df52 100644 --- a/gcc/ada/ChangeLog +++ b/gcc/ada/ChangeLog @@ -1,3 +1,14 @@ +2011-08-02 Geert Bosch + + * gcc-interface/gigi.h, gcc-interface/misc.c (enumerate_modes): New + function. + * gcc-interface/Make-lang.in: Update dependencies. + +2011-08-02 Olivier Hainque + + * gcc-interface/trans.c (Subprogram_Body_to_gnu): Set the function + end_locus. + 2011-08-02 Javier Miranda * sem_ch3.adb (Check_Anonymous_Access_Components): Create extra formals diff --git a/gcc/ada/gcc-interface/Make-lang.in b/gcc/ada/gcc-interface/Make-lang.in index 96cf1c628ad..c745c404f83 100644 --- a/gcc/ada/gcc-interface/Make-lang.in +++ b/gcc/ada/gcc-interface/Make-lang.in @@ -333,6 +333,7 @@ GNAT_ADA_OBJS = \ ada/urealp.o \ ada/usage.o \ ada/validsw.o \ + ada/warnsw.o \ ada/widechar.o # Object files for gnat executables @@ -1530,14 +1531,14 @@ ada/csets.o : ada/ada.ads ada/a-unccon.ads ada/a-uncdea.ads ada/csets.ads \ ada/cstand.o : ada/ada.ads ada/a-except.ads ada/a-unccon.ads \ ada/a-uncdea.ads ada/alloc.ads ada/aspects.ads ada/atree.ads \ - ada/atree.adb ada/casing.ads ada/checks.ads ada/csets.ads \ - ada/cstand.ads ada/cstand.adb ada/debug.ads ada/einfo.ads ada/einfo.adb \ - ada/elists.ads ada/err_vars.ads ada/errout.ads ada/errout.adb \ - ada/erroutc.ads ada/erroutc.adb ada/exp_ch11.ads ada/exp_disp.ads \ - ada/exp_tss.ads ada/exp_util.ads ada/fname.ads ada/freeze.ads \ - ada/get_targ.ads ada/gnat.ads ada/g-htable.ads ada/gnatvsn.ads \ - ada/hostparm.ads ada/interfac.ads ada/layout.ads ada/lib.ads \ - ada/lib-xref.ads ada/namet.ads ada/namet.adb ada/nlists.ads \ + ada/atree.adb ada/back_end.ads ada/casing.ads ada/checks.ads \ + ada/csets.ads ada/cstand.ads ada/cstand.adb ada/debug.ads ada/einfo.ads \ + ada/einfo.adb ada/elists.ads ada/err_vars.ads ada/errout.ads \ + ada/errout.adb ada/erroutc.ads ada/erroutc.adb ada/exp_ch11.ads \ + ada/exp_disp.ads ada/exp_tss.ads ada/exp_util.ads ada/fname.ads \ + ada/freeze.ads ada/get_targ.ads ada/gnat.ads ada/g-htable.ads \ + ada/gnatvsn.ads ada/hostparm.ads ada/interfac.ads ada/layout.ads \ + ada/lib.ads ada/lib-xref.ads ada/namet.ads ada/namet.adb ada/nlists.ads \ ada/nlists.adb ada/nmake.ads ada/nmake.adb ada/opt.ads ada/output.ads \ ada/restrict.ads ada/rident.ads ada/rtsfind.ads ada/scans.ads \ ada/scn.ads ada/scng.ads ada/scng.adb ada/sem.ads ada/sem_attr.ads \ diff --git a/gcc/ada/gcc-interface/gigi.h b/gcc/ada/gcc-interface/gigi.h index e8a725979e8..13c9f5418f8 100644 --- a/gcc/ada/gcc-interface/gigi.h +++ b/gcc/ada/gcc-interface/gigi.h @@ -929,6 +929,11 @@ extern bool default_pass_by_ref (tree gnu_type); if it should be passed by reference. */ extern bool 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. */ +extern void enumerate_modes (void (*f) (const char *, int, int, int, int, int, + int)); + /* Return the size of the FP mode with precision PREC. */ extern int fp_prec_to_size (int prec); diff --git a/gcc/ada/gcc-interface/misc.c b/gcc/ada/gcc-interface/misc.c index 62e7ac7769b..a03bb0fbf35 100644 --- a/gcc/ada/gcc-interface/misc.c +++ b/gcc/ada/gcc-interface/misc.c @@ -39,6 +39,7 @@ #include "opts.h" #include "options.h" #include "plugin.h" +#include "real.h" #include "function.h" /* For pass_by_reference. */ #include "ada.h" @@ -636,6 +637,124 @@ must_pass_by_ref (tree gnu_type) && TREE_CODE (TYPE_SIZE (gnu_type)) != INTEGER_CST)); } +/* 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 + 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 + be in order of preference, with the smallest/cheapest types first. + + In particular, C predefined types should be listed before other types, + binary floating point types before decimal ones, and narrower/cheaper + type versions before more expensive ones. In type selection the first + matching variant will be used. + + NAME pointer to first char of type name + DIGS number of decimal digits for floating-point modes, else 0 + 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 + ALIGN number of bits to which mode is aligned. */ + +void +enumerate_modes (void (*f) (const char *, int, int, int, int, int, int)) +{ + const tree c_types[] + = { float_type_node, double_type_node, long_double_type_node }; + const char *const c_names[] + = { "float", "double", "long double" }; + int iloop; + + for (iloop = 0; iloop < NUM_MACHINE_MODES; iloop++) + { + enum machine_mode i = (enum machine_mode) iloop; + enum machine_mode inner_mode = i; + bool float_p = false; + bool complex_p = false; + bool vector_p = false; + bool skip_p = false; + int digs = 0; + unsigned int nameloop; + Float_Rep_Kind float_rep = IEEE_Binary; /* Until proven otherwise */ + + switch (GET_MODE_CLASS (i)) + { + case MODE_INT: + break; + case MODE_FLOAT: + float_p = true; + break; + case MODE_COMPLEX_INT: + complex_p = true; + inner_mode = GET_MODE_INNER (i); + break; + case MODE_COMPLEX_FLOAT: + float_p = true; + complex_p = true; + inner_mode = GET_MODE_INNER (i); + break; + case MODE_VECTOR_INT: + vector_p = true; + inner_mode = GET_MODE_INNER (i); + break; + case MODE_VECTOR_FLOAT: + float_p = true; + vector_p = true; + inner_mode = GET_MODE_INNER (i); + break; + default: + skip_p = true; + } + + if (float_p) + { + const struct real_format *fmt = REAL_MODE_FORMAT (inner_mode); + + if (fmt->b == 2) + digs = (fmt->p - 1) * 1233 / 4096; /* scale by log (2) */ + + else if (fmt->b == 10) + digs = fmt->p; + + else + gcc_unreachable(); + + if (fmt == &vax_f_format + || fmt == &vax_d_format + || fmt == &vax_g_format) + float_rep = VAX_Native; + } + + /* 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) + for (nameloop = 0; nameloop < ARRAY_SIZE (c_types); nameloop++) + { + tree typ = c_types[nameloop]; + const char *nam = c_names[nameloop]; + + if (TYPE_MODE (typ) == i) + { + f (nam, digs, complex_p, + vector_p ? GET_MODE_NUNITS (i) : 0, float_rep, + TYPE_PRECISION (typ), TYPE_ALIGN (typ)); + 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)); + } +} + /* Return the size of the FP mode with precision PREC. */ int diff --git a/gcc/ada/gcc-interface/trans.c b/gcc/ada/gcc-interface/trans.c index b0b83b3383b..f9acdcdfeef 100644 --- a/gcc/ada/gcc-interface/trans.c +++ b/gcc/ada/gcc-interface/trans.c @@ -2762,6 +2762,12 @@ Subprogram_Body_to_gnu (Node_Id gnat_node) end_subprog_body (gnu_result); + /* Attempt setting the end_locus of our GCC body tree, typically a + BIND_EXPR or STATEMENT_LIST, then the end_locus of our GCC subprogram + declaration tree. */ + set_end_locus_from_node (gnu_result, gnat_node); + set_end_locus_from_node (gnu_subprog_decl, gnat_node); + /* Finally annotate the parameters and disconnect the trees for parameters that we have turned into variables since they are now unusable. */ for (gnat_param = First_Formal_With_Extras (gnat_subprog_id); -- 2.30.2