[v2] genemit.c (main): split insn-emit.c for compiling parallelly

Message ID 20200721031252.9486-1-jiejie_rong@c-sky.com
State New
Headers show
Series
  • [v2] genemit.c (main): split insn-emit.c for compiling parallelly
Related show

Commit Message

Jojo R July 21, 2020, 3:12 a.m.
gcc/ChangeLog:

	* genemit.c (main): Print 'split line'.
	* Makefile.in (insn-emit.c): Define split count and file

---
 gcc/Makefile.in | 10 ++++++
 gcc/genemit.c   | 86 +++++++++++++++++++++++++++----------------------
 2 files changed, 58 insertions(+), 38 deletions(-)

-- 
2.24.3 (Apple Git-128)

Comments

Dimitrij Mijoski via Gcc-patches July 21, 2020, 6:55 a.m. | #1
On Tue, Jul 21, 2020 at 11:14 AM Jojo <jiejie_rong@c-sky.com> wrote:
>

> gcc/ChangeLog:

>

>         * genemit.c (main): Print 'split line'.

>         * Makefile.in (insn-emit.c): Define split count and file

>


Thanks for working one this, following comments are based on the
assumption that the approach is feasible after your investigation.

It's great to accelerate compilation time, do you have any number
showing how much this can achieve, on a typical machine with
reasonable parallelism?

> ---

>  gcc/Makefile.in | 10 ++++++

>  gcc/genemit.c   | 86 +++++++++++++++++++++++++++----------------------

>  2 files changed, 58 insertions(+), 38 deletions(-)

>

> diff --git a/gcc/Makefile.in b/gcc/Makefile.in

> index 2ba76656dbf..f805050a119 100644

> --- a/gcc/Makefile.in

> +++ b/gcc/Makefile.in

> @@ -1253,6 +1253,13 @@ ANALYZER_OBJS = \

>  # We put the *-match.o and insn-*.o files first so that a parallel make

>  # will build them sooner, because they are large and otherwise tend to be

>  # the last objects to finish building.

> +

> +insn-generated-split-num = 15

Hardcode number 15 looks strange here, how shall we know it's enough?
Or one step further, can we use some kind of general match "*" for
writing make rules here?
> +

> +insn-emit-split-c = $(foreach o, $(shell for i in {1..$(insn-generated-split-num)}; do echo $$i; done), insn-emit$(o).c)

> +insn-emit-split-obj = $(patsubst %.c,%.o, $(insn-emit-split-c))

> +$(insn-emit-split-c): insn-emit.c

> +

>  OBJS = \

>         gimple-match.o \

>         generic-match.o \

> @@ -1260,6 +1267,7 @@ OBJS = \

>         insn-automata.o \

>         insn-dfatab.o \

>         insn-emit.o \

> +       $(insn-emit-split-obj) \

>         insn-extract.o \

>         insn-latencytab.o \

>         insn-modes.o \

> @@ -2367,6 +2375,8 @@ $(simple_generated_c:insn-%.c=s-%): s-%: build/gen%$(build_exeext)

>         $(RUN_GEN) build/gen$*$(build_exeext) $(md_file) \

>           $(filter insn-conditions.md,$^) > tmp-$*.c

>         $(SHELL) $(srcdir)/../move-if-change tmp-$*.c insn-$*.c

> +       -csplit insn-$*.c /i\ am\ split\ line/ -k -s {$(insn-generated-split-num)} -f insn-$* -b "%d.c"

> +       -( [ ! -s insn-$*0.c ] && for i in {1..$(insn-generated-split-num)}; do touch insn-$*$$i.c; done && echo "" > insn-$*.c)

Not sure if this is the first time that csplit/coreutils is used,
shall we mention it here
https://gcc.gnu.org/install/prerequisites.html, even check it in
configure?
>         $(STAMP) s-$*

>

>  # gencheck doesn't read the machine description, and the file produced

