# add\_custom\_command with generator config commands

**URL:** https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662
**Category:** Usage
**Created:** [December 14, 2021, 4:27pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662 "2021-12-14T16:27:10Z")
**Posts on this page:** 16
**Page:** 1

<div class="post-metadata">

### Author: ![scottaronbloom](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/s/b4bc9f/32.png) [@scottaronbloom](https://discourse.cmake.org/u/scottaronbloom)
#### Post date: [December 14, 2021, 4:27pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/1 "2021-12-14T16:27:10Z")

</div>

I am trying to copy a pdb file on windows as part of a add\_custom\_commad

Since it only is generated in RelWithDebInfo and Debug my command looks like the following

```auto
COMMAND $<$<OR:$<CONFIG:Debug>,$<CONFIG:RelWithDebInfo>>:${CMAKE_COMMAND} -E copy_if_different $<TARGET_FILE_DIR:bif>/$<TARGET_FILE_BASE_NAME:bif>.pdb $<TARGET_FILE_DIR:MyApp>

```

Unfortunately the batch file command created for VS 2019 generates a call like this

```auto
""$"<1:C:\Program Files\CMake\bin\cmake.exe" 

```

Any ideas on the right way to format this?

---

<div class="post-metadata">

### Author: ![ben.boeckel](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/b/ea5d25/32.png) [@ben.boeckel](https://discourse.cmake.org/u/ben.boeckel)
#### Post date: [December 14, 2021, 4:29pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/2 "2021-12-14T16:29:01Z")

</div>

I think you’re missing a trailing `>` at the end.

---

<div class="post-metadata">

### Author: ![scottaronbloom](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/s/b4bc9f/32.png) [@scottaronbloom](https://discourse.cmake.org/u/scottaronbloom)
#### Post date: [December 14, 2021, 4:35pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/3 "2021-12-14T16:35:03Z")

</div>

Looks like there was a cut and paste issue sorry.

```auto
    COMMAND $<$<OR:$<CONFIG:Debug>,$<CONFIG:RelWithDebInfo>>:${CMAKE_COMMAND} -E copy_if_different "$<TARGET_FILE_DIR:bif>/$<TARGET_FILE_BASE_NAME:bif>.pdb" "$<TARGET_FILE_DIR:App>/imageformats" >

```

---

<div class="post-metadata">

### Author: ![ben.boeckel](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/b/ea5d25/32.png) [@ben.boeckel](https://discourse.cmake.org/u/ben.boeckel)
#### Post date: [December 14, 2021, 4:43pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/4 "2021-12-14T16:43:49Z")

</div>

Note that variable splitting happens before genex parsing, so you have these arguments here:

- `$<$<OR:$<CONFIG:Debug>,$<CONFIG:RelWithDebInfo>>:${CMAKE_COMMAND}`
- `-E`
- `copy_if_different`
- `"$<TARGET_FILE_DIR:bif>/$<TARGET_FILE_BASE_NAME:bif>.pdb"`
- `"$<TARGET_FILE_DIR:App>/imageformats"`
- `>`

You can use `;` to separate it or do something like this:

```cmake
set(pdb_copy_command
  ${CMAKE_COMMAND} -E copy_if_different
    "$<TARGET_FILE_DIR:bif>/$<TARGET_FILE_BASE_NAME:bif>.pdb"
    "$<TARGET_FILE_DIR:App>/imageformats")
add_custom_command(…
    COMMAND $<$<OR:$<CONFIG:Debug>,$<CONFIG:RelWithDebInfo>>:${pdb_copy_command}>)

```

Additionally `$<CONFIG:Debug,RelWithDebInfo>` would be simpler.

---

<div class="post-metadata">

### Author: ![scottaronbloom](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/s/b4bc9f/32.png) [@scottaronbloom](https://discourse.cmake.org/u/scottaronbloom)
#### Post date: [December 14, 2021, 4:45pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/5 "2021-12-14T16:45:00Z")

</div>

Thanks Ill give it a try and let you know

---

<div class="post-metadata">

### Author: ![scottaronbloom](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/s/b4bc9f/32.png) [@scottaronbloom](https://discourse.cmake.org/u/scottaronbloom)
#### Post date: [December 14, 2021, 4:46pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/6 "2021-12-14T16:46:07Z")

</div>

And yes… the Debug,RelWithDebInfo is definitely easier, I couldnt find that on out there as a valid syntax. Very nice!

