I'm building ubuntu-8.04 with gcc 3.4 and I need to generate the .i files, which are the output of the gcc preprocessor. I have tried adding the --save-temps flag but this only generates the .i files for the top level directory, i.e. source, and does not seem to get passed recursively to the child directories. I also tried the -E flag, which is supposed to output preprocessed files and stop compilation, but this did not generate the files either.
I'm specifically looking to generate the .i files for the source in net/core.
Any help is appreciated. Thanks!!
There is no support for bulk preprocessing.
For single file use "make net/core/foo.i"
For bulk, workaround is "make C=2 CHECK="cc -E"".
I know that is an old post, but maybe can be useful; for me this works:
gcc -E filename.c -o outputfile.i
Related
i'm working on a project requiring cmake. i'd like to add some custom rules to my makefile, but can't quite get my head around how to do it.
both c source files and header files are in the same directory. also in this same directory are a number of .def files, which are the sources for some of the header files #included in the source during compilation.
if i were to do this in a makefile, i'd use a simple rule like
.SUFFIXES: .def
.def.h:
$(PREPROC) $< > $#
how can i do this with cmake ??
i've tried various permutations of the following, both with and without cmake working directory specifications :
add_custom_command(
OUTPUT vvr_const.h
PRE_BUILD
COMMAND preproc vvr_const.def > vvr_const.h
DEPENDS vvr_const.def
)
add_custom_target(vvr_const.h DEPENDS vvr_const.def)
but the header file isn't generated by the time the c source file is compiled, so the compile fails. i've also tried a variation where i replace the last line above with
set_property(SOURCE main.c APPEND PROPERTY OBJECT_DEPENDS vvr_const.h)
in this case, the header file is correctly generated in advance, but make can't find it, and complains that there's no rule to make the target .h.
ideally this would be a general rule, like the make rule above, but i'm not opposed to making a separate rule for each of the .def files if that's what it takes.
cheers.
There are 2 problems with the add_custom_command approach you present:
You did not specify a working directory; by default the command is run in the build directory, not in the source directory.
You rely on shell functionality here (the redirect to a file). Even though this probably still works. You should go with an approach that does not rely on the shell.
To solve issues 1 and 2 I recommend creating a seperate cmake script file receiving the absolute paths to input and output files and using those in the custom command. This allows you to use execute_process to specify the file to write without relying on the platform.
preprocess_def.cmake
# preprocess def file
# parameters INPUT_FILE and OUTPUT_FILE denote the file to use as source
# and the file to write the results to respectively
# use preproc tool to get data to write to the output file
execute_process(COMMAND preproc "${INPUT_FILE}"
RESULT_VARIABLE _EXIT_CODE
OUTPUT_FILE "${OUTPUT_FILE}")
if (_EXIT_CODE)
message(FATAL_ERROR "An error occured when preprocessing the file ${INPUT_FILE}")
endif()
CMakeLists.txt
set(_INPUT_FILE "${CMAKE_CURRENT_SOURCE_DIR}/vvr_const.def")
set(_OUTPUT_FILE "${CMAKE_CURRENT_SOURCE_DIR}/vvr_const.h")
# not necessary to use build event here, if we mark the output file as generated
add_custom_command(OUTPUT "${_OUTPUT_FILE}"
COMMAND "${CMAKE_BUILD_TOOL}" -D "OUPUT_FILE=${_OUTPUT_FILE}" -D "INPUT_FILE=${_INPUT_FILE}" -P "${CMAKE_CURRENT_SOURCE_DIR}/preprocess_def.cmake"
DEPENDS "${_INPUT_FILE}")
add_executable(my_target vvr_const.h ...)
set_source_files_properties(vvr_const.h PROPERTIES GENERATED 1)
Documentation from cmake:
PRE_BUILD
On Visual Studio Generators, run before any other rules are executed within the target. On other generators, run just before PRE_LINK commands.
So possibly your command is just running too late.
According to Clang doc:
-I < directory >
Add the specified directory to the search path for include files.
I wounder if there a way to add multiple search path on the same directory with one -I command, something like this:
-I"Dir1/SubDir/SubDir/SubDir/{IncludePath1,IncludePath2,IncludePath3}"
My project folder tree (unfortunately) is in a formation that there are 2 main folders for include paths which each one includes many paths for the -I option. This cause the clang command to be very long and i will give an example:
clang (...)
-I"Dir1/SubDir/SubDir/.../SubDir/IncludePath1"
-I"Dir1/SubDir/SubDir/.../SubDir/IncludePath2"
-I"Dir1/SubDir/SubDir/.../SubDir/IncludePath3"
-I"Dir1/SubDir/SubDir/.../SubDir/(And so on...)"
-I"Dir2/SubDir/SubDir/.../SubDir/IncludePath1"
-I"Dir2/SubDir/SubDir/.../SubDir/IncludePath2"
-I"Dir2/SubDir/SubDir/.../SubDir/IncludePath3"
-I"Dir2/SubDir/SubDir/.../SubDir/(And so on...)"
So again i wonder if there a way to tell clang to search with one command multiple search path or maybe make it search within a specific dir
Use options -isysroot and -iwithsysroot:
clang -isysroot"Dir1/SubDir/SubDir/SubDir/" -iwithsysroot"/IncludePath1/" \
-iwithsysroot"/IncludePath2/" -iwithsysroot"/IncludePath3/"
Unfortunately, this solution only works for one main folder and it also makes those include folders system ones, i.e., Clang won't show any warnings for them.
Also, -iwithsysroot is pretty long, so you may not save much typing there :)
But I'm not aware of any better way to do this directly via Clang options.
Although you could always write a shell script to ease the job...
Note. While digging through Clang command line reference trying to find a better solution, I came across option -ivfsoverlay that seems like it maybe could solve your problem.
I wasn't able to make it work, though, but I still decided to leave it here, maybe it'll be useful for you.
I'm trying to convert an makefile-build to cmake (to avoid the current state of being forced to take care for the windows-build env based on make/msdev and the linux based on make/gcc).
In this project, I've found a directory full of sourcecode files that get, based on a naming convention, compiled to libraries. (e.g. c1223.c => c1223.dll (or .sl) )
The current makefile consists of some directives using wildcards, e.g.:
LIB_NO = $(basename $(subst s,,$#))
OBJ = $(OBJ_PATH)/s$(LIB_NO).o $(OBJ_PATH)/c$(LIB_NO).o\
$(OBJ_PATH)/b$(LIB_NO).o
$(OBJ_PATH)/%.o : %.c
-$(CC) $(CFLAGS) -I$(PWD) -c $< -o $#
-(chmod a+w $#;true)
I've searched for a while but can't find anything that seems to work. Is it even possible with cmake to let it generate a wildcard based build?
Any comments, hints and suggestions are very welcome :)
cheers
Markus
You can use fairly primitive globbing (there's no regular expression syntax that I can see).
file(GLOB TESTSRCS "test/src/*.cpp")
# Compile the test sources.
add_executable(Tests ${TESTSRCS})
target_link_libraries(Tests ${LIB} gtest gtest_main)
The actual makefiles do not seem to contain wildcard searches inside them. If you add new files you will need to re-run cmake.
What I don't know is how you would manage to wrap up the library creation in a single macro if you have many different library files to generate.
You might be able to do something like this if there's only one c file per library:
file(GLOB libfiles "path/to/libs/c*.c")
foreach(libfile ${libfiles})
GET_FILENAME_COMPONENT(libname ${libfile} NAME) # remove the '.c' part (untested, hopefully this will work)
add_library(${libname} ${libfile})
endforeach(libfile)
If anybody else has a better solution, I would also like to learn it.
CMake does not generate makefiles that have wildcard-based rules in them. It generates specific rules for the files that it knows about.
In your example, you are explicitly listing the .o files that comprise your library. In CMake, you would instead explicitly list the source files that contribute to your library, and then let CMake take care of the rest.
Do you need makefiles that have wildcard-based rules in them for some reason?
Couldn't you simply construct a list of the source files, and then, for each element in the list, do an "add_library" call with the source file and a library name constructed from the source file name?
Everybody
I have a small problem . I just doing it for experiment. I'm using ubuntu 10.04
my problem is that my c program name 2.c is at /home/Desktop (location) but my .o files are at different location /tmp/man(location of 3.o) /usr/jan(location of 4.o)
I complied the program form home account by command
gcc"/home/Desktop/2.c""/tmp/man/3.0"/usr/jan/4.0 "
but every time i compile the program it shows error like that
bash: gcc/home/Desktop/2.c/tmp/man/3.0: No such file or directory.
what I'm doing wrong ?
can any body what is the proper way to run the program
one request please don't tell to paste the all file in same folder than use gcc or changind ld_library path .
if You are giving me suggestion about makefile than please give the complete make file .
just tell me how i can compile and run the program ?
First, don't use " to separate the arguments, use spaces. Also, you wrote 3.0 and 4.0 (with zero, not oh). Then, do you want to compile the 2.c file and link it with the 3.o and 4.o files ? You just have to call
> gcc /home/Desktop/2.c /tmp/man/3.o /usr/jan/4.o -o /your/path/exefile
This will compile 2.c, link it with 3.o and 4.o and build the exefile executable in the specified path.
Try
$ gcc /home/Desktop/2.c /tmp/man/3.o /usr/jan/4.o
Why on earth do you have .o files in /tmp/man?
I am trying to read some code that has a lot of macros in it. And often the macros are chained. Is there any way to see a version of the file where all the macros have been expanded -- without doing a full run of the preprocessor (which would also do stuff like expand #imports)? This would really help me read the code.
EDIT: Often the macros are defined in other files.
Not sure if there's a way to do this in Xcode, but you can use the compiler, specifically the -E option, which stops processing right after preprocessing.
cc -E foo.c
will print all the preprocessed results on stdout. And
cc -E foo.c -o foo.preproc
will dump the preprocessed output into foo.preproc.
As best I can tell, the answer to my question is that there is no way to do it. The best I can do is do a full precompile, then search for the part of the file that starts after all the #include statements.