> diff --git a/gcc/genemit.c b/gcc/genemit.c

> index 84d07d388ee..fd60cdeeb96 100644

> --- a/gcc/genemit.c

> +++ b/gcc/genemit.c

> @@ -847,6 +847,45 @@ handle_overloaded_gen (overloaded_name *oname)

>      }

>  }

>

> +#define printf_include() \

> +  printf ("/* Generated automatically by the program `genemit'\n\

> +from the machine description file `md'.  */\n\n"); \

> +  printf ("#define IN_TARGET_CODE 1\n"); \

> +  printf ("#include \"config.h\"\n"); \

> +  printf ("#include \"system.h\"\n"); \

> +  printf ("#include \"coretypes.h\"\n"); \

> +  printf ("#include \"backend.h\"\n"); \

> +  printf ("#include \"predict.h\"\n"); \

> +  printf ("#include \"tree.h\"\n"); \

> +  printf ("#include \"rtl.h\"\n"); \

> +  printf ("#include \"alias.h\"\n"); \

> +  printf ("#include \"varasm.h\"\n"); \

> +  printf ("#include \"stor-layout.h\"\n"); \

> +  printf ("#include \"calls.h\"\n"); \

> +  printf ("#include \"memmodel.h\"\n"); \

> +  printf ("#include \"tm_p.h\"\n"); \

> +  printf ("#include \"flags.h\"\n"); \

> +  printf ("#include \"insn-config.h\"\n"); \

> +  printf ("#include \"expmed.h\"\n"); \

> +  printf ("#include \"dojump.h\"\n"); \

> +  printf ("#include \"explow.h\"\n"); \

> +  printf ("#include \"emit-rtl.h\"\n"); \

> +  printf ("#include \"stmt.h\"\n"); \

> +  printf ("#include \"expr.h\"\n"); \

> +  printf ("#include \"insn-codes.h\"\n"); \

> +  printf ("#include \"optabs.h\"\n"); \

> +  printf ("#include \"dfp.h\"\n"); \

> +  printf ("#include \"output.h\"\n"); \

> +  printf ("#include \"recog.h\"\n"); \

> +  printf ("#include \"df.h\"\n"); \

> +  printf ("#include \"resource.h\"\n"); \

> +  printf ("#include \"reload.h\"\n"); \

> +  printf ("#include \"diagnostic-core.h\"\n"); \

> +  printf ("#include \"regs.h\"\n"); \

> +  printf ("#include \"tm-constrs.h\"\n"); \

> +  printf ("#include \"ggc.h\"\n"); \

> +  printf ("#include \"target.h\"\n\n"); \


Can you use do {} while(0) style for defining this code block macro?
The trailing '\' is also strange here.
> +

>  int

>  main (int argc, const char **argv)

>  {

> @@ -862,49 +901,19 @@ main (int argc, const char **argv)

>    /* Assign sequential codes to all entries in the machine description

>       in parallel with the tables in insn-output.c.  */

>

> -  printf ("/* Generated automatically by the program `genemit'\n\

> -from the machine description file `md'.  */\n\n");

> -

> -  printf ("#define IN_TARGET_CODE 1\n");

> -  printf ("#include \"config.h\"\n");

> -  printf ("#include \"system.h\"\n");

> -  printf ("#include \"coretypes.h\"\n");

> -  printf ("#include \"backend.h\"\n");

> -  printf ("#include \"predict.h\"\n");

> -  printf ("#include \"tree.h\"\n");

> -  printf ("#include \"rtl.h\"\n");

> -  printf ("#include \"alias.h\"\n");

> -  printf ("#include \"varasm.h\"\n");

> -  printf ("#include \"stor-layout.h\"\n");

> -  printf ("#include \"calls.h\"\n");

> -  printf ("#include \"memmodel.h\"\n");

> -  printf ("#include \"tm_p.h\"\n");

> -  printf ("#include \"flags.h\"\n");

> -  printf ("#include \"insn-config.h\"\n");

> -  printf ("#include \"expmed.h\"\n");

> -  printf ("#include \"dojump.h\"\n");

> -  printf ("#include \"explow.h\"\n");

> -  printf ("#include \"emit-rtl.h\"\n");

> -  printf ("#include \"stmt.h\"\n");

> -  printf ("#include \"expr.h\"\n");

> -  printf ("#include \"insn-codes.h\"\n");

> -  printf ("#include \"optabs.h\"\n");

> -  printf ("#include \"dfp.h\"\n");

> -  printf ("#include \"output.h\"\n");

> -  printf ("#include \"recog.h\"\n");

> -  printf ("#include \"df.h\"\n");

> -  printf ("#include \"resource.h\"\n");

> -  printf ("#include \"reload.h\"\n");

> -  printf ("#include \"diagnostic-core.h\"\n");

> -  printf ("#include \"regs.h\"\n");

> -  printf ("#include \"tm-constrs.h\"\n");

> -  printf ("#include \"ggc.h\"\n");

> -  printf ("#include \"target.h\"\n\n");

> +  long long read_count = 0;

>

>    /* Read the machine description.  */

>

>    md_rtx_info info;

>    while (read_md_rtx (&info))

> +    {

> +    if (!(read_count++ % 10000))

> +      {

> +        printf ("/* i am split line %d :) */\n\n", read_count);

I would prefer a better comment explaining this line is to split file
into separate compilation units for parallel compilation.
> +        printf_include()

Together with above comment about macro, it's better to have a semicolon here?

Thanks,
bin
> +      }

> +

>      switch (GET_CODE (info.def))

>        {

>        case DEFINE_INSN:

> @@ -929,6 +938,7 @@ from the machine description file `md'.  */\n\n");

>        default:

>         break;

>        }

