1

As this question says, I need a way to do

gcc -E -c main.cc -o main.o

On my compiler, from QNX but based on gcc 4.4.2, using -save-temps only gives me the assembly files (and no preprocessor files).

If I add -E like in the command above, the preprocessor output will be saved to main.o.

I need a solution that does both compilation AND outputs the preprocessor in one invocation of gcc with the above constraints.

Community
  • 1
  • 1
Bob
  • 4,576
  • 7
  • 39
  • 107
  • 2
    XY problem. What's the problem using two steps? – too honest for this site May 19 '17 at 23:04
  • @Olaf taking twice as long. The preprocessor is already invoked during compilation so why shouldn't this be possible? – Bob May 19 '17 at 23:05
  • That's not the same. On modern compilers there are not necessarily two distinct passes for preprocessing and compilation. And if there are two phases you most likely don't loose much performance. However, if you are after speeding up compilation, use a build tool; it will save much more time than what you seem to worry about. – too honest for this site May 19 '17 at 23:11
  • according to [this site](https://gcc.gnu.org/onlinedocs/gcc/Overall-Options.html) regarding `-E` option: `(...) and one of the options -c, -S, or -E to say where gcc is to stop` - "to stop" does not leave much hope in doing that in one step. – quetzalcoatl May 19 '17 at 23:12
  • @Adrian Speaking generally: It's quite possible that in normal compilation there is no *separate* preprocessing step. So while it of course is a solvable programming problem, nobody has implemented a 1-step solution to your problem, because internally it is 2 steps anyway. – hyde May 19 '17 at 23:13
  • Adrian - you said `taking twice as long` - did you really measure it? I mean, measure the time that gcc took to finish two phases? or do you just refer to the fact that you have to run it twice with two commandlines to run? – quetzalcoatl May 19 '17 at 23:17
  • Partly for efficiency and partly for debugging information for macros GCC doesn't do preprocessing in separate steps. As far as I know. – Zan Lynx May 19 '17 at 23:17
  • @ZanLynx It provides an option to save the preprocessor output in a file. Doesn't that suggest that it generates this intermediate form internally, even if it's not a separate step? That's consistent with the OP's goal -- he wants to get that file even while it continues to perform the other phases of compilation. – Barmar May 19 '17 at 23:21
  • 1
    @Barmar: It generates that as a special favor when it is asked. When it continues on normally, it never generates a text form. It is parsing the file into in-memory syntax trees from preprocessing and C/C++ parsing at the same time. – Zan Lynx May 19 '17 at 23:25
  • @Barmar: The GNU C-preprocessor `gpp` is not the same as the C compiler which includes the preprocessor. Note that `gcc` and `g++` are actually frontend for various backend tools, including gpp, the C compiler (cc1 IIRC), the C++ compiler, Ada, Fortran, the linker, etc. The standard does not mandate a seperate preprocessor, but explicitly allows compilation stages to be done in one pass **as long they have the same result**. – too honest for this site May 19 '17 at 23:43
  • @Olaf This question has little to do with the standard, since it also doesn't say anything about options to view the intermediate stages. – Barmar May 19 '17 at 23:47
  • @Barmar: It very well has! OP clearly assumes there have to be seperate stages, which the standard does not mandate. And last time I checked, the C-tag was about standard C. – too honest for this site May 19 '17 at 23:51
  • @Olaf His question is about implementation-specific options like `-E` and `--save-temps`. These options work despite the standard not requiring them. – Barmar May 19 '17 at 23:53
  • @Olaf I don't see the C tag, I see `gcc`. – Barmar May 19 '17 at 23:54
  • @barmer: Read the comments and between the lines. and `s/C/C++/` – too honest for this site May 20 '17 at 00:06
  • @Olaf The C and C++ standards do specify separate stages, they are called "phases of translation". See section [lex.phases] of C++14. – M.M May 20 '17 at 01:07
  • @M.M: Where did I say different? At least the C standard also states they need not be implemented sepereately as described, but can be integrated. Which every modern compiler does. – too honest for this site May 20 '17 at 01:13

1 Answers1

2

On my compiler, from QNX but based on gcc 4.4.2, using -save-temps only gives me the assembly files (and no preprocessor files).

I can't verify that for such an old version of GCC, or any QNX variant. Certainly all mainline GCC versions at least as old as 4.7 respect ... -c -save-temps foo.c by saving the preprocessed source in foo.i and the assembly in foo.s.

But if that's the case with your QNX GCC 4.4.2, there's a workaround.

From your comments it appears that your objection to invoking the compiler twice is that you do not want time to be wasted in preprocessing the source twice. But you can invoke the compiler twice, once to do the preprocessing only, and again to do the compiling only, so I presume that would be a satisfactory solution.

Your wished-for command line:

gcc -E -c main.cc -o main.o

shows a C++ source file being given to the C compiler. I assume that's a slip. The recipes for the outcome you're after are symmetrically different for C and for C++.

For C you want:

gcc -E main.c > main.i && gcc -c -o main.o main.i

For C++ you want:

g++ -E main.cc > main.ii && g++ -c -o main.o main.ii

This writes the preprocessed C[C++] output that you want to save to main.i[.ii] and then passes that preprocessed output to the compiler again for C[C++] compilation. gcc[g++] recognizes the file extension .i[.ii] as denoting C[C++] source code that should not be preprocessed. See 3.2 Options Controlling the Kind of Output; so it will not attempt to preprocess the source again.

This solution also has the merit of not generating the assembly files, which you don't want.

Mike Kinghan
  • 55,740
  • 12
  • 153
  • 182