Browse Source

Merge topic 'cpack-rpm-external-symlink-handling'

eae4eef0 CPack/RPM external symlink handling
Brad King 9 years ago
parent
commit
e0cc8bf5d7

+ 5 - 0
Help/release/dev/cpack-rpm-external-symlink-handling.rst

@@ -0,0 +1,5 @@
+cpack-rpm-external-symlink-handling
+-----------------------------------
+
+* The "CPackRPM" module learned how to correctly handle symlinks
+  that are pointing outside generated packages.

+ 23 - 7
Modules/CPackRPM.cmake

@@ -599,9 +599,10 @@
 # while determining if symlink should be either created or present in a
 # post install script - depending on relocation paths.
 #
-# Currenty there are a few limitations though:
+# Symbolic links that point to locations outside packaging path produce a
+# warning and are treated as non relocatable permanent symbolic links.
 #
-# * Only symbolic links with relative path can be packaged.
+# Currenty there are a few limitations though:
 #
 # * For component based packaging component interdependency is not checked
 #   when processing symbolic links. Symbolic links pointing to content of
@@ -1068,13 +1069,28 @@ function(cpack_rpm_prepare_install_files INSTALL_FILES_LIST WDIR PACKAGE_PREFIXE
           get_filename_component(SYMLINK_POINT_ "${SYMLINK_LOCATION_}/${SYMLINK_POINT_}" ABSOLUTE)
         endif()
 
-        string(SUBSTRING "${SYMLINK_POINT_}" ${WDR_LEN_} -1 SYMLINK_POINT_WD_)
+        # recalculate path length after conversion to canonical form
+        string(LENGTH "${SYMLINK_POINT_}" SYMLINK_POINT_LENGTH_)
 
-        cpack_rpm_symlink_get_relocation_prefixes("${F}" "${PACKAGE_PREFIXES}" "SYMLINK_RELOCATIONS")
-        cpack_rpm_symlink_get_relocation_prefixes("${SYMLINK_POINT_WD_}" "${PACKAGE_PREFIXES}" "POINT_RELOCATIONS")
+        if(SYMLINK_POINT_ MATCHES "${WDIR}/.*")
+          # only symlinks that are pointing inside the packaging structure should be checked for relocation
+          string(SUBSTRING "${SYMLINK_POINT_}" ${WDR_LEN_} -1 SYMLINK_POINT_WD_)
+          cpack_rpm_symlink_get_relocation_prefixes("${F}" "${PACKAGE_PREFIXES}" "SYMLINK_RELOCATIONS")
+          cpack_rpm_symlink_get_relocation_prefixes("${SYMLINK_POINT_WD_}" "${PACKAGE_PREFIXES}" "POINT_RELOCATIONS")
 
-        list(LENGTH SYMLINK_RELOCATIONS SYMLINK_RELOCATIONS_COUNT)
-        list(LENGTH POINT_RELOCATIONS POINT_RELOCATIONS_COUNT)
+          list(LENGTH SYMLINK_RELOCATIONS SYMLINK_RELOCATIONS_COUNT)
+          list(LENGTH POINT_RELOCATIONS POINT_RELOCATIONS_COUNT)
+        else()
+          # location pointed to is ouside WDR so it should be treated as a permanent symlink
+          set(SYMLINK_POINT_WD_ "${SYMLINK_POINT_}")
+
+          unset(SYMLINK_RELOCATIONS)
+          unset(POINT_RELOCATIONS)
+          unset(SYMLINK_RELOCATIONS_COUNT)
+          unset(POINT_RELOCATIONS_COUNT)
+
+          message(AUTHOR_WARNING "CPackRPM:Warning: Symbolic link '${F}' points to location that is outside packaging path! Link will possibly not be relocatable.")
+        endif()
 
         if(SYMLINK_RELOCATIONS_COUNT AND POINT_RELOCATIONS_COUNT)
           # find matching

+ 3 - 0
Tests/CPackComponentsForAll/CMakeLists.txt

@@ -92,6 +92,9 @@ if("${CPACK_GENERATOR}" MATCHES "RPM")
   # test symbolic link to location outside package
   execute_process(COMMAND ${CMAKE_COMMAND} -E create_symlink ./outside_package symlink_outside_package)
   install(FILES ${CMAKE_CURRENT_BINARY_DIR}/symlink_outside_package DESTINATION ${CMAKE_INSTALL_LIBDIR}/inside_relocatable_one/depth_two COMPONENT libraries)
+  # test symbolic link to location outside wdr (packaging directory)
+  execute_process(COMMAND ${CMAKE_COMMAND} -E create_symlink /outside_package_wdr symlink_outside_wdr)
+  install(FILES ${CMAKE_CURRENT_BINARY_DIR}/symlink_outside_wdr DESTINATION ${CMAKE_INSTALL_LIBDIR}/inside_relocatable_one/depth_two COMPONENT libraries)
 endif()
 
 # CPack boilerplate for this project

+ 3 - 0
Tests/CPackComponentsForAll/RunCPackVerifyResult.cmake

@@ -188,6 +188,7 @@ if(CPackGen MATCHES "RPM")
 /usr/foo/bar/lib${LIB_SUFFIX}/inside_relocatable_one/depth_two/depth_three
 /usr/foo/bar/lib${LIB_SUFFIX}/inside_relocatable_one/depth_two/depth_three/symlink_parentdir_path
 /usr/foo/bar/lib${LIB_SUFFIX}/inside_relocatable_one/depth_two/symlink_outside_package
+/usr/foo/bar/lib${LIB_SUFFIX}/inside_relocatable_one/depth_two/symlink_outside_wdr
 /usr/foo/bar/lib${LIB_SUFFIX}/inside_relocatable_one/depth_two/symlink_relocatable_subpath
 /usr/foo/bar/lib${LIB_SUFFIX}/inside_relocatable_one/depth_two/symlink_samedir_path
 /usr/foo/bar/lib${LIB_SUFFIX}/inside_relocatable_one/depth_two/symlink_samedir_path_current_dir
@@ -354,6 +355,8 @@ if(CPackGen MATCHES "RPM")
         string(REGEX MATCH "^.*${whitespaces}->${whitespaces}${CPACK_PACKAGING_INSTALL_PREFIX}/non_relocatable/depth_two$" check_symlink "${SYMLINK_POINT_}")
       elseif("${symlink_name}" STREQUAL "symlink_outside_package")
         string(REGEX MATCH "^.*${whitespaces}->${whitespaces}outside_package$" check_symlink "${SYMLINK_POINT_}")
+      elseif("${symlink_name}" STREQUAL "symlink_outside_wdr")
+        string(REGEX MATCH "^.*${whitespaces}->${whitespaces}/outside_package_wdr$" check_symlink "${SYMLINK_POINT_}")
       elseif("${symlink_name}" STREQUAL "symlink_other_relocatable_path"
           OR "${symlink_name}" STREQUAL "symlink_from_non_relocatable_path"
           OR "${symlink_name}" STREQUAL "symlink_relocatable_subpath")