> +    }

>

>    /* Write out the routines to add CLOBBERs to a pattern and say whether they

>       clobber a hard reg.  */

> --

> 2.24.3 (Apple Git-128)

>
Jojo R July 24, 2020, 4:47 a.m. | #2
在 2020年7月21日 +0800 PM2:55,Bin.Cheng <amker.cheng@gmail.com>,写道:
> On Tue, Jul 21, 2020 at 11:14 AM Jojo <jiejie_rong@c-sky.com> wrote:

> >

> > gcc/ChangeLog:

> >

> > * genemit.c (main): Print 'split line'.

> > * Makefile.in (insn-emit.c): Define split count and file

> >

>

> Thanks for working one this, following comments are based on the

> assumption that the approach is feasible after your investigation.

>

> It's great to accelerate compilation time, do you have any number

> showing how much this can achieve, on a typical machine with

> reasonable parallelism?

>


Here are time collections from machine:

20 Intel(R) Xeon(R) Gold 6148 CPU @ 2.40GHz,

Size of insn-emit.c (du -sh insn-emit.c) : 121M

Not split (same like j1) :  195 second

Split 20, -j1 : 213 second

Split 20, -j4: 76 second

Split 20, -j8: 44 second

Split 20, -j12: 44 second

Split 20, -j16: 44 second

Split 20, -j20: 44 second

Also, litter RAM will be consumed by litter code :)
> > ---

> > gcc/Makefile.in | 10 ++++++

> > gcc/genemit.c | 86 +++++++++++++++++++++++++++----------------------

> > 2 files changed, 58 insertions(+), 38 deletions(-)

> >

> > diff --git a/gcc/Makefile.in b/gcc/Makefile.in

> > index 2ba76656dbf..f805050a119 100644

> > --- a/gcc/Makefile.in

> > +++ b/gcc/Makefile.in

> > @@ -1253,6 +1253,13 @@ ANALYZER_OBJS = \

> > # We put the *-match.o and insn-*.o files first so that a parallel make

> > # will build them sooner, because they are large and otherwise tend to be

> > # the last objects to finish building.

> > +

> > +insn-generated-split-num = 15

