[CMake] Hi and some newbie questions

Goswin von Brederlow brederlo at informatik.uni-tuebingen.de
Thu Sep 13 20:34:26 EDT 2007


Jack Kelly <endgame.dos at gmail.com> writes:

> Goswin von Brederlow wrote:
>> Hi everyone.
>>
>> A friend of mine keeps cursing about autotools and suggests cmake
>> instead. So I looked into it for a small project. Like all newbies I
>> run into a lot of unknowns and I'm somewhat stuck now.
>>
>> My CMakeLists.txt looks like below. My questions are in the comments.
>>
>> ----------------------------------------------------------------------
>> project (MOOSE)
>>
>> # Building subdirectories recursively not done to mimik original
>> # Makefile, not because I don't know how.
>> #add_subdirectory (lib)
>>
>> # How do I specify those more correctly? I need/want those flags and I
>> # probably want them for all or most subdirs.
>> ADD_DEFINITIONS(-fno-builtin -g -O2 -W -Wall -Werror -Wredundant-decls -Wno-format -Wstrict-prototypes -Wnested-externs -Wpointer-arith -Winline -D__XEN_INTERFACE_VERSION__=0x00030203 -m64 -mno-red-zone -fpic -fno-reorder-blocks -fno-asynchronous-unwind-tables -Wno-unused)
> # I'm assuming CFLAGS here, but the principle is the same for C++, just
> # use CXX instead of C. They look like GCC flags, so I wrapped them in a
> # test:
> IF(CMAKE_COMPILER_IS_GNUCC)
>   SET(CMAKE_C_FLAGS "-fno-builtin ...")
> ENDIF(CMAKE_COMPILER_IS_GNUCC)
> # Note also that if you are using CMAKE_BUILD_TYPE, then you can also
> # set variables such as CMAKE_C_FLAGS_DEBUG to set flags on a per
> # build-type basis.

What happens when CFLAGS is already set in the environment or when I
need to just extend it. I guess what I'm looking for is the Makefile
syntax

CFLAGS += something

> # One way would be to have a file i486.cmake:
> SET(ARCH i486)
> # and whatever else...

And cmake automatically includes the right file then?

> # A file called x86_64.cmake:
> SET(ARCH x86_64)
> # ...
>
> # Put this in the CMakeLists.txt:
> INCLUDE(${PLATFORM})
>
> # and invoke cmake like so:
> # cmake -DPLATFORM=x86_64 /path/to/build

That would be stupid. It should know itself what architecture to pick.

>> # Now here is my first big problem. CMake doesn't know how to handle
>> # any of these:
>> #add_executable (mini-os.gz mini-os.elf x86_64.o)
> # I don't think ADD_EXECUTABLE is what you're looking for here.
> # If you can set up the build steps with ADD_CUSTOM_COMMAND you should
> # be able to add those with an ADD_CUSTOM_TARGET

'add_executable (mini-os.elf ....)' at least should work. The target
is a normal elf binary. The x86_64.o object file just doesn't tell
cmake enough to know how to link it. I figure it wants to know whether
this is C or C++ or some other language needing special flags. Once I
add some *.c file there or if I could teach cmake about *.S then it
should work.

>> # How do I make a rule for assembler files? Doesn't seem to be preset.
>> ADD_CUSTOM_COMMAND (OUTPUT x86_64.o
>>                     COMMAND gcc -D__ASSEMBLY__ -Iinclude  -Iinclude/x86     -Iinclude/x86/x86_64 -c x86_64.S -o x86_64.o
>>                     COMMENT Assembler pass)
>>
>> # Or define my own linker script?
>> ADD_CUSTOM_COMMAND (OUTPUT mini-os.elf
>>                     COMMAND ld -N -T minios-x86_64.lds -m elf_x86_64 x86_64.o -L. -lminios -o mini-os.elf
>>                     DEPENDS x86_64.o minios
>>                     COMMENT Link kernel into shape)
>>
>> # And a rule to gzip the result?
>> ADD_CUSTOM_COMMAND (OUTPUT mini-os.gz
>>                     COMMAND gzip -f -9 -c mini-os.elf >mini-os.gz
>>                     DEPENDS mini-os.elf
>>                     COMMENT compress kernel)
> # These look reasonable, apart from the fact that you should be looking
> # for the executables with FIND_PROGRAM because not everyone will have
> # the right versions at the front of the system path. Just allows a user
> # override, that's all. Are they giving you a specific problem?

Just that they disapear when I don't have a ADD_CUSTOM_TARGET
depending on them. The rest is just taste. They look dirty.

For the mini-os.elf I thought I could set some LDFLAGS (for -T
minios-${ARCH}) and have it fill in the remaining parts automatically
as it would with ADD_EXECUTABLE in some way.


I think what I was really asking here was how to make a pattern rule
here. In Unix Makefile terms:

%.gz: %
	gzip -9 $<

%.o: %.S
	gcc -D__ASSEMBLY__ <incude paths> <ASFLAGS> -c $< -o $@


> # You may also want to add explicit paths
> # (like gcc -c ${MOOSE_SOURCE_DIR}/x86_64.S) and see if it's possible to
> # do away with that redirection in the gzip.

Yes to the first part. Why to the redirection? Is it worth splitting
that in 'gzip mini-os.elf' and 'mv mini-os.elf.gz mini-os.gz'.

>> # And last why can't I add a custom command to the all target as in
>> #ADD_CUSTOM_TARGET (all DEPENDS mini-os.gz)
>> # or
>> #ADD_CUSTOM_COMMAND (TARGET all PRE_LINK COMMAND make mini-os.gz)
>>
>> ADD_CUSTOM_TARGET (mini-os DEPENDS mini-os.gz)
> ADD_CUSTOM_TARGET(mini-os ALL DEPENDS mini-os.gz VERBATIM)
> # The ALL will force it to be rebuilt even if you just run `make'.
> # The VERBATIM is just a style thing, it's recommended: (man cmake)
>
> # Use  of  VERBATIM  is  recommended as it enables correct
> # behavior. When VERBATIM is not given the  behavior  is  platform
> # specific.  In the future VERBATIM may be enabled by default. The
> # only reason it is an option is to  preserve  compatibility  with
> # older CMake code.

Thanks. Must have overlooked the ALL flag while browsing the cmake
webpages.

> # -- Jack

Thanks for your excelent pointers. This gets me a fair bit further to
something I would call 'clean'.

MfG
        Goswin


More information about the CMake mailing list