[CMake] Generating C++ code from Idl language with variable number of files as output

Clifford Yapp cliffyapp at gmail.com
Wed Jul 20 09:00:18 EDT 2011


On Mon, Jul 18, 2011 at 8:42 AM, Valentin-Daniel Boca
<dboca at eservicios.indracompany.com> wrote:

> gen_code xxx.idl -> xxxIdl.h, xxxIdl.cc, xWrappers.h and xxxWData.h
>
> So for every "keyword struct" there is one more file generated. The first
> three files are always the same.
>
> Given this, I can't know the list of output files to put it in the list of
> add_custom_command output section.
>
> I need somehow to be able to tell to add_custom_command that the content of
> OUTPUT files should be somehow taken from the result of running the COMMAND
> (which I know it's impossible).

What about this: a two stage process, where the first stage runs a
stand-alone CMake script that runs all of the idl commands ahead of
time, outputting the contents into a custom directory.  For each idl
file, do the following steps in the stand-alone script:

1) run the idl gen_code on the file
2) use CMakes glob routines to capture what files were generated in
the temporary directory as a result of that command
3) write the results of that glob to an xxx_idl.out file
4) clear out the generated idl files in the temporary directory.

Once you have all the idl.out files, in the main CMake logic you can
write a macro for doing the add_custom_command routine that
incorporates reading in the xxx_idl.out file contents into a
variable/list.  You might need to generate per-idl-file .cmake files
to run, based on a template and using configure_file

Look into commands like:

   execute_process(COMMAND ${CMAKE_COMMAND} ...)
   FILE(GLOB IDL_OUTFILES tmpdir/*)
   FILE(WRITE ${xxx}_idl.out ${IDL_OUTFILES}

Once you have your xxx_idl.out files, you can incorporate them into a
wrapper macro in the main file and use that macro to add your idl
files:

MACRO(add_idl xxx)
   FILE(READ ${xxx}_idl.out IDL_OUTFILES)
   add_custom_command(
        OUTPUT ${IDL_OUTFILES}
        COMMAND gen_code xxx.idl
        DEPENDS ${xxx}_idl.out ${xxx}.idl
   )
   add_custom_target(${xxx}_idl ALL DEPENDS ${IDL_OUTFILES})
ENDMACRO(add_idl)

This achieves the effect of per-file custom OUTPUT files in principle.
  This is a more or less "off the cuff" response, so it may not be
quite the approach you will need, but it's how I would start
experimenting in such a case.  I should note that the drawback is any
change to the idl files will require re-running CMake, not just
running make - I'm not sure if there is a way to enforce that that
actually happens when an idl file changes but I'm also not sure if
there's any way around it, since you're essentially faking dynamic
OUTPUT lists in custom commands and that actually does require
re-generation of the Makefiles (or whatever) whenever the idl contents
change (as far as I know).

CMake devs, is there any way to tell CMake that it needs to re-run
itself when a user-specified file changes?  (e.g. trigger the same
behavior for idl files that gets triggered when a CMakeLists.txt file
is updated?)

Hope that helps, and good luck.

Cheers,
CY


More information about the CMake mailing list