> Hardcode number 15 looks strange here, how shall we know it's enough?

> Or one step further, can we use some kind of general match "*" for

> writing make rules here?


I have researched the detail of Makefile rules, As far as I know, ‘Make’ analyze the dependent objects before
some object running it’s shell command, so we need to static define the ‘insn-emit.c’ counts for creating ‘insn-emit.o’.

We can define split counts from processor numbers from machine, it should be nice ?
It’s fixed in v3 patch.
> > +

> > +insn-emit-split-c = $(foreach o, $(shell for i in {1..$(insn-generated-split-num)}; do echo $$i; done), insn-emit$(o).c)

> > +insn-emit-split-obj = $(patsubst %.c,%.o, $(insn-emit-split-c))

> > +$(insn-emit-split-c): insn-emit.c

> > +

> > OBJS = \

> > gimple-match.o \

> > generic-match.o \

> > @@ -1260,6 +1267,7 @@ OBJS = \

> > insn-automata.o \

> > insn-dfatab.o \

> > insn-emit.o \

> > + $(insn-emit-split-obj) \

> > insn-extract.o \

> > insn-latencytab.o \

> > insn-modes.o \

> > @@ -2367,6 +2375,8 @@ $(simple_generated_c:insn-%.c=s-%): s-%: build/gen%$(build_exeext)

> > $(RUN_GEN) build/gen$*$(build_exeext) $(md_file) \

> > $(filter insn-conditions.md,$^) > tmp-$*.c

> > $(SHELL) $(srcdir)/../move-if-change tmp-$*.c insn-$*.c

> > + -csplit insn-$*.c /i\ am\ split\ line/ -k -s {$(insn-generated-split-num)} -f insn-$* -b "%d.c"

> > + -( [ ! -s insn-$*0.c ] && for i in {1..$(insn-generated-split-num)}; do touch insn-$*$$i.c; done && echo "" > insn-$*.c)

> Not sure if this is the first time that csplit/coreutils is used,

> shall we mention it here

> https://gcc.gnu.org/install/prerequisites.html, even check it in

> configure?


I grep coreutils from gcc source code and much more modules have checked the coreutils
like libcc1, libssp and so on.
> > $(STAMP) s-$*

> >

> > # gencheck doesn't read the machine description, and the file produced

> > diff --git a/gcc/genemit.c b/gcc/genemit.c

> > index 84d07d388ee..fd60cdeeb96 100644

> > --- a/gcc/genemit.c

> > +++ b/gcc/genemit.c

> > @@ -847,6 +847,45 @@ handle_overloaded_gen (overloaded_name *oname)

> > }

> > }

> >

> > +#define printf_include() \

