From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 62784 invoked by alias); 3 Sep 2018 12:27:40 -0000 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Received: (qmail 62755 invoked by uid 89); 3 Sep 2018 12:27:39 -0000 Authentication-Results: sourceware.org; auth=none X-Spam-SWARE-Status: No, score=-11.1 required=5.0 tests=BAYES_00,GIT_PATCH_2,GIT_PATCH_3,KAM_ASCII_DIVIDERS,SPF_PASS autolearn=ham version=3.3.2 spammy=shut, viable, lose, leaf X-HELO: mx1.suse.de Received: from mx2.suse.de (HELO mx1.suse.de) (195.135.220.15) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with ESMTP; Mon, 03 Sep 2018 12:27:36 +0000 Received: from relay1.suse.de (unknown [195.135.220.254]) by mx1.suse.de (Postfix) with ESMTP id F00EFAFE7 for ; Mon, 3 Sep 2018 12:27:33 +0000 (UTC) Subject: Re: [RFH] split {generic,gimple}-match.c files To: Richard Biener , gcc-patches@gcc.gnu.org References: From: =?UTF-8?Q?Martin_Li=c5=a1ka?= Message-ID: Date: Mon, 03 Sep 2018 12:27:00 -0000 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:52.0) Gecko/20100101 Thunderbird/52.9.1 MIME-Version: 1.0 In-Reply-To: Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 7bit X-IsSubscribed: yes X-SW-Source: 2018-09/txt/msg00100.txt.bz2 On 04/25/2018 01:42 PM, Richard Biener wrote: > > The following patch^Whack splits $subject files into three, one > for the predicates (due to an implementation detail) and two for > the rest - for now into similar LOC size files. > > I'd like to get help on the makefile changes to make them less > verbose, somehow globbing the -[12p] parts. > > Also you can see the split point is manually chosen which means > it will bitrot. Timings for the stage2 compiles on a x86_64 > box are > > gimple-match-p.c 5s > generic-match-p.c 3s > gimple-match-1.c 85s > generic-match-1.c 56s > gimple-match-2.c 82s > generic-match-2.c 31s > > the required header files are quite big (and of course everything > needs to be exported without the analysis work becoming too cumbersome), > it's 3342 LOC for gimple-match-head.h and 1556 LOC for > generic-match-head.h > > The machine I tested is quite fast so the 80ish second timings are still > too slow I guess and thus splitting up into four files for gimple and > three files for generic looks better. > > Note we lose some inlining/cloning capability in the splitting process > (I see quite a bit of constprop/isra work being done on the generated > files). I didn't try to measure the runtime impact though. > > The patch still needs quite some TLC, it really is a bit hacky but I'd > like to get feedback on the approach and I didn't want to spend time > on programatically finding optimal split points (so everything is output > in the same semi-random order as before). > > Richard. > > > > Index: gcc/genmatch.c > =================================================================== > --- gcc/genmatch.c (revision 259638) > +++ gcc/genmatch.c (working copy) > @@ -1641,7 +1641,7 @@ struct decision_tree > dt_node *root; > > void insert (struct simplify *, unsigned); > - void gen (FILE *f, bool gimple); > + void gen (const char *, FILE *, vec &, bool gimple); > void print (FILE *f = stderr); > > decision_tree () { root = new dt_node (dt_node::DT_NODE, NULL); } > @@ -3608,12 +3608,25 @@ sinfo_hashmap_traits::equal_keys (const > return compare_op (v->s->result, v->s, candidate->s->result, candidate->s); > } > > +/* Write the common header for the GIMPLE/GENERIC IL matching routines. */ > + > +static void > +write_header (FILE *f, bool gimple) > +{ > + fprintf (f, "/* Generated automatically by the program `genmatch' from\n"); > + fprintf (f, " a IL pattern matching and simplification description. */\n"); > + > + /* Include the header instead of writing it awkwardly quoted here. */ > + fprintf (f, "\n#include \"%s-match-head.c\"\n", > + gimple ? "gimple" : "generic"); > +} > > /* Main entry to generate code for matching GIMPLE IL off the decision > tree. */ > > void > -decision_tree::gen (FILE *f, bool gimple) > +decision_tree::gen (const char *output, FILE *headerf, > + vec &pieces, bool gimple) > { > sinfo_map_t si; > > @@ -3624,6 +3637,34 @@ decision_tree::gen (FILE *f, bool gimple > gimple ? "GIMPLE" : "GENERIC", > root->num_leafs, root->max_level, root->total_size); > > + FILE *f; > + char *outputtem = NULL; > + if (output) > + outputtem = XNEWVEC (char, strlen (output) + strlen ("-1.c") + 1); > + > + unsigned do_header = headerf ? 2 : 1; > + unsigned n_per_part = -1U; > + unsigned file_n = output ? 1 : 2; > + do > + { > + unsigned n_fn = 0; > + do_header--; > + > + if (do_header) > + f = headerf; > + else if (!output) > + f = stdout; > + else > + { > + sprintf (outputtem, "%s-%d.c", output, file_n++); > + f = fopen (outputtem, "w"); > + if (!f) > + { > + perror ("failed to open output file"); > + exit(1); > + } > + write_header (f, gimple); > + } > /* First split out the transform part of equal leafs. */ > unsigned rcnt = 0; > unsigned fcnt = 1; > @@ -3643,21 +3684,22 @@ decision_tree::gen (FILE *f, bool gimple > } > > /* Generate a split out function with the leaf transform code. */ > + if (do_header || !output) > s->fname = xasprintf ("%s_simplify_%u", gimple ? "gimple" : "generic", > fcnt++); > if (gimple) > - fprintf (f, "\nstatic bool\n" > + fprintf (f, "\n%sbool\n" > "%s (code_helper *res_code, tree *res_ops,\n" > " gimple_seq *seq, tree (*valueize)(tree) " > "ATTRIBUTE_UNUSED,\n" > " const tree ARG_UNUSED (type), tree *ARG_UNUSED " > "(captures)\n", > - s->fname); > + headerf ? "" : "static ", s->fname); > else > { > - fprintf (f, "\nstatic tree\n" > + fprintf (f, "\n%stree\n" > "%s (location_t ARG_UNUSED (loc), const tree ARG_UNUSED (type),\n", > - (*iter).second->fname); > + headerf ? "" : "static ", (*iter).second->fname); > for (unsigned i = 0; > i < as_a (s->s->s->match)->ops.length (); ++i) > fprintf (f, " tree ARG_UNUSED (op%d),", i); > @@ -3674,7 +3716,12 @@ decision_tree::gen (FILE *f, bool gimple > fprintf (f, ", const combined_fn ARG_UNUSED (%s)", > s->s->s->for_subst_vec[i].first->id); > } > - > + n_fn++; > + if (do_header) > + { > + fprintf (f, ");\n"); > + continue; > + } > fprintf (f, ")\n{\n"); > s->s->gen_1 (f, 2, gimple, s->s->s->result); > if (gimple) > @@ -3682,7 +3729,22 @@ decision_tree::gen (FILE *f, bool gimple > else > fprintf (f, " return NULL_TREE;\n"); > fprintf (f, "}\n"); > + > + if (n_fn == pieces[file_n - 2]) > + { > + fclose (f); > + sprintf (outputtem, "%s-%d.c", output, file_n++); > + f = fopen (outputtem, "w"); > + if (!f) > + { > + perror ("failed to open output file"); > + exit(1); > + } > + write_header (f, gimple); > + n_fn = 0; > + } > } > + if (!do_header) > fprintf (stderr, "removed %u duplicate tails\n", rcnt); > > for (unsigned n = 1; n <= 3; ++n) > @@ -3702,20 +3764,26 @@ decision_tree::gen (FILE *f, bool gimple > continue; > > if (gimple) > - fprintf (f, "\nstatic bool\n" > + fprintf (f, "\n%sbool\n" > "gimple_simplify_%s (code_helper *res_code, tree *res_ops,\n" > " gimple_seq *seq, tree (*valueize)(tree) " > "ATTRIBUTE_UNUSED,\n" > " code_helper ARG_UNUSED (code), tree " > "ARG_UNUSED (type)\n", > - e->operation->id); > + headerf ? "" : "static ", e->operation->id); > else > - fprintf (f, "\nstatic tree\n" > + fprintf (f, "\n%stree\n" > "generic_simplify_%s (location_t ARG_UNUSED (loc), enum " > "tree_code ARG_UNUSED (code), const tree ARG_UNUSED (type)", > - e->operation->id); > + headerf ? "" : "static ", e->operation->id); > for (unsigned i = 0; i < n; ++i) > fprintf (f, ", tree op%d", i); > + n_fn++; > + if (do_header) > + { > + fprintf (f, ");\n"); > + continue; > + } > fprintf (f, ")\n"); > fprintf (f, "{\n"); > dop->gen_kids (f, 2, gimple); > @@ -3724,21 +3792,43 @@ decision_tree::gen (FILE *f, bool gimple > else > fprintf (f, " return NULL_TREE;\n"); > fprintf (f, "}\n"); > + > + if (n_fn == pieces[file_n - 2]) > + { > + fclose (f); > + sprintf (outputtem, "%s-%d.c", output, file_n++); > + f = fopen (outputtem, "w"); > + if (!f) > + { > + perror ("failed to open output file"); > + exit(1); > + } > + write_header (f, gimple); > + n_fn = 0; > + } > + > } > > /* Then generate the main entry with the outermost switch and > tail-calls to the split-out functions. */ > if (gimple) > - fprintf (f, "\nstatic bool\n" > + fprintf (f, "\n%sbool\n" > "gimple_simplify (code_helper *res_code, tree *res_ops,\n" > " gimple_seq *seq, tree (*valueize)(tree),\n" > - " code_helper code, const tree type"); > + " code_helper code, const tree type", > + headerf ? "" : "static "); > else > fprintf (f, "\ntree\n" > "generic_simplify (location_t loc, enum tree_code code, " > "const tree type ATTRIBUTE_UNUSED"); > for (unsigned i = 0; i < n; ++i) > fprintf (f, ", tree op%d", i); > + n_fn++; > + if (do_header) > + { > + fprintf (f, ");\n"); > + continue; > + } > fprintf (f, ")\n"); > fprintf (f, "{\n"); > > @@ -3786,19 +3876,46 @@ decision_tree::gen (FILE *f, bool gimple > else > fprintf (f, " return NULL_TREE;\n"); > fprintf (f, "}\n"); > + if (n_fn == pieces[file_n - 2]) > + { > + fclose (f); > + sprintf (outputtem, "%s-%d.c", output, file_n++); > + f = fopen (outputtem, "w"); > + if (!f) > + { > + perror ("failed to open output file"); > + exit(1); > + } > + write_header (f, gimple); > + n_fn = 0; > + } > + } > + > + n_per_part = n_fn / 4 + 1; > } > + while (do_header); > + if (output) > + fclose (f); > } > > /* Output code to implement the predicate P from the decision tree DT. */ > > void > -write_predicate (FILE *f, predicate_id *p, decision_tree &dt, bool gimple) > +write_predicate (FILE *f, predicate_id *p, decision_tree &dt, bool gimple, > + bool for_header) > { > fprintf (f, "\nbool\n" > - "%s%s (tree t%s%s)\n" > - "{\n", gimple ? "gimple_" : "tree_", p->id, > + "%s%s (tree t%s%s)", > + gimple ? "gimple_" : "tree_", p->id, > p->nargs > 0 ? ", tree *res_ops" : "", > gimple ? ", tree (*valueize)(tree) ATTRIBUTE_UNUSED" : ""); > + if (for_header) > + { > + fprintf (f, ";\n"); > + return; > + } > + > + fprintf (f, "\n{\n"); > /* Conveniently make 'type' available. */ > fprintf_indent (f, 2, "const tree type = TREE_TYPE (t);\n"); > > @@ -3810,18 +3927,6 @@ write_predicate (FILE *f, predicate_id * > "}\n"); > } > > -/* Write the common header for the GIMPLE/GENERIC IL matching routines. */ > - > -static void > -write_header (FILE *f, const char *head) > -{ > - fprintf (f, "/* Generated automatically by the program `genmatch' from\n"); > - fprintf (f, " a IL pattern matching and simplification description. */\n"); > - > - /* Include the header instead of writing it awkwardly quoted here. */ > - fprintf (f, "\n#include \"%s\"\n", head); > -} > - > > > /* AST parsing. */ > @@ -4969,6 +5074,9 @@ main (int argc, char **argv) > > bool gimple = true; > char *input = argv[argc-1]; > + char *output = NULL; > + char *header = NULL; > + auto_vec pieces; > for (int i = 1; i < argc - 1; ++i) > { > if (strcmp (argv[i], "--gimple") == 0) > @@ -4979,13 +5087,25 @@ main (int argc, char **argv) > verbose = 1; > else if (strcmp (argv[i], "-vv") == 0) > verbose = 2; > + else if (strcmp (argv[i], "-c") == 0) > + { > + char *endp; > + output = argv[++i]; > + while (i + 1 < argc - 1 > + && ISDIGIT (argv[i + 1][0])) > + pieces.safe_push (strtoul (argv[++i], &endp, 10)); > + } > + else if (strcmp (argv[i], "-h") == 0) > + header = argv[++i]; > else > { > fprintf (stderr, "Usage: genmatch " > - "[--gimple] [--generic] [-v[v]] input\n"); > + "[--gimple] [--generic] [-v[v]] " > + "[-c output num...] [-h header] input\n"); > return 1; > } > } > + pieces.safe_push (-1UL); > > line_table = XCNEW (struct line_maps); > linemap_init (line_table, 0); > @@ -5039,10 +5159,32 @@ add_operator (VIEW_CONVERT2, "view_conve > /* Parse ahead! */ > parser p (r); > > - if (gimple) > - write_header (stdout, "gimple-match-head.c"); > + FILE *f, *headerf = NULL; > + if (!output) > + f = stdout; > else > - write_header (stdout, "generic-match-head.c"); > + { > + char *outputtem = XNEWVEC (char, strlen (output) + strlen ("-1.c") + 1); > + sprintf (outputtem, "%s-p.c", output); > + f = fopen (outputtem, "w"); > + if (!f) > + { > + perror ("failed to open output file"); > + exit(1); > + } > + } > + if (header) > + { > + headerf = fopen (header, "w"); > + if (!headerf) > + { > + perror ("failed to open output file"); > + exit(1); > + } > + } > + > + fprintf (f, "#define GENFOO_MAIN_FILE 1\n"); > + write_header (f, gimple); > > /* Go over all predicates defined with patterns and perform > lowering and code generation. */ > @@ -5062,8 +5204,12 @@ add_operator (VIEW_CONVERT2, "view_conve > if (verbose == 2) > dt.print (stderr); > > - write_predicate (stdout, pred, dt, gimple); > + if (header) > + write_predicate (headerf, pred, dt, gimple, true); > + write_predicate (f, pred, dt, gimple, false); > } > + if (output) > + fclose (f); > > /* Lower the main simplifiers and generate code for them. */ > lower (p.simplifiers, gimple); > @@ -5079,7 +5225,10 @@ add_operator (VIEW_CONVERT2, "view_conve > if (verbose == 2) > dt.print (stderr); > > - dt.gen (stdout, gimple); > + dt.gen (output, headerf, pieces, gimple); > + > + if (header) > + fclose (headerf); > > /* Finalize. */ > cpp_finish (r, NULL); > Index: gcc/gimple-match-head.c > =================================================================== > --- gcc/gimple-match-head.c (revision 259638) > +++ gcc/gimple-match-head.c (working copy) > @@ -40,21 +40,10 @@ along with GCC; see the file COPYING3. > #include "case-cfn-macros.h" > #include "gimplify.h" > #include "optabs-tree.h" > +#include "gimple-match-head.h" > > > -/* Forward declarations of the private auto-generated matchers. > - They expect valueized operands in canonical order and do not > - perform simplification of all-constant operands. */ > -static bool gimple_simplify (code_helper *, tree *, > - gimple_seq *, tree (*)(tree), > - code_helper, tree, tree); > -static bool gimple_simplify (code_helper *, tree *, > - gimple_seq *, tree (*)(tree), > - code_helper, tree, tree, tree); > -static bool gimple_simplify (code_helper *, tree *, > - gimple_seq *, tree (*)(tree), > - code_helper, tree, tree, tree, tree); > - > +#if GENFOO_MAIN_FILE > > /* Return whether T is a constant that we'll dispatch to fold to > evaluate fully constant expressions. */ > @@ -772,6 +761,8 @@ gimple_simplify (gimple *stmt, > return false; > } > > +#endif > + > > /* Helper for the autogenerated code, valueize OP. */ > > Index: gcc/generic-match-head.c > =================================================================== > --- gcc/generic-match-head.c (revision 259638) > +++ gcc/generic-match-head.c (working copy) > @@ -34,6 +34,7 @@ along with GCC; see the file COPYING3. > #include "case-cfn-macros.h" > #include "gimplify.h" > #include "optabs-tree.h" > +#include "generic-match-head.h" > > > /* Routine to determine if the types T1 and T2 are effectively > Index: gcc/Makefile.in > =================================================================== > --- gcc/Makefile.in (revision 259638) > +++ gcc/Makefile.in (working copy) > @@ -216,8 +216,12 @@ gengtype-lex.o-warn = -Wno-error > libgcov-util.o-warn = -Wno-error > libgcov-driver-tool.o-warn = -Wno-error > libgcov-merge-tool.o-warn = -Wno-error > -gimple-match.o-warn = -Wno-unused > -generic-match.o-warn = -Wno-unused > +gimple-match-p.o-warn = -Wno-unused > +gimple-match-1.o-warn = -Wno-unused > +gimple-match-2.o-warn = -Wno-unused > +generic-match-p.o-warn = -Wno-unused > +generic-match-1.o-warn = -Wno-unused > +generic-match-2.o-warn = -Wno-unused > dfp.o-warn = -Wno-strict-aliasing > > # All warnings have to be shut off in stage1 if the compiler used then > @@ -771,7 +775,7 @@ COMPILERS = @all_compilers@ > > # List of things which should already be built whenever we try to use xgcc > # to compile anything (without linking). > -GCC_PASSES=xgcc$(exeext) specs > +GCC_PASSES=xgcc$(exeext) > > # Directory to link to, when using the target `maketest'. > DIR = ../gcc > @@ -1207,8 +1211,12 @@ C_COMMON_OBJS = c-family/c-common.o c-fa > # will build them sooner, because they are large and otherwise tend to be > # the last objects to finish building. > OBJS = \ > - gimple-match.o \ > - generic-match.o \ > + gimple-match-p.o \ > + generic-match-p.o \ > + gimple-match-1.o \ > + generic-match-1.o \ > + gimple-match-2.o \ > + generic-match-2.o \ > insn-attrtab.o \ > insn-automata.o \ > insn-dfatab.o \ > @@ -1654,7 +1662,9 @@ MOSTLYCLEANFILES = insn-flags.h insn-con > insn-output.c insn-recog.c insn-emit.c insn-extract.c insn-peep.c \ > insn-attr.h insn-attr-common.h insn-attrtab.c insn-dfatab.c \ > insn-latencytab.c insn-opinit.c insn-opinit.h insn-preds.c insn-constants.h \ > - tm-preds.h tm-constrs.h checksum-options gimple-match.c generic-match.c \ > + tm-preds.h tm-constrs.h checksum-options gimple-match-head.h gimple-match-1.c \ > + gimple-match-2.c gimple-match-p.c generic-match-head.h generic-match-1.c \ > + generic-match-p.c generic-match-2.c \ > tree-check.h min-insn-modes.c insn-modes.c insn-modes.h insn-modes-inline.h \ > genrtl.h gt-*.h gtype-*.h gtype-desc.c gtyp-input.list \ > case-cfn-macros.h cfn-operators.pd \ > @@ -1899,7 +1909,7 @@ all.internal: start.encap rest.encap doc > all.cross: native gcc-cross$(exeext) cpp$(exeext) specs \ > libgcc-support lang.all.cross doc selftest @GENINSRC@ srcextra > # This is what must be made before installing GCC and converting libraries. > -start.encap: native xgcc$(exeext) cpp$(exeext) specs \ > +start.encap: native xgcc$(exeext) cpp$(exeext) \ > libgcc-support lang.start.encap @GENINSRC@ srcextra > # These can't be made until after GCC can run. > rest.encap: lang.rest.encap > @@ -2054,7 +2064,7 @@ checksum-options: > libgcc-support: libgcc.mvars stmp-int-hdrs $(TCONFIG_H) \ > $(MACHMODE_H) gcov-iov.h > > -libgcc.mvars: config.status Makefile specs xgcc$(exeext) > +libgcc.mvars: config.status Makefile xgcc$(exeext) > : > tmp-libgcc.mvars > echo GCC_CFLAGS = '$(GCC_CFLAGS)' >> tmp-libgcc.mvars > echo INHIBIT_LIBC_CFLAGS = '$(INHIBIT_LIBC_CFLAGS)' >> tmp-libgcc.mvars > @@ -2271,8 +2281,9 @@ $(common_out_object_file): $(common_out_ > .PRECIOUS: insn-config.h insn-flags.h insn-codes.h insn-constants.h \ > insn-emit.c insn-recog.c insn-extract.c insn-output.c insn-peep.c \ > insn-attr.h insn-attr-common.h insn-attrtab.c insn-dfatab.c \ > - insn-latencytab.c insn-preds.c gimple-match.c generic-match.c \ > - insn-target-def.h > + insn-latencytab.c insn-preds.c gimple-match-head.h gimple-match-1.c \ > + gimple-match-2.c generic-match-head.h generic-match-1.c generic-match-2.c \ > + gimple-match-p.c generic-match-p.c insn-target-def.h > > # Dependencies for the md file. The first time through, we just assume > # the md file itself and the generated dependency file (in order to get > @@ -2504,18 +2515,36 @@ s-tm-texi: build/genhooks$(build_exeext) > false; \ > fi > > -gimple-match.c: s-match gimple-match-head.c ; @true > -generic-match.c: s-match generic-match-head.c ; @true > +gimple-match-p.c: s-match gimple-match-head.c ; @true > +gimple-match-1.c: s-match gimple-match-head.c ; @true > +gimple-match-2.c: s-match gimple-match-head.c ; @true > +generic-match-p.c: s-match generic-match-head.c ; @true > +generic-match-1.c: s-match generic-match-head.c ; @true > +generic-match-2.c: s-match generic-match-head.c ; @true > > s-match: build/genmatch$(build_exeext) $(srcdir)/match.pd cfn-operators.pd > - $(RUN_GEN) build/genmatch$(build_exeext) --gimple $(srcdir)/match.pd \ > - > tmp-gimple-match.c > - $(RUN_GEN) build/genmatch$(build_exeext) --generic $(srcdir)/match.pd \ > - > tmp-generic-match.c > - $(SHELL) $(srcdir)/../move-if-change tmp-gimple-match.c \ > - gimple-match.c > - $(SHELL) $(srcdir)/../move-if-change tmp-generic-match.c \ > - generic-match.c > + $(RUN_GEN) build/genmatch$(build_exeext) --gimple \ > + -h tmp-gimple-match-head.h -c tmp-gimple-match 460 \ > + $(srcdir)/match.pd > + $(RUN_GEN) build/genmatch$(build_exeext) --generic \ > + -h tmp-generic-match-head.h -c tmp-generic-match 290 \ > + $(srcdir)/match.pd > + $(SHELL) $(srcdir)/../move-if-change tmp-gimple-match-head.h \ > + gimple-match-head.h > + $(SHELL) $(srcdir)/../move-if-change tmp-gimple-match-1.c \ > + gimple-match-1.c > + $(SHELL) $(srcdir)/../move-if-change tmp-gimple-match-2.c \ > + gimple-match-2.c > + $(SHELL) $(srcdir)/../move-if-change tmp-gimple-match-p.c \ > + gimple-match-p.c > + $(SHELL) $(srcdir)/../move-if-change tmp-generic-match-head.h \ > + generic-match-head.h > + $(SHELL) $(srcdir)/../move-if-change tmp-generic-match-1.c \ > + generic-match-1.c > + $(SHELL) $(srcdir)/../move-if-change tmp-generic-match-2.c \ > + generic-match-2.c > + $(SHELL) $(srcdir)/../move-if-change tmp-generic-match-p.c \ > + generic-match-p.c > $(STAMP) s-match > > GTFILES = $(CPP_ID_DATA_H) $(srcdir)/input.h $(srcdir)/coretypes.h \ > Hi. I took a look at gimple-match.c and what about doing a split in following way: - all gimple_simplify_$number going into a separate header file (~12000 LOC) - all the function can be marked as static inline - all other gimple_simplify_$code can be split into arbitrary number of parts - we have 287 such functions where each function only calls gimple_simplify_$number and on average there 10 of such calls - that would allow to remove most of gimple_simplify_$number functions from the header file Richi do you think it will be viable? Martin