find_package() ignores <PackageName>_ROOT

495 Views Asked by At

In my CMake script I append the path to a folder containing <PackageName>Config.cmake to <PackageName>_ROOT and then call find_package(<PackageName> REQUIRED) but it can't find my package.

When I use CMAKE_FIND_DEBUG_MODE I see my folder listed in <PackageName>_ROOT CMake variable [CMAKE_FIND_USE_PACKAGE_ROOT_PATH] (it is actually the only folder there), but it is not listed after find_package considered the following locations for the Config module:.

Why am I getting such behaviour? I use CMake 3.18.1 from Android Studio. The package I'm trying to find is OpenCV.


Relatively to my CMakeLists.txt file OpenCV is installed in ../../build/opencv-build<custom suffix>, so my code for finding it is:

get_filename_component(OPENCV_BUILD_DIRS_ROOT ../../build REALPATH)
file(GLOB OPENCV_BUILD_DIRS ${OPENCV_BUILD_DIRS_ROOT}/opencv-build*)
list(APPEND OpenCV_ROOT ${OPENCV_BUILD_DIRS})

find_package(OpenCV ${OPENCV_VERSION} REQUIRED ${OPENCV_PUBLIC_LIBRARIES} ${OPENCV_PRIVATE_LIBRARIES})

When I run it on Linux (WSL actually), everything works fine and CMake finds OpenCV succesfully in ../../build/opencv-build (or <project path>/build/opencv-build in the form of absolute path).

But when I try to build the project from Android Studio it doesn't, and I get this output from CMAKE_FIND_DEBUG_MODE:

CMake Debug Log at external/opencv/CMakeLists.txt:12 (find_package):
  find_package considered the following paths for OpenCV.cmake

    C:/Users/<username>/AppData/Local/Android/Sdk/cmake/3.18.1/share/cmake-3.18/Modules/FindOpenCV.cmake

  The file was not found.

  <PackageName>_ROOT CMake variable [CMAKE_FIND_USE_PACKAGE_ROOT_PATH].

    <project path>/build/opencv-build

  

  CMAKE_PREFIX_PATH variable [CMAKE_FIND_USE_CMAKE_PATH].

    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/windows-x86_64

  

  CMAKE_FRAMEWORK_PATH and CMAKE_APPBUNDLE_PATH variables
  [CMAKE_FIND_USE_CMAKE_PATH].

  

  Env variable OpenCV_DIR [CMAKE_FIND_USE_CMAKE_ENVIRONMENT_PATH].

    none

  CMAKE_PREFIX_PATH env variable [CMAKE_FIND_USE_CMAKE_ENVIRONMENT_PATH].

    none

  CMAKE_FRAMEWORK_PATH and CMAKE_APPBUNDLE_PATH env variables
  [CMAKE_FIND_USE_CMAKE_ENVIRONMENT_PATH].

    none

  Paths specified by the find_package HINTS option.

    none

  Standard system environment variables
  [CMAKE_FIND_USE_SYSTEM_ENVIRONMENT_PATH].

    <a lot of unrelated directories>

  

  CMake User Package Registry [CMAKE_FIND_USE_PACKAGE_REGISTRY].

    none

  CMake variables defined in the Platform file
  [CMAKE_FIND_USE_CMAKE_SYSTEM_PATH].

    C:/Users/<username>/AppData/Local/Android/Sdk/cmake/3.18.1
    <other unrelated directories>

  

  CMake System Package Registry
  [CMAKE_FIND_PACKAGE_NO_SYSTEM_PACKAGE_REGISTRY].

    none

  Paths specified by the find_package PATHS option.

    none

  find_package considered the following locations for the Config module:

    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/windows-x86_64/OpenCVConfig.cmake
    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/windows-x86_64/opencv-config.cmake
    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/OpenCVConfig.cmake
    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/opencv-config.cmake
    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/windows-x86_64/sysroot/usr/lib/i686-linux-android/21/OpenCVConfig.cmake
    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/windows-x86_64/sysroot/usr/lib/i686-linux-android/21/opencv-config.cmake
    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/windows-x86_64/sysroot/usr/local/OpenCVConfig.cmake
    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/windows-x86_64/sysroot/usr/local/opencv-config.cmake
    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/windows-x86_64/sysroot/usr/OpenCVConfig.cmake
    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/windows-x86_64/sysroot/usr/opencv-config.cmake
    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/windows-x86_64/sysroot/OpenCVConfig.cmake
    C:/Users/<username>/AppData/Local/Android/Sdk/ndk/23.1.7779620/toolchains/llvm/prebuilt/windows-x86_64/sysroot/opencv-config.cmake

  The file was not found.
1

There are 1 best solutions below

0
On BEST ANSWER

So, the problem actually was that for Android (and, probably, iOS) CMake sets CMAKE_FIND_ROOT_PATH_MODE_PACKAGE variable (and other CMAKE_FIND_ROOT_PATH_MODE_* variables) to ONLY which makes find_package (and other find_* functions) prefix paths with what is in CMAKE_FIND_ROOT_PATH list.

To override this, one can do some of the following:

  • Set CMAKE_FIND_ROOT_PATH_MODE_* to BOTH or NEVER
  • Use CMAKE_FIND_ROOT_PATH_BOTH or NO_CMAKE_FIND_ROOT_PATH for each find_* call

It should also fix the issues when CMake ignores paths from HINTS, PATHS and other prefix construction steps.