---

<div class="post-metadata">

### Author: ![scottaronbloom](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/s/b4bc9f/32.png) [@scottaronbloom](https://discourse.cmake.org/u/scottaronbloom)
#### Post date: [December 14, 2021, 4:51pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/7 "2021-12-14T16:51:58Z")

</div>

Unfortunately that didnt help. this is the current as variable and custom command

```auto
SET( _PDB_COPY_CMD 
	${CMAKE_COMMAND} -E
	copy_if_different 
	"$<TARGET_FILE_DIR:bif>/$<TARGET_FILE_BASE_NAME:bif>.pdb"
	"$<TARGET_FILE_DIR:App>/imageformats"
	)
add_custom_command( TARGET App POST_BUILD 
    COMMAND $<$<CONFIG:Debug,RelWithDebInfo>:${_PDB_COPY_CMD} >
    DEPENDS bif
    COMMENT "ADDING BIF Image Format Shared Library PDB file Library"
    )

```

and this is the generated output from the vcxproj

```auto
App/MediaManager.vcxproj:""$"&lt;1:C:\Program Files\CMake\bin\cmake.exe" -E copy_if_different "D:/Visual Studio/sb/github/scottaronbloom/MediaManager/build/SABUtils/bif/Debug/bif.pdb" "D:/Visual Studio/sb/github/scottaronbloom/MediaManager/build/App/Debug/imageformats" &gt;
App/MediaManager.vcxproj:""$"&lt;0:C:\Program Files\CMake\bin\cmake.exe" -E copy_if_different "D:/Visual Studio/sb/github/scottaronbloom/MediaManager/build/SABUtils/bif/Release/bif.pdb" "D:/Visual Studio/sb/github/scottaronbloom/MediaManager/build/App/Release/imageformats" &gt;
App/MediaManager.vcxproj:""$"&lt;0:C:\Program Files\CMake\bin\cmake.exe" -E copy_if_different "D:/Visual Studio/sb/github/scottaronbloom/MediaManager/build/SABUtils/bif/MinSizeRel/bif.pdb" "D:/Visual Studio/sb/github/scottaronbloom/MediaManager/build/App/MinSizeRel/imageformats" &gt;
App/MediaManager.vcxproj:""$"&lt;1:C:\Program Files\CMake\bin\cmake.exe" -E copy_if_different "D:/Visual Studio/sb/github/scottaronbloom/MediaManager/build/SABUtils/bif/RelWithDebInfo/bif.pdb" "D:/Visual Studio/sb/github/scottaronbloom/MediaManager/build/App/RelWithDebInfo/imageformats" &gt;

```

---

<div class="post-metadata">

### Author: ![ben.boeckel](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/b/ea5d25/32.png) [@ben.boeckel](https://discourse.cmake.org/u/ben.boeckel)
#### Post date: [December 14, 2021, 4:54pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/8 "2021-12-14T16:54:03Z")

</div>