> > + printf ("/* Generated automatically by the program `genemit'\n\

> > +from the machine description file `md'. */\n\n"); \

> > + printf ("#define IN_TARGET_CODE 1\n"); \

> > + printf ("#include \"config.h\"\n"); \

> > + printf ("#include \"system.h\"\n"); \

> > + printf ("#include \"coretypes.h\"\n"); \

> > + printf ("#include \"backend.h\"\n"); \

> > + printf ("#include \"predict.h\"\n"); \

> > + printf ("#include \"tree.h\"\n"); \

> > + printf ("#include \"rtl.h\"\n"); \

> > + printf ("#include \"alias.h\"\n"); \

> > + printf ("#include \"varasm.h\"\n"); \

> > + printf ("#include \"stor-layout.h\"\n"); \

> > + printf ("#include \"calls.h\"\n"); \

> > + printf ("#include \"memmodel.h\"\n"); \

> > + printf ("#include \"tm_p.h\"\n"); \

> > + printf ("#include \"flags.h\"\n"); \

> > + printf ("#include \"insn-config.h\"\n"); \

> > + printf ("#include \"expmed.h\"\n"); \

> > + printf ("#include \"dojump.h\"\n"); \

> > + printf ("#include \"explow.h\"\n"); \

> > + printf ("#include \"emit-rtl.h\"\n"); \

> > + printf ("#include \"stmt.h\"\n"); \

> > + printf ("#include \"expr.h\"\n"); \

> > + printf ("#include \"insn-codes.h\"\n"); \

> > + printf ("#include \"optabs.h\"\n"); \

> > + printf ("#include \"dfp.h\"\n"); \

> > + printf ("#include \"output.h\"\n"); \

> > + printf ("#include \"recog.h\"\n"); \

> > + printf ("#include \"df.h\"\n"); \

> > + printf ("#include \"resource.h\"\n"); \

> > + printf ("#include \"reload.h\"\n"); \

> > + printf ("#include \"diagnostic-core.h\"\n"); \

> > + printf ("#include \"regs.h\"\n"); \

> > + printf ("#include \"tm-constrs.h\"\n"); \

> > + printf ("#include \"ggc.h\"\n"); \

> > + printf ("#include \"target.h\"\n\n"); \

>

> Can you use do {} while(0) style for defining this code block macro?

> The trailing '\' is also strange here.


It’s fixed in v3 patch.
> > +

> > int

> > main (int argc, const char **argv)

> > {

> > @@ -862,49 +901,19 @@ main (int argc, const char **argv)

> > /* Assign sequential codes to all entries in the machine description

> > in parallel with the tables in insn-output.c. */

> >

> > - printf ("/* Generated automatically by the program `genemit'\n\

> > -from the machine description file `md'. */\n\n");

> > -

> > - printf ("#define IN_TARGET_CODE 1\n");

> > - printf ("#include \"config.h\"\n");

> > - printf ("#include \"system.h\"\n");

> > - printf ("#include \"coretypes.h\"\n");

> > - printf ("#include \"backend.h\"\n");

> > - printf ("#include \"predict.h\"\n");

> > - printf ("#include \"tree.h\"\n");

> > - printf ("#include \"rtl.h\"\n");

> > - printf ("#include \"alias.h\"\n");

> > - printf ("#include \"varasm.h\"\n");

> > - printf ("#include \"stor-layout.h\"\n");

> > - printf ("#include \"calls.h\"\n");

> > - printf ("#include \"memmodel.h\"\n");

> > - printf ("#include \"tm_p.h\"\n");

> > - printf ("#include \"flags.h\"\n");

> > - printf ("#include \"insn-config.h\"\n");

> > - printf ("#include \"expmed.h\"\n");

> > - printf ("#include \"dojump.h\"\n");

> > - printf ("#include \"explow.h\"\n");

> > - printf ("#include \"emit-rtl.h\"\n");

> > - printf ("#include \"stmt.h\"\n");

> > - printf ("#include \"expr.h\"\n");

> > - printf ("#include \"insn-codes.h\"\n");

> > - printf ("#include \"optabs.h\"\n");

> > - printf ("#include \"dfp.h\"\n");

> > - printf ("#include \"output.h\"\n");

> > - printf ("#include \"recog.h\"\n");

> > - printf ("#include \"df.h\"\n");

> > - printf ("#include \"resource.h\"\n");

> > - printf ("#include \"reload.h\"\n");

> > - printf ("#include \"diagnostic-core.h\"\n");

> > - printf ("#include \"regs.h\"\n");

> > - printf ("#include \"tm-constrs.h\"\n");

> > - printf ("#include \"ggc.h\"\n");

> > - printf ("#include \"target.h\"\n\n");

> > + long long read_count = 0;

> >

> > /* Read the machine description. */

> >

> > md_rtx_info info;

> > while (read_md_rtx (&info))

> > + {

> > + if (!(read_count++ % 10000))

> > + {

> > + printf ("/* i am split line %d :) */\n\n", read_count);

> I would prefer a better comment explaining this line is to split file

> into separate compilation units for parallel compilation.


It’s fixed in v3 patch.
> > + printf_include()

> Together with above comment about macro, it's better to have a semicolon here?


It’s fixed in v3 patch.
>

> Thanks,

> bin

> > + }

> > +

> > switch (GET_CODE (info.def))

> > {

> > case DEFINE_INSN:

> > @@ -929,6 +938,7 @@ from the machine description file `md'. */\n\n");

> > default:

> > break;

> > }

