X-Git-Url: http://git.sourceforge.jp/view?a=blobdiff_plain;f=gcc%2Fgenmodes.c;h=8b6f5bce96b937f71fe76d47916dee167d2bb59b;hb=e6c80a80e7e5827932e5b981ee24798b607fca3e;hp=d8ba5df01484c5fdb2d23d3e93cf301d5a7f8e85;hpb=3c28f41a5c47111104ef608679448ae441408286;p=pf3gnuchains%2Fgcc-fork.git diff --git a/gcc/genmodes.c b/gcc/genmodes.c index d8ba5df0148..8b6f5bce96b 100644 --- a/gcc/genmodes.c +++ b/gcc/genmodes.c @@ -1,12 +1,12 @@ /* Generate the machine mode enumeration and associated tables. - Copyright (C) 2003, 2004 + Copyright (C) 2003, 2004, 2005, 2006, 2007, 2010 Free Software Foundation, Inc. This file is part of GCC. GCC is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free -Software Foundation; either version 2, or (at your option) any later +Software Foundation; either version 3, or (at your option) any later version. GCC is distributed in the hope that it will be useful, but WITHOUT ANY @@ -15,9 +15,8 @@ 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 -along with GCC; see the file COPYING. If not, write to the Free -Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA -02110-1301, USA. */ +along with GCC; see the file COPYING3. If not see +. */ #include "bconfig.h" #include "system.h" @@ -64,7 +63,6 @@ struct mode_data struct mode_data *component; /* mode of components */ struct mode_data *wider; /* next wider mode */ - struct mode_data *wider_2x; /* 2x wider mode */ struct mode_data *contained; /* Pointer to list of modes that have this mode as a component. */ @@ -73,6 +71,8 @@ struct mode_data const char *file; /* file and line of definition, */ unsigned int line; /* for error reporting */ unsigned int counter; /* Rank ordering of modes */ + unsigned int ibit; /* the number of integral bits */ + unsigned int fbit; /* the number of fractional bits */ }; static struct mode_data *modes[MAX_MODE_CLASS]; @@ -82,8 +82,8 @@ static struct mode_data *void_mode; static const struct mode_data blank_mode = { 0, "", MAX_MODE_CLASS, -1U, -1U, -1U, -1U, - 0, 0, 0, 0, 0, 0, - "", 0, 0 + 0, 0, 0, 0, 0, + "", 0, 0, 0, 0 }; static htab_t modes_by_name; @@ -104,6 +104,8 @@ struct mode_adjust static struct mode_adjust *adj_bytesize; static struct mode_adjust *adj_alignment; static struct mode_adjust *adj_format; +static struct mode_adjust *adj_ibit; +static struct mode_adjust *adj_fbit; /* Mode class operations. */ static enum mode_class @@ -126,6 +128,10 @@ vector_class (enum mode_class cl) { case MODE_INT: return MODE_VECTOR_INT; case MODE_FLOAT: return MODE_VECTOR_FLOAT; + case MODE_FRACT: return MODE_VECTOR_FRACT; + case MODE_UFRACT: return MODE_VECTOR_UFRACT; + case MODE_ACCUM: return MODE_VECTOR_ACCUM; + case MODE_UACCUM: return MODE_VECTOR_UACCUM; default: error ("no vector class for class %s", mode_class_names[cl]); return MODE_RANDOM; @@ -172,7 +178,7 @@ new_mode (enum mode_class cl, const char *name, n_modes[cl]++; *htab_find_slot (modes_by_name, m, INSERT) = m; - + return m; } @@ -200,7 +206,8 @@ static void ATTRIBUTE_UNUSED new_adjust (const char *name, struct mode_adjust **category, const char *catname, const char *adjustment, - enum mode_class required_class, + enum mode_class required_class_from, + enum mode_class required_class_to, const char *file, unsigned int line) { struct mode_data *mode = find_mode (name); @@ -214,13 +221,15 @@ new_adjust (const char *name, return; } - if (required_class != MODE_RANDOM && mode->cl != required_class) + if (required_class_from != MODE_RANDOM + && (mode->cl < required_class_from || mode->cl > required_class_to)) { - error ("%s:%d: mode \"%s\" is not class %s", - file, line, name, mode_class_names[required_class] + 5); + error ("%s:%d: mode \"%s\" is not among class {%s, %s}", + file, line, name, mode_class_names[required_class_from] + 5, + mode_class_names[required_class_to] + 5); return; } - + for (a = *category; a; a = a->next) if (a->mode == mode) { @@ -327,11 +336,16 @@ complete_mode (struct mode_data *m) case MODE_INT: case MODE_FLOAT: case MODE_DECIMAL_FLOAT: + case MODE_FRACT: + case MODE_UFRACT: + case MODE_ACCUM: + case MODE_UACCUM: /* A scalar mode must have a byte size, may have a bit size, and must not have components. A float mode must have a format. */ validate_mode (m, OPTIONAL, SET, UNSET, UNSET, - m->cl != MODE_INT ? SET : UNSET); + (m->cl == MODE_FLOAT || m->cl == MODE_DECIMAL_FLOAT) + ? SET : UNSET); m->ncomponents = 1; m->component = 0; @@ -361,6 +375,10 @@ complete_mode (struct mode_data *m) case MODE_VECTOR_INT: case MODE_VECTOR_FLOAT: + case MODE_VECTOR_FRACT: + case MODE_VECTOR_UFRACT: + case MODE_VECTOR_ACCUM: + case MODE_VECTOR_UACCUM: /* Vector modes should have a component and a number of components. */ validate_mode (m, UNSET, UNSET, SET, SET, UNSET); if (m->component->precision != (unsigned int)-1) @@ -533,6 +551,35 @@ make_int_mode (const char *name, m->precision = precision; } +#define FRACT_MODE(N, Y, F) \ + make_fixed_point_mode (MODE_FRACT, #N, Y, 0, F, __FILE__, __LINE__) + +#define UFRACT_MODE(N, Y, F) \ + make_fixed_point_mode (MODE_UFRACT, #N, Y, 0, F, __FILE__, __LINE__) + +#define ACCUM_MODE(N, Y, I, F) \ + make_fixed_point_mode (MODE_ACCUM, #N, Y, I, F, __FILE__, __LINE__) + +#define UACCUM_MODE(N, Y, I, F) \ + make_fixed_point_mode (MODE_UACCUM, #N, Y, I, F, __FILE__, __LINE__) + +/* Create a fixed-point mode by setting CL, NAME, BYTESIZE, IBIT, FBIT, + FILE, and LINE. */ + +static void +make_fixed_point_mode (enum mode_class cl, + const char *name, + unsigned int bytesize, + unsigned int ibit, + unsigned int fbit, + const char *file, unsigned int line) +{ + struct mode_data *m = new_mode (cl, name, file, line); + m->bytesize = bytesize; + m->ibit = ibit; + m->fbit = fbit; +} + #define FLOAT_MODE(N, Y, F) FRACTIONAL_FLOAT_MODE (N, -1U, Y, F) #define FRACTIONAL_FLOAT_MODE(N, B, Y, F) \ make_float_mode (#N, B, Y, #F, __FILE__, __LINE__) @@ -635,7 +682,9 @@ make_vector_mode (enum mode_class bclass, error ("%s:%d: no mode \"%s\"", file, line, base); return; } - if (component->cl != bclass) + if (component->cl != bclass + && (component->cl != MODE_PARTIAL_INT + || bclass != MODE_INT)) { error ("%s:%d: mode \"%s\" is not class %s", file, line, base, mode_class_names[bclass] + 5); @@ -656,12 +705,14 @@ make_vector_mode (enum mode_class bclass, } /* Adjustability. */ -#define _ADD_ADJUST(A, M, X, C) \ - new_adjust (#M, &adj_##A, #A, #X, MODE_##C, __FILE__, __LINE__) +#define _ADD_ADJUST(A, M, X, C1, C2) \ + new_adjust (#M, &adj_##A, #A, #X, MODE_##C1, MODE_##C2, __FILE__, __LINE__) -#define ADJUST_BYTESIZE(M, X) _ADD_ADJUST(bytesize, M, X, RANDOM) -#define ADJUST_ALIGNMENT(M, X) _ADD_ADJUST(alignment, M, X, RANDOM) -#define ADJUST_FLOAT_FORMAT(M, X) _ADD_ADJUST(format, M, X, FLOAT) +#define ADJUST_BYTESIZE(M, X) _ADD_ADJUST(bytesize, M, X, RANDOM, RANDOM) +#define ADJUST_ALIGNMENT(M, X) _ADD_ADJUST(alignment, M, X, RANDOM, RANDOM) +#define ADJUST_FLOAT_FORMAT(M, X) _ADD_ADJUST(format, M, X, FLOAT, FLOAT) +#define ADJUST_IBIT(M, X) _ADD_ADJUST(ibit, M, X, ACCUM, UACCUM) +#define ADJUST_FBIT(M, X) _ADD_ADJUST(fbit, M, X, FRACT, UACCUM) static void create_modes (void) @@ -687,8 +738,8 @@ create_modes (void) static int cmp_modes (const void *a, const void *b) { - struct mode_data *m = *(struct mode_data **)a; - struct mode_data *n = *(struct mode_data **)b; + const struct mode_data *const m = *(const struct mode_data *const*)a; + const struct mode_data *const n = *(const struct mode_data *const*)b; if (m->bytesize > n->bytesize) return 1; @@ -738,7 +789,7 @@ calc_wider_mode (void) /* Allocate max_n_modes + 1 entries to leave room for the extra null pointer assigned after the qsort call below. */ - sortbuf = (struct mode_data **) alloca ((max_n_modes + 1) * sizeof (struct mode_data *)); + sortbuf = XALLOCAVEC (struct mode_data *, max_n_modes + 1); for (c = 0; c < MAX_MODE_CLASS; c++) { @@ -752,7 +803,6 @@ calc_wider_mode (void) for (prev = 0, m = modes[c]; m; m = next) { m->wider = void_mode; - m->wider_2x = void_mode; /* this is nreverse */ next = m->next; @@ -775,7 +825,6 @@ calc_wider_mode (void) for (j = 0; j < i; j++) sortbuf[j]->next = sortbuf[j]->wider = sortbuf[j + 1]; - modes[c] = sortbuf[0]; } } @@ -784,8 +833,7 @@ calc_wider_mode (void) /* Output routines. */ #define tagged_printf(FMT, ARG, TAG) do { \ - int count_; \ - printf (" " FMT ",%n", ARG, &count_); \ + int count_ = printf (" " FMT ",", ARG); \ printf ("%*s/* %s */\n", 27 - count_, "", TAG); \ } while (0) @@ -819,8 +867,7 @@ enum machine_mode\n{"); for (c = 0; c < MAX_MODE_CLASS; c++) for (m = modes[c]; m; m = m->next) { - int count_; - printf (" %smode,%n", m->name, &count_); + int count_ = printf (" %smode,", m->name); printf ("%*s/* %s:%d */\n", 27 - count_, "", trim_filename (m->file), m->line); } @@ -861,6 +908,8 @@ enum machine_mode\n{"); #if 0 /* disabled for backward compatibility, temporary */ printf ("#define CONST_REAL_FORMAT_FOR_MODE%s\n", adj_format ? "" :" const"); #endif + printf ("#define CONST_MODE_IBIT%s\n", adj_ibit ? "" : " const"); + printf ("#define CONST_MODE_FBIT%s\n", adj_fbit ? "" : " const"); puts ("\ \n\ #endif /* insn-modes.h */"); @@ -1010,6 +1059,21 @@ emit_mode_wider (void) continue; } + /* For vectors we want twice the number of components, + with the same element type. */ + if (m->cl == MODE_VECTOR_INT + || m->cl == MODE_VECTOR_FLOAT + || m->cl == MODE_VECTOR_FRACT + || m->cl == MODE_VECTOR_UFRACT + || m->cl == MODE_VECTOR_ACCUM + || m->cl == MODE_VECTOR_UACCUM) + { + if (m2->ncomponents != 2 * m->ncomponents) + continue; + if (m->component != m2->component) + continue; + } + break; } if (m2 == void_mode) @@ -1095,7 +1159,7 @@ emit_class_narrowest_mode (void) ? modes[c]->next->name : void_mode->name)) : void_mode->name); - + print_closer (); } @@ -1108,7 +1172,7 @@ emit_real_format_for_mode (void) or not the table itself is constant. For backward compatibility this table is always writable - (several targets modify it in OVERRIDE_OPTIONS). FIXME: + (several targets modify it in TARGET_OPTION_OVERRIDE). FIXME: convert all said targets to use ADJUST_FORMAT instead. */ #if 0 print_maybe_const_decl ("const struct real_format *%s", @@ -1173,6 +1237,10 @@ emit_mode_adjustments (void) case MODE_VECTOR_INT: case MODE_VECTOR_FLOAT: + case MODE_VECTOR_FRACT: + case MODE_VECTOR_UFRACT: + case MODE_VECTOR_ACCUM: + case MODE_VECTOR_UACCUM: printf (" mode_size[%smode] = %d*s;\n", m->name, m->ncomponents); printf (" mode_base_align[%smode] = (%d*s) & (~(%d*s)+1);\n", @@ -1207,6 +1275,10 @@ emit_mode_adjustments (void) case MODE_VECTOR_INT: case MODE_VECTOR_FLOAT: + case MODE_VECTOR_FRACT: + case MODE_VECTOR_UFRACT: + case MODE_VECTOR_ACCUM: + case MODE_VECTOR_UACCUM: printf (" mode_base_align[%smode] = %d*s;\n", m->name, m->ncomponents); break; @@ -1219,7 +1291,23 @@ emit_mode_adjustments (void) } } } - + + /* Ibit adjustments don't have to propagate. */ + for (a = adj_ibit; a; a = a->next) + { + printf ("\n /* %s:%d */\n s = %s;\n", + a->file, a->line, a->adjustment); + printf (" mode_ibit[%smode] = s;\n", a->mode->name); + } + + /* Fbit adjustments don't have to propagate. */ + for (a = adj_fbit; a; a = a->next) + { + printf ("\n /* %s:%d */\n s = %s;\n", + a->file, a->line, a->adjustment); + printf (" mode_fbit[%smode] = s;\n", a->mode->name); + } + /* Real mode formats don't have to propagate anywhere. */ for (a = adj_format; a; a = a->next) printf ("\n /* %s:%d */\n REAL_MODE_FORMAT (%smode) = %s;\n", @@ -1228,6 +1316,43 @@ emit_mode_adjustments (void) puts ("}"); } +/* Emit ibit for all modes. */ + +static void +emit_mode_ibit (void) +{ + int c; + struct mode_data *m; + + print_maybe_const_decl ("%sunsigned char", + "mode_ibit", "NUM_MACHINE_MODES", + ibit); + + for_all_modes (c, m) + tagged_printf ("%u", m->ibit, m->name); + + print_closer (); +} + +/* Emit fbit for all modes. */ + +static void +emit_mode_fbit (void) +{ + int c; + struct mode_data *m; + + print_maybe_const_decl ("%sunsigned char", + "mode_fbit", "NUM_MACHINE_MODES", + fbit); + + for_all_modes (c, m) + tagged_printf ("%u", m->fbit, m->name); + + print_closer (); +} + + static void emit_insn_modes_c (void) { @@ -1244,6 +1369,8 @@ emit_insn_modes_c (void) emit_class_narrowest_mode (); emit_real_format_for_mode (); emit_mode_adjustments (); + emit_mode_ibit (); + emit_mode_fbit (); } static void @@ -1258,7 +1385,7 @@ emit_min_insn_modes_c (void) /* Master control. */ int -main(int argc, char **argv) +main (int argc, char **argv) { bool gen_header = false, gen_min = false; progname = argv[0]; @@ -1282,7 +1409,7 @@ main(int argc, char **argv) if (have_error) return FATAL_EXIT_CODE; - + calc_wider_mode (); if (gen_header)