Fix searching for dll paths, instead of adding .lib path.#6410
Fix searching for dll paths, instead of adding .lib path.#6410larshg wants to merge 4 commits intoPointCloudLibrary:masterfrom
Conversation
There was a problem hiding this comment.
Pull request overview
This PR addresses Windows CMake import target metadata so that IMPORTED_LOCATION points to the actual runtime .dll (not the .lib import library), fixing $<TARGET_RUNTIME_DLLS:...> behavior (Issue #6345).
Changes:
- Adds
find_file()lookups for per-component DLL paths under${PCL_ROOT}/bin. - Updates imported PCL component targets to use found DLL paths for
IMPORTED_LOCATION[_<CONFIG>]while keeping.libpaths inIMPORTED_IMPLIB[_<CONFIG>]. - Introduces a special-case branch for the
iocomponent DLL naming.
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Wrap dll search for windows in "if WIN32".
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 1 out of 1 changed files in this pull request and generated 5 comments.
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
PCLConfig.cmake.in
Outdated
| if ("${component}" STREQUAL "io") | ||
| find_file(PCL_${COMPONENT}_DLL_PATH | ||
| NAMES | ||
| pcl_io_ply${PCL_RELEASE_SUFFIX}.dll | ||
| pcl_io_ply${PCL_RELWITHDEBINFO_SUFFIX}.dll | ||
| pcl_io_ply${PCL_MINSIZEREL_SUFFIX}.dll | ||
| HINTS "${PCL_ROOT}/bin" | ||
| NO_DEFAULT_PATH) | ||
|
|
||
| find_file(PCL_${COMPONENT}_DLL_PATH_DEBUG | ||
| NAMES ${pcl_component}${PCL_DEBUG_SUFFIX}.dll | ||
| HINTS "${PCL_ROOT}/bin" | ||
| NO_DEFAULT_PATH) | ||
|
|
||
| endif() | ||
|
|
There was a problem hiding this comment.
The special case for the "io" component appears to be incorrect. When the component is "io", pcl_component is "pcl_io", not "pcl_io_ply". The io_ply is a separate component that gets processed in its own iteration of the loop (as seen in lines 460-462 where io_ply is inserted as a separate component).
This special case should be removed entirely, as the general case at lines 639-649 already correctly uses ${pcl_component} which will be "pcl_io_ply" when processing the io_ply component and "pcl_io" when processing the io component.
Additionally, there's an inconsistency in the debug path search: line 661 searches for ${pcl_component}${PCL_DEBUG_SUFFIX}.dll (which would be pcl_io), but lines 652-658 search for pcl_io_ply DLLs for release builds.
| if ("${component}" STREQUAL "io") | |
| find_file(PCL_${COMPONENT}_DLL_PATH | |
| NAMES | |
| pcl_io_ply${PCL_RELEASE_SUFFIX}.dll | |
| pcl_io_ply${PCL_RELWITHDEBINFO_SUFFIX}.dll | |
| pcl_io_ply${PCL_MINSIZEREL_SUFFIX}.dll | |
| HINTS "${PCL_ROOT}/bin" | |
| NO_DEFAULT_PATH) | |
| find_file(PCL_${COMPONENT}_DLL_PATH_DEBUG | |
| NAMES ${pcl_component}${PCL_DEBUG_SUFFIX}.dll | |
| HINTS "${PCL_ROOT}/bin" | |
| NO_DEFAULT_PATH) | |
| endif() |
| find_file(PCL_${COMPONENT}_DLL_PATH | ||
| NAMES | ||
| ${pcl_component}${PCL_RELEASE_SUFFIX}.dll | ||
| ${pcl_component}${PCL_RELWITHDEBINFO_SUFFIX}.dll | ||
| ${pcl_component}${PCL_MINSIZEREL_SUFFIX}.dll | ||
| HINTS "${PCL_ROOT}/bin" | ||
| NO_DEFAULT_PATH) | ||
| find_file(PCL_${COMPONENT}_DLL_PATH_DEBUG | ||
| NAMES ${pcl_component}${PCL_DEBUG_SUFFIX}.dll | ||
| HINTS "${PCL_ROOT}/bin" | ||
| NO_DEFAULT_PATH) |
There was a problem hiding this comment.
The find_file results for DLL paths are not validated before being used in set_target_properties. If a DLL is not found, the variables PCL_${COMPONENT}DLL_PATH or PCL${COMPONENT}_DLL_PATH_DEBUG will be empty or set to NOTFOUND, which could result in invalid IMPORTED_LOCATION properties.
Consider adding validation after the find_file calls, such as checking if the variables are defined and not empty, and providing appropriate error messages or fallback behavior if the DLLs cannot be found. This is especially important for shared library builds on Windows where the DLLs are required for runtime.
| find_file(PCL_${COMPONENT}_DLL_PATH | ||
| NAMES | ||
| ${pcl_component}${PCL_RELEASE_SUFFIX}.dll | ||
| ${pcl_component}${PCL_RELWITHDEBINFO_SUFFIX}.dll | ||
| ${pcl_component}${PCL_MINSIZEREL_SUFFIX}.dll | ||
| HINTS "${PCL_ROOT}/bin" | ||
| NO_DEFAULT_PATH) | ||
| find_file(PCL_${COMPONENT}_DLL_PATH_DEBUG | ||
| NAMES ${pcl_component}${PCL_DEBUG_SUFFIX}.dll | ||
| HINTS "${PCL_ROOT}/bin" | ||
| NO_DEFAULT_PATH) |
There was a problem hiding this comment.
The newly introduced DLL path variables PCL_${COMPONENT}DLL_PATH and PCL${COMPONENT}DLL_PATH_DEBUG should be marked as advanced, similar to how other found paths like PCL${COMPONENT}_LIBRARY are marked at line 621. This follows the established pattern in the codebase and prevents these cache variables from cluttering the CMake GUI.
| if(PCL_${COMPONENT}_LIBRARY_DEBUG) | ||
| set_target_properties(${pcl_component} | ||
| PROPERTIES | ||
| IMPORTED_CONFIGURATIONS "RELEASE;DEBUG" | ||
| IMPORTED_LOCATION_RELEASE "${PCL_${COMPONENT}_DLL_PATH}" | ||
| IMPORTED_LOCATION_DEBUG "${PCL_${COMPONENT}_DLL_PATH_DEBUG}" | ||
| IMPORTED_IMPLIB_RELEASE "${PCL_${COMPONENT}_LIBRARY}" | ||
| IMPORTED_IMPLIB_DEBUG "${PCL_${COMPONENT}_LIBRARY_DEBUG}" | ||
| ) | ||
| else() | ||
| set_target_properties(${pcl_component} | ||
| PROPERTIES | ||
| IMPORTED_LOCATION "${PCL_${COMPONENT}_DLL_PATH}" | ||
| IMPORTED_IMPLIB "${PCL_${COMPONENT}_LIBRARY}" | ||
| ) | ||
| endif() |
There was a problem hiding this comment.
The code doesn't handle the case where only debug libraries and DLLs are available (analogous to lines 588-590 for .lib files). When only debug is available, PCL_${COMPONENT}LIBRARY_DEBUG will be set, causing the code to enter the dual-configuration branch at line 667. However, PCL${COMPONENT}_DLL_PATH (release) may not be found, leading to an empty or NOTFOUND value being set for IMPORTED_LOCATION_RELEASE.
Consider adding similar fallback logic for DLL paths: if PCL_${COMPONENT}DLL_PATH is not found but PCL${COMPONENT}_DLL_PATH_DEBUG is found, use the debug DLL path as a fallback for release builds on Windows.
PCLConfig.cmake.in
Outdated
| if(WIN32 AND NOT MINGW) | ||
| # On Windows, shared libraries are split into .dll (runtime) and .lib (import library). | ||
| # find dll paths | ||
| find_file(PCL_${COMPONENT}_DLL_PATH | ||
| NAMES | ||
| ${pcl_component}${PCL_RELEASE_SUFFIX}.dll | ||
| ${pcl_component}${PCL_RELWITHDEBINFO_SUFFIX}.dll | ||
| ${pcl_component}${PCL_MINSIZEREL_SUFFIX}.dll | ||
| HINTS "${PCL_ROOT}/bin" | ||
| NO_DEFAULT_PATH) | ||
| find_file(PCL_${COMPONENT}_DLL_PATH_DEBUG | ||
| NAMES ${pcl_component}${PCL_DEBUG_SUFFIX}.dll | ||
| HINTS "${PCL_ROOT}/bin" | ||
| NO_DEFAULT_PATH) | ||
|
|
||
| if ("${component}" STREQUAL "io") | ||
| find_file(PCL_${COMPONENT}_DLL_PATH | ||
| NAMES | ||
| pcl_io_ply${PCL_RELEASE_SUFFIX}.dll | ||
| pcl_io_ply${PCL_RELWITHDEBINFO_SUFFIX}.dll | ||
| pcl_io_ply${PCL_MINSIZEREL_SUFFIX}.dll | ||
| HINTS "${PCL_ROOT}/bin" | ||
| NO_DEFAULT_PATH) | ||
|
|
||
| find_file(PCL_${COMPONENT}_DLL_PATH_DEBUG | ||
| NAMES ${pcl_component}${PCL_DEBUG_SUFFIX}.dll | ||
| HINTS "${PCL_ROOT}/bin" | ||
| NO_DEFAULT_PATH) | ||
|
|
||
| endif() | ||
|
|
||
| if(PCL_${COMPONENT}_LIBRARY_DEBUG) | ||
| set_target_properties(${pcl_component} | ||
| PROPERTIES | ||
| IMPORTED_CONFIGURATIONS "RELEASE;DEBUG" | ||
| IMPORTED_LOCATION_RELEASE "${PCL_${COMPONENT}_DLL_PATH}" | ||
| IMPORTED_LOCATION_DEBUG "${PCL_${COMPONENT}_DLL_PATH_DEBUG}" | ||
| IMPORTED_IMPLIB_RELEASE "${PCL_${COMPONENT}_LIBRARY}" | ||
| IMPORTED_IMPLIB_DEBUG "${PCL_${COMPONENT}_LIBRARY_DEBUG}" | ||
| ) | ||
| else() | ||
| set_target_properties(${pcl_component} | ||
| PROPERTIES | ||
| IMPORTED_LOCATION "${PCL_${COMPONENT}_DLL_PATH}" | ||
| IMPORTED_IMPLIB "${PCL_${COMPONENT}_LIBRARY}" | ||
| ) | ||
| endif() |
There was a problem hiding this comment.
The DLL search logic should only be applied when PCL is built as shared libraries. When PCL is built as static libraries (PCL_SHARED_LIBS is OFF), there are no DLLs to find, and the code should use the .lib files for IMPORTED_LOCATION instead.
Consider wrapping the DLL search and the Windows-specific set_target_properties calls in a condition that checks PCL_SHARED_LIBS. When PCL_SHARED_LIBS is OFF, the Windows path should behave like the non-Windows path at lines 684-698, using PCL_${COMPONENT}_LIBRARY for IMPORTED_LOCATION.
Fixes #6345