> > + }

> >

> > /* Write out the routines to add CLOBBERs to a pattern and say whether they

> > clobber a hard reg. */

> > --

> > 2.24.3 (Apple Git-128)

Patch

diff --git a/gcc/Makefile.in b/gcc/Makefile.in
index 2ba76656dbf..f805050a119 100644
--- a/gcc/Makefile.in
+++ b/gcc/Makefile.in
@@ -1253,6 +1253,13 @@  ANALYZER_OBJS = \
 # We put the *-match.o and insn-*.o files first so that a parallel make
 # will build them sooner, because they are large and otherwise tend to be
 # the last objects to finish building.
+
+insn-generated-split-num = 15
+
+insn-emit-split-c = $(foreach o, $(shell for i in {1..$(insn-generated-split-num)}; do echo $$i; done), insn-emit$(o).c)
+insn-emit-split-obj = $(patsubst %.c,%.o, $(insn-emit-split-c))
+$(insn-emit-split-c): insn-emit.c
+
 OBJS = \
 	gimple-match.o \
 	generic-match.o \
@@ -1260,6 +1267,7 @@  OBJS = \
 	insn-automata.o \
 	insn-dfatab.o \
 	insn-emit.o \
+	$(insn-emit-split-obj) \
 	insn-extract.o \
 	insn-latencytab.o \
 	insn-modes.o \
@@ -2367,6 +2375,8 @@  $(simple_generated_c:insn-%.c=s-%): s-%: build/gen%$(build_exeext)
 	$(RUN_GEN) build/gen$*$(build_exeext) $(md_file) \
 	  $(filter insn-conditions.md,$^) > tmp-$*.c
 	$(SHELL) $(srcdir)/../move-if-change tmp-$*.c insn-$*.c
+	-csplit insn-$*.c /i\ am\ split\ line/ -k -s {$(insn-generated-split-num)} -f insn-$* -b "%d.c"
+	-( [ ! -s insn-$*0.c ] && for i in {1..$(insn-generated-split-num)}; do touch insn-$*$$i.c; done && echo "" > insn-$*.c)
 	$(STAMP) s-$*
 
 # gencheck doesn't read the machine description, and the file produced
diff --git a/gcc/genemit.c b/gcc/genemit.c
index 84d07d388ee..fd60cdeeb96 100644
--- a/gcc/genemit.c
+++ b/gcc/genemit.c
@@ -847,6 +847,45 @@  handle_overloaded_gen (overloaded_name *oname)
     }
 }
 