> [@scottaronbloom](#):
>
> `COMMAND $<$<CONFIG:Debug,RelWithDebInfo>:${_PDB_COPY_CMD} >`

Remove the space before the `>`. The genex needs to be a single argument for it to be parsed properly. The whole thing may need quoted, but my gut says it shouldn’t need to be.

---

<div class="post-metadata">

### Author: ![scottaronbloom](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/s/b4bc9f/32.png) [@scottaronbloom](https://discourse.cmake.org/u/scottaronbloom)
#### Post date: [December 14, 2021, 4:59pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/9 "2021-12-14T16:59:54Z")

</div>

Getting closer 🙂 removing the space and wrapping the command in quotes is a bit better

```auto
SET( _PDB_COPY_CMD 
	${CMAKE_COMMAND} -E
	copy_if_different 
	"$<TARGET_FILE_DIR:bif>/$<TARGET_FILE_BASE_NAME:bif>.pdb"
	"$<TARGET_FILE_DIR:App>/imageformats"
	)
add_custom_command( TARGET App POST_BUILD 
    COMMAND "$<$<CONFIG:Debug,RelWithDebInfo>:${_PDB_COPY_CMD}>"
    DEPENDS bif
    COMMENT "ADDING BIF Image Format Shared Library PDB file Library"
    )

```

But the final step (this one was easier to debug)… You need to add the COMMAND\_EXPAND\_LISTS to the add\_custom\_command

```auto
add_custom_command( TARGET MediaManager POST_BUILD 
    COMMAND "$<$<CONFIG:Debug,RelWithDebInfo>:${_PDB_COPY_CMD}>"
    DEPENDS bif
    COMMENT "ADDING BIF Image Format Shared Library PDB file Library"
	COMMAND_EXPAND_LISTS
    )

```

Thanks for all the help. How would a normal person debug this?

---

<div class="post-metadata">

### Author: ![ben.boeckel](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/b/ea5d25/32.png) [@ben.boeckel](https://discourse.cmake.org/u/ben.boeckel)
#### Post date: [December 14, 2021, 5:05pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/10 "2021-12-14T17:05:14Z")

</div>

> [@scottaronbloom](#):
>
> How would a normal person debug this?

Other than knowing CMake variable expansion, parsing, and argument passing behaviors through hard-earned experience? Not sure (as that’s how I knew what to look for). Using `cmake --trace-expand` to see what is happening helps to see what arguments are actually being passed around. Knowing that literal spaces in genexes in source code basically invalidate them is the other piece of knowledge there.

---

<div class="post-metadata">

### Author: ![scottaronbloom](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/s/b4bc9f/32.png) [@scottaronbloom](https://discourse.cmake.org/u/scottaronbloom)
#### Post date: [December 14, 2021, 5:07pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/11 "2021-12-14T17:07:06Z")

</div>

Thanks. Ill try the --trace-expand next time.

I would be really great, if the add\_custom\_command had a CONFIGURATIONS option like install does

---

<div class="post-metadata">

### Author: ![ben.boeckel](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/b/ea5d25/32.png) [@ben.boeckel](https://discourse.cmake.org/u/ben.boeckel)
#### Post date: [December 14, 2021, 5:10pm UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/12 "2021-12-14T17:10:52Z")

</div>

Now that we have configuration-dependent outputs for `add_custom_command` in all generators, this seems like a reasonable request to me at least.

---

<div class="post-metadata">

### Author: ![scottaronbloom](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/s/b4bc9f/32.png) [@scottaronbloom](https://discourse.cmake.org/u/scottaronbloom)
#### Post date: [December 15, 2021, 12:17am UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/13 "2021-12-15T00:17:11Z")

</div>

Do you know of any way to have a post build command that is a CMake functon?

for exmaple

FUNCTION( foo in1 in2 )  
# do something in cmake that modifies something using config generators  
endfnction

add\_custom\_command( TARGET xxx POST\_BUILD  
COMMAND foo $\<$CONFIG:Debug:xxxx.pdb\>\> $\<TARGET\_FILE\_DIR:MediaManager\>  
)

---

<div class="post-metadata">

### Author: ![ben.boeckel](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/b/ea5d25/32.png) [@ben.boeckel](https://discourse.cmake.org/u/ben.boeckel)
#### Post date: [December 15, 2021, 12:23am UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/14 "2021-12-15T00:23:42Z")

</div>

You can put the code you want to run into a script and use `${CMAKE_COMMAND} -P path/to/script.cmake` (with `-D` flags as needed to pass information).

---

<div class="post-metadata">

### Author: ![scottaronbloom](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/s/b4bc9f/32.png) [@scottaronbloom](https://discourse.cmake.org/u/scottaronbloom)
#### Post date: [December 15, 2021, 12:24am UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/15 "2021-12-15T00:24:49Z")

</div>

That is exactly what Im doing ☹ I was hoping for a better way

---

<div class="post-metadata">

### Author: ![scottaronbloom](https://discourse.cmake.org/letter_avatar_proxy/v4/letter/s/b4bc9f/32.png) [@scottaronbloom](https://discourse.cmake.org/u/scottaronbloom)
#### Post date: [December 15, 2021, 2:26am UTC](https://discourse.cmake.org/t/add-custom-command-with-generator-config-commands/4662/16 "2021-12-15T02:26:19Z")

</div>

In case you are interested. You can take a look at how I wound up using it.

> **[SABUtils/Modules at master · scottaronbloom/SABUtils](https://github.com/scottaronbloom/SABUtils/tree/master/Modules)**
>
> master/Modules

You can take a look at two Files, InstallFile.cmake and FindInstallFile.cmake for the end result of whats going on.

Basically the InstallFile function is a wrapper around configure\_file with COPYONLY that also reports on the file being updated or not.

InstallFile.cmake allows for it to be used directly with a -P