+#define printf_include() \
+  printf ("/* Generated automatically by the program `genemit'\n\
+from the machine description file `md'.  */\n\n"); \
+  printf ("#define IN_TARGET_CODE 1\n"); \
+  printf ("#include \"config.h\"\n"); \
+  printf ("#include \"system.h\"\n"); \
+  printf ("#include \"coretypes.h\"\n"); \
+  printf ("#include \"backend.h\"\n"); \
+  printf ("#include \"predict.h\"\n"); \
+  printf ("#include \"tree.h\"\n"); \
+  printf ("#include \"rtl.h\"\n"); \
+  printf ("#include \"alias.h\"\n"); \
+  printf ("#include \"varasm.h\"\n"); \
+  printf ("#include \"stor-layout.h\"\n"); \
+  printf ("#include \"calls.h\"\n"); \
+  printf ("#include \"memmodel.h\"\n"); \
+  printf ("#include \"tm_p.h\"\n"); \
+  printf ("#include \"flags.h\"\n"); \
+  printf ("#include \"insn-config.h\"\n"); \
+  printf ("#include \"expmed.h\"\n"); \
+  printf ("#include \"dojump.h\"\n"); \
+  printf ("#include \"explow.h\"\n"); \
+  printf ("#include \"emit-rtl.h\"\n"); \
+  printf ("#include \"stmt.h\"\n"); \
+  printf ("#include \"expr.h\"\n"); \
+  printf ("#include \"insn-codes.h\"\n"); \
+  printf ("#include \"optabs.h\"\n"); \
+  printf ("#include \"dfp.h\"\n"); \
+  printf ("#include \"output.h\"\n"); \
+  printf ("#include \"recog.h\"\n"); \
+  printf ("#include \"df.h\"\n"); \
+  printf ("#include \"resource.h\"\n"); \
+  printf ("#include \"reload.h\"\n"); \
+  printf ("#include \"diagnostic-core.h\"\n"); \
+  printf ("#include \"regs.h\"\n"); \
+  printf ("#include \"tm-constrs.h\"\n"); \
+  printf ("#include \"ggc.h\"\n"); \
+  printf ("#include \"target.h\"\n\n"); \
+
 int
 main (int argc, const char **argv)
 {
@@ -862,49 +901,19 @@  main (int argc, const char **argv)
   /* Assign sequential codes to all entries in the machine description
      in parallel with the tables in insn-output.c.  */
 
-  printf ("/* Generated automatically by the program `genemit'\n\
-from the machine description file `md'.  */\n\n");
-
-  printf ("#define IN_TARGET_CODE 1\n");
-  printf ("#include \"config.h\"\n");
-  printf ("#include \"system.h\"\n");
-  printf ("#include \"coretypes.h\"\n");
-  printf ("#include \"backend.h\"\n");
-  printf ("#include \"predict.h\"\n");
-  printf ("#include \"tree.h\"\n");
-  printf ("#include \"rtl.h\"\n");
-  printf ("#include \"alias.h\"\n");
-  printf ("#include \"varasm.h\"\n");
-  printf ("#include \"stor-layout.h\"\n");
-  printf ("#include \"calls.h\"\n");
-  printf ("#include \"memmodel.h\"\n");
-  printf ("#include \"tm_p.h\"\n");
-  printf ("#include \"flags.h\"\n");
-  printf ("#include \"insn-config.h\"\n");
-  printf ("#include \"expmed.h\"\n");
-  printf ("#include \"dojump.h\"\n");
-  printf ("#include \"explow.h\"\n");
-  printf ("#include \"emit-rtl.h\"\n");
-  printf ("#include \"stmt.h\"\n");
-  printf ("#include \"expr.h\"\n");
-  printf ("#include \"insn-codes.h\"\n");
-  printf ("#include \"optabs.h\"\n");
-  printf ("#include \"dfp.h\"\n");
-  printf ("#include \"output.h\"\n");
-  printf ("#include \"recog.h\"\n");
-  printf ("#include \"df.h\"\n");
-  printf ("#include \"resource.h\"\n");
-  printf ("#include \"reload.h\"\n");
-  printf ("#include \"diagnostic-core.h\"\n");
-  printf ("#include \"regs.h\"\n");
-  printf ("#include \"tm-constrs.h\"\n");
-  printf ("#include \"ggc.h\"\n");
-  printf ("#include \"target.h\"\n\n");
+  long long read_count = 0;
 
   /* Read the machine description.  */
 
   md_rtx_info info;
   while (read_md_rtx (&info))
+    {
+    if (!(read_count++ % 10000))
+      {
+        printf ("/* i am split line %d :) */\n\n", read_count);
+        printf_include()
+      }
+
     switch (GET_CODE (info.def))
       {
       case DEFINE_INSN:
@@ -929,6 +938,7 @@  from the machine description file `md'.  */\n\n");
       default:
 	break;
       }
+    }
 
   /* Write out the routines to add CLOBBERs to a pattern and say whether they
      clobber a hard reg.  */