فهرست منبع

Merge topic 'ImproveFindPackageConfigMode'

5cdfc9c Improve wording of the error message of find_package() in config-mode
4969c3b Improve version notice in the generated message
e8ae504 Add option CONFIG_MODE to FPHSA()
b4b8f96 Don't create an empty element at the end of Foo_CONSIDERED_CONFIGS/VERSIONS
cc955a0 Small cleanup of FindPackageHandleStandardArgs.cmake
0367245 Replace the two vector<string,string> with one vector<struct{string,string}>
130b0e2 Improve error message in Config-mode when no appropriate version was found
dfe9c95 Record all considered Config files and their versions.
Brad King 15 سال پیش
والد
کامیت
4ea441eaf9
3فایلهای تغییر یافته به همراه225 افزوده شده و 96 حذف شده
  1. 111 61
      Modules/FindPackageHandleStandardArgs.cmake
  2. 109 34
      Source/cmFindPackageCommand.cxx
  3. 5 1
      Source/cmFindPackageCommand.h

+ 111 - 61
Modules/FindPackageHandleStandardArgs.cmake

@@ -20,18 +20,24 @@
 # The second mode is more powerful and also supports version checking:
 #    FIND_PACKAGE_HANDLE_STANDARD_ARGS(NAME [REQUIRED_VARS <var1>...<varN>]
 #                                           [VERSION_VAR   <versionvar>
+#                                           [CONFIG_MODE]
 #                                           [FAIL_MESSAGE "Custom failure message"] )
 #
 # As above, if <var1> through <varN> are all valid, <UPPERCASED_NAME>_FOUND
 # will be set to TRUE.
-# Via FAIL_MESSAGE a custom failure message can be specified, if this is not
-# used, the default message will be displayed.
+# After REQUIRED_VARS the variables which are required for this package are listed.
 # Following VERSION_VAR the name of the variable can be specified which holds
 # the version of the package which has been found. If this is done, this version
 # will be checked against the (potentially) specified required version used
 # in the find_package() call. The EXACT keyword is also handled. The default
 # messages include information about the required version and the version
 # which has been actually found, both if the version is ok or not.
+# Use the option CONFIG_MODE if your FindXXX.cmake module is a wrapper for
+# a find_package(... NO_MODULE) call, in this case all the information
+# provided by the config-mode of find_package() will be evaluated
+# automatically.
+# Via FAIL_MESSAGE a custom failure message can be specified, if this is not
+# used, the default message will be displayed.
 #
 # Example for mode 1:
 #
@@ -53,6 +59,15 @@
 # Also the version of BISON will be checked by using the version contained
 # in BISON_VERSION.
 # Since no FAIL_MESSAGE is given, the default messages will be printed.
+#
+# Another example for mode 2:
+#
+#    FIND_PACKAGE(Automoc4 QUIET NO_MODULE HINTS /opt/automoc4)
+#    FIND_PACKAGE_HANDLE_STANDARD_ARGS(Automoc4  CONFIG_MODE)
+# In this case, FindAutmoc4.cmake wraps a call to FIND_PACKAGE(Automoc4 NO_MODULE)
+# and adds an additional search directory for automoc4.
+# The following FIND_PACKAGE_HANDLE_STANDARD_ARGS() call produces a proper
+# success/error message.
 
 #=============================================================================
 # Copyright 2007-2009 Kitware, Inc.
@@ -70,12 +85,50 @@
 INCLUDE(FindPackageMessage)
 INCLUDE(CMakeParseArguments)
 
-
-FUNCTION(FIND_PACKAGE_HANDLE_STANDARD_ARGS _NAME _FIRST_ARG _VAR1)
+# internal helper macro
+MACRO(_FPHSA_FAILURE_MESSAGE _msg)
+  IF (${_NAME}_FIND_REQUIRED)
+    MESSAGE(FATAL_ERROR "${_msg}")
+  ELSE (${_NAME}_FIND_REQUIRED)
+    IF (NOT ${_NAME}_FIND_QUIETLY)
+      MESSAGE(STATUS "${_msg}")
+    ENDIF (NOT ${_NAME}_FIND_QUIETLY)
+  ENDIF (${_NAME}_FIND_REQUIRED)
+ENDMACRO(_FPHSA_FAILURE_MESSAGE _msg)
+
+
+# internal helper macro to generate the failure message when used in CONFIG_MODE:
+MACRO(_FPHSA_HANDLE_FAILURE_CONFIG_MODE)
+  # <name>_CONFIG is set, but FOUND is false, this means that some other of the REQUIRED_VARS was not found:
+  IF(${_NAME}_CONFIG)
+    _FPHSA_FAILURE_MESSAGE("${FPHSA_FAIL_MESSAGE}: missing: ${MISSING_VARS} (found ${${_NAME}_CONFIG} ${VERSION_MSG})")
+  ELSE(${_NAME}_CONFIG)
+    # If _CONSIDERED_CONFIGS is set, the config-file has been found, but no suitable version.
+    # List them all in the error message:
+    IF(${_NAME}_CONSIDERED_CONFIGS)
+      SET(configsText "")
+      LIST(LENGTH ${_NAME}_CONSIDERED_CONFIGS configsCount)
+      MATH(EXPR configsCount "${configsCount} - 1")
+      FOREACH(currentConfigIndex RANGE ${configsCount})
+        LIST(GET ${_NAME}_CONSIDERED_CONFIGS ${currentConfigIndex} filename)
+        LIST(GET ${_NAME}_CONSIDERED_VERSIONS ${currentConfigIndex} version)
+        SET(configsText "${configsText}    ${filename} (version ${version})\n")
+      ENDFOREACH(currentConfigIndex)
+      _FPHSA_FAILURE_MESSAGE("${FPHSA_FAIL_MESSAGE} ${VERSION_MSG}, checked the following files:\n${configsText}")
+
+    ELSE(${_NAME}_CONSIDERED_CONFIGS)
+      # Simple case: No Config-file was found at all:
+      _FPHSA_FAILURE_MESSAGE("${FPHSA_FAIL_MESSAGE}: found neither ${_NAME}Config.cmake nor ${_NAME_LOWER}-config.cmake ${VERSION_MSG}")
+    ENDIF(${_NAME}_CONSIDERED_CONFIGS)
+  ENDIF(${_NAME}_CONFIG)
+ENDMACRO(_FPHSA_HANDLE_FAILURE_CONFIG_MODE)
+
+
+FUNCTION(FIND_PACKAGE_HANDLE_STANDARD_ARGS _NAME _FIRST_ARG)
 
 # set up the arguments for CMAKE_PARSE_ARGUMENTS and check whether we are in
 # new extended or in the "old" mode:
-  SET(options) # none
+  SET(options CONFIG_MODE)
   SET(oneValueArgs FAIL_MESSAGE VERSION_VAR)
   SET(multiValueArgs REQUIRED_VARS)
   SET(_KEYWORDS_FOR_EXTENDED_MODE  ${options} ${oneValueArgs} ${multiValueArgs} )
@@ -83,11 +136,11 @@ FUNCTION(FIND_PACKAGE_HANDLE_STANDARD_ARGS _NAME _FIRST_ARG _VAR1)
 
   IF(${INDEX} EQUAL -1)
     SET(FPHSA_FAIL_MESSAGE ${_FIRST_ARG})
-    SET(FPHSA_REQUIRED_VARS ${_VAR1} ${ARGN})
+    SET(FPHSA_REQUIRED_VARS ${ARGN})
     SET(FPHSA_VERSION_VAR)
   ELSE(${INDEX} EQUAL -1)
 
-    CMAKE_PARSE_ARGUMENTS(FPHSA "${options}" "${oneValueArgs}" "${multiValueArgs}"  ${_FIRST_ARG} ${_VAR1} ${ARGN})
+    CMAKE_PARSE_ARGUMENTS(FPHSA "${options}" "${oneValueArgs}" "${multiValueArgs}"  ${_FIRST_ARG} ${ARGN})
 
     IF(FPHSA_UNPARSED_ARGUMENTS)
       MESSAGE(FATAL_ERROR "Unknown keywords given to FIND_PACKAGE_HANDLE_STANDARD_ARGS(): \"${FPHSA_UNPARSED_ARGUMENTS}\"")
@@ -104,6 +157,14 @@ FUNCTION(FIND_PACKAGE_HANDLE_STANDARD_ARGS _NAME _FIRST_ARG _VAR1)
     SET(FPHSA_FAIL_MESSAGE "Could NOT find ${_NAME}")
   ENDIF("${FPHSA_FAIL_MESSAGE}" STREQUAL "DEFAULT_MSG")
 
+  # In config-mode, we rely on the variable <package>_CONFIG, which is set by find_package()
+  # when it successfully found the config-file, including version checking:
+  IF(FPHSA_CONFIG_MODE)
+    LIST(INSERT FPHSA_REQUIRED_VARS 0 ${_NAME}_CONFIG)
+    LIST(REMOVE_DUPLICATES FPHSA_REQUIRED_VARS)
+    SET(FPHSA_VERSION_VAR ${_NAME}_VERSION)
+  ENDIF(FPHSA_CONFIG_MODE)
+
   IF(NOT FPHSA_REQUIRED_VARS)
     MESSAGE(FATAL_ERROR "No REQUIRED_VARS specified for FIND_PACKAGE_HANDLE_STANDARD_ARGS()")
   ENDIF(NOT FPHSA_REQUIRED_VARS)
@@ -111,8 +172,9 @@ FUNCTION(FIND_PACKAGE_HANDLE_STANDARD_ARGS _NAME _FIRST_ARG _VAR1)
   LIST(GET FPHSA_REQUIRED_VARS 0 _FIRST_REQUIRED_VAR)
 
   STRING(TOUPPER ${_NAME} _NAME_UPPER)
+  STRING(TOLOWER ${_NAME} _NAME_LOWER)
 
-  # collect all variables which were not found, so they can be printed, so the 
+  # collect all variables which were not found, so they can be printed, so the
   # user knows better what went wrong (#6375)
   SET(MISSING_VARS "")
   SET(DETAILS "")
@@ -131,44 +193,42 @@ FUNCTION(FIND_PACKAGE_HANDLE_STANDARD_ARGS _NAME _FIRST_ARG _VAR1)
   # version handling:
   SET(VERSION_MSG "")
   SET(VERSION_OK TRUE)
+  SET(VERSION ${${FPHSA_VERSION_VAR}} )
   IF (${_NAME}_FIND_VERSION)
 
-    # if the package was found, check for the version using <NAME>_FIND_VERSION
-    IF (${_NAME_UPPER}_FOUND)
-      SET(VERSION ${${FPHSA_VERSION_VAR}} )
-
-      IF(VERSION)
-
-        IF(${_NAME}_FIND_VERSION_EXACT)       # exact version required
-          IF (NOT "${${_NAME}_FIND_VERSION}" VERSION_EQUAL "${VERSION}")
-            SET(VERSION_MSG " Found version \"${VERSION}\", but required is exact version \"${${_NAME}_FIND_VERSION}\"")
-            SET(VERSION_OK FALSE)
-          ELSE (NOT "${${_NAME}_FIND_VERSION}" VERSION_EQUAL "${VERSION}")
-            SET(VERSION_MSG " (found exact version \"${VERSION}\")")
-          ENDIF (NOT "${${_NAME}_FIND_VERSION}" VERSION_EQUAL "${VERSION}")
-
-        ELSE(${_NAME}_FIND_VERSION_EXACT)     # minimum version specified:
-          IF ("${${_NAME}_FIND_VERSION}" VERSION_GREATER "${VERSION}")
-            SET(VERSION_MSG " Found version \"${VERSION}\", but required is at least \"${${_NAME}_FIND_VERSION}\"")
-            SET(VERSION_OK FALSE)
-          ELSE ("${${_NAME}_FIND_VERSION}" VERSION_GREATER "${VERSION}")
-            SET(VERSION_MSG " (found version \"${VERSION}\", required is \"${${_NAME}_FIND_VERSION}\")")
-          ENDIF ("${${_NAME}_FIND_VERSION}" VERSION_GREATER "${VERSION}")
-        ENDIF(${_NAME}_FIND_VERSION_EXACT)
-
-# Uncomment the following two lines to see to which Find-modules the VERSION_VAR keywords still need to be added:
-#      ELSE(VERSION)
-#        SET(VERSION_MSG " (WARNING: Required version is \"${${_NAME}_FIND_VERSION}\", but version of ${_NAME} is unknown)")
-      ENDIF(VERSION)
-
-    # if the package was not found, but a version was given, add that to the output:
-    ELSE (${_NAME_UPPER}_FOUND)
+    IF(VERSION)
+
+      IF(${_NAME}_FIND_VERSION_EXACT)       # exact version required
+        IF (NOT "${${_NAME}_FIND_VERSION}" VERSION_EQUAL "${VERSION}")
+          SET(VERSION_MSG "Found unsuitable version \"${VERSION}\", but required is exact version \"${${_NAME}_FIND_VERSION}\"")
+          SET(VERSION_OK FALSE)
+        ELSE (NOT "${${_NAME}_FIND_VERSION}" VERSION_EQUAL "${VERSION}")
+          SET(VERSION_MSG "(found suitable exact version \"${VERSION}\")")
+        ENDIF (NOT "${${_NAME}_FIND_VERSION}" VERSION_EQUAL "${VERSION}")
+
+      ELSE(${_NAME}_FIND_VERSION_EXACT)     # minimum version specified:
+        IF ("${${_NAME}_FIND_VERSION}" VERSION_GREATER "${VERSION}")
+          SET(VERSION_MSG "Found unsuitable version \"${VERSION}\", but required is at least \"${${_NAME}_FIND_VERSION}\"")
+          SET(VERSION_OK FALSE)
+        ELSE ("${${_NAME}_FIND_VERSION}" VERSION_GREATER "${VERSION}")
+          SET(VERSION_MSG "(found suitable version \"${VERSION}\", required is \"${${_NAME}_FIND_VERSION}\")")
+        ENDIF ("${${_NAME}_FIND_VERSION}" VERSION_GREATER "${VERSION}")
+      ENDIF(${_NAME}_FIND_VERSION_EXACT)
+
+    ELSE(VERSION)
+
+      # if the package was not found, but a version was given, add that to the output:
       IF(${_NAME}_FIND_VERSION_EXACT)
-         SET(VERSION_MSG " (Required is exact version \"${${_NAME}_FIND_VERSION}\")")
+         SET(VERSION_MSG "(Required is exact version \"${${_NAME}_FIND_VERSION}\")")
       ELSE(${_NAME}_FIND_VERSION_EXACT)
-         SET(VERSION_MSG " (Required is at least version \"${${_NAME}_FIND_VERSION}\")")
+         SET(VERSION_MSG "(Required is at least version \"${${_NAME}_FIND_VERSION}\")")
       ENDIF(${_NAME}_FIND_VERSION_EXACT)
-    ENDIF (${_NAME_UPPER}_FOUND)
+
+    ENDIF(VERSION)
+  ELSE (${_NAME}_FIND_VERSION)
+    IF(VERSION)
+      SET(VERSION_MSG "(found version \"${VERSION}\")")
+    ENDIF(VERSION)
   ENDIF (${_NAME}_FIND_VERSION)
 
   IF(VERSION_OK)
@@ -182,26 +242,16 @@ FUNCTION(FIND_PACKAGE_HANDLE_STANDARD_ARGS _NAME _FIRST_ARG _VAR1)
   IF (${_NAME_UPPER}_FOUND)
     FIND_PACKAGE_MESSAGE(${_NAME} "Found ${_NAME}: ${${_FIRST_REQUIRED_VAR}} ${VERSION_MSG}" "${DETAILS}")
   ELSE (${_NAME_UPPER}_FOUND)
-    IF(NOT VERSION_OK)
-
-      IF (${_NAME}_FIND_REQUIRED)
-          MESSAGE(FATAL_ERROR "${FPHSA_FAIL_MESSAGE}: ${VERSION_MSG} (found ${${_FIRST_REQUIRED_VAR}})")
-      ELSE (${_NAME}_FIND_REQUIRED)
-        IF (NOT ${_NAME}_FIND_QUIETLY)
-          MESSAGE(STATUS "${FPHSA_FAIL_MESSAGE}: ${VERSION_MSG} (found ${${_FIRST_REQUIRED_VAR}})")
-        ENDIF (NOT ${_NAME}_FIND_QUIETLY)
-      ENDIF (${_NAME}_FIND_REQUIRED)
-
-    ELSE(NOT VERSION_OK)
-
-      IF (${_NAME}_FIND_REQUIRED)
-          MESSAGE(FATAL_ERROR "${FPHSA_FAIL_MESSAGE} (missing: ${MISSING_VARS}) ${VERSION_MSG}")
-      ELSE (${_NAME}_FIND_REQUIRED)
-        IF (NOT ${_NAME}_FIND_QUIETLY)
-          MESSAGE(STATUS "${FPHSA_FAIL_MESSAGE}  (missing: ${MISSING_VARS}) ${VERSION_MSG}")
-        ENDIF (NOT ${_NAME}_FIND_QUIETLY)
-      ENDIF (${_NAME}_FIND_REQUIRED)
-    ENDIF(NOT VERSION_OK)
+
+    IF(FPHSA_CONFIG_MODE)
+      _FPHSA_HANDLE_FAILURE_CONFIG_MODE()
+    ELSE(FPHSA_CONFIG_MODE)
+      IF(NOT VERSION_OK)
+        _FPHSA_FAILURE_MESSAGE("${FPHSA_FAIL_MESSAGE}: ${VERSION_MSG} (found ${${_FIRST_REQUIRED_VAR}})")
+      ELSE(NOT VERSION_OK)
+        _FPHSA_FAILURE_MESSAGE("${FPHSA_FAIL_MESSAGE} (missing: ${MISSING_VARS}) ${VERSION_MSG}")
+      ENDIF(NOT VERSION_OK)
+    ENDIF(FPHSA_CONFIG_MODE)
 
   ENDIF (${_NAME_UPPER}_FOUND)
 

+ 109 - 34
Source/cmFindPackageCommand.cxx

@@ -156,6 +156,11 @@ cmFindPackageCommand::cmFindPackageCommand()
     "The full path to the configuration file is stored in the cmake "
     "variable <package>_CONFIG."
     "\n"
+    "All configuration files which have been considered by CMake while "
+    "searching for an installation of the package with an appropriate "
+    "version are stored in the cmake variable <package>_CONSIDERED_CONFIGS, "
+    "the associated versions in <package>_CONSIDERED_VERSIONS. "
+    "\n"
     "If the package configuration file cannot be found CMake "
     "will generate an error describing the problem unless the QUIET "
     "argument is specified.  If REQUIRED is specified and the package "
@@ -618,7 +623,7 @@ void cmFindPackageCommand::SetModuleVariables(const std::string& components)
   // Store the list of components.
   std::string components_var = this->Name + "_FIND_COMPONENTS";
   this->AddFindDefinition(components_var.c_str(), components.c_str());
-   
+
   if(this->Quiet)
     {
     // Tell the module that is about to be read that it should find
@@ -721,6 +726,8 @@ bool cmFindPackageCommand::FindModule(bool& found)
 //----------------------------------------------------------------------------
 bool cmFindPackageCommand::HandlePackageMode()
 {
+  this->ConsideredConfigs.clear();
+
   // Support old capitalization behavior.
   std::string upperDir = cmSystemTools::UpperCase(this->Name);
   std::string upperFound = cmSystemTools::UpperCase(this->Name);
@@ -809,36 +816,58 @@ bool cmFindPackageCommand::HandlePackageMode()
     {
     // The variable is not set.
     cmOStringStream e;
-    e << "Could not find ";
-    if(!this->NoModule)
-      {
-      e << "module Find" << this->Name << ".cmake or ";
-      }
-    e << "a configuration file for package " << this->Name << ".\n";
-    if(!this->NoModule)
-      {
-      e << "Adjust CMAKE_MODULE_PATH to find Find"
-        << this->Name << ".cmake or set ";
-      }
-    else
-      {
-      e << "Set ";
-      }
-    e << this->Variable << " to the directory containing a CMake "
-      << "configuration file for " << this->Name << ".  ";
-    if(this->Configs.size() == 1)
-      {
-      e << "The file will be called " << this->Configs[0];
+    // If there are files in ConsideredConfigs, it means that FooConfig.cmake
+    // have been found, but they didn't have appropriate versions.
+    if (this->ConsideredConfigs.size() > 0)
+      {
+      e << "Could not find a configuration file for package \""
+        << this->Name << "\" that "
+        << (this->VersionExact? "exactly matches" : "is compatible with")
+        << " requested version \"" << this->Version << "\".\n"
+        << "The following configuration files were considered but not "
+           "accepted:\n";
+      for(std::vector<ConfigFileInfo>::size_type i=0;
+          i<this->ConsideredConfigs.size(); i++)
+        {
+        e << "  " << this->ConsideredConfigs[i].filename
+          << ", version: " << this->ConsideredConfigs[i].version << "\n";
+        }
       }
     else
       {
-      e << "The file will have one of the following names:\n";
-      for(std::vector<std::string>::const_iterator ci = this->Configs.begin();
-          ci != this->Configs.end(); ++ci)
+      e << "Could not find ";
+      if(!this->NoModule)
+        {
+        e << "module Find" << this->Name << ".cmake or ";
+        }
+      e << "a configuration file for package " << this->Name << ".\n";
+      if(!this->NoModule)
+        {
+        e << "Adjust CMAKE_MODULE_PATH to find Find"
+          << this->Name << ".cmake or set ";
+        }
+      else
+        {
+        e << "Set ";
+        }
+      e << this->Variable << " to the directory containing a CMake "
+        << "configuration file for " << this->Name << ".  ";
+      if(this->Configs.size() == 1)
+        {
+        e << "The file will be called " << this->Configs[0];
+        }
+      else
         {
-        e << "  " << *ci << "\n";
+        e << "The file will have one of the following names:\n";
+        for(std::vector<std::string>::const_iterator ci=this->Configs.begin();
+            ci != this->Configs.end(); ++ci)
+          {
+          e << "  " << *ci << "\n";
+          }
         }
       }
+
+
     this->Makefile->IssueMessage(
       this->Required? cmake::FATAL_ERROR : cmake::WARNING, e.str());
     }
@@ -897,6 +926,31 @@ bool cmFindPackageCommand::HandlePackageMode()
     }
 #endif
 
+  std::string consideredConfigsVar = this->Name;
+  consideredConfigsVar += "_CONSIDERED_CONFIGS";
+  std::string consideredVersionsVar = this->Name;
+  consideredVersionsVar += "_CONSIDERED_VERSIONS";
+
+  std::string consideredConfigFiles;
+  std::string consideredVersions;
+
+  const char* sep = "";
+  for(std::vector<ConfigFileInfo>::size_type i=0;
+      i<this->ConsideredConfigs.size(); i++)
+    {
+    consideredConfigFiles += sep;
+    consideredVersions += sep;
+    consideredConfigFiles += this->ConsideredConfigs[i].filename;
+    consideredVersions += this->ConsideredConfigs[i].version;
+    sep = ";";
+    }
+
+  this->Makefile->AddDefinition(consideredConfigsVar.c_str(),
+                                consideredConfigFiles.c_str());
+
+  this->Makefile->AddDefinition(consideredVersionsVar.c_str(),
+                                consideredVersions.c_str());
+
   return result;
 }
 
@@ -1481,6 +1535,10 @@ bool cmFindPackageCommand::FindConfigFile(std::string const& dir,
 //----------------------------------------------------------------------------
 bool cmFindPackageCommand::CheckVersion(std::string const& config_file)
 {
+  bool result = false; // by default, assume the version is not ok.
+  bool haveResult = false;
+  std::string version = "unknown";
+
   // Get the filename without the .cmake extension.
   std::string::size_type pos = config_file.rfind('.');
   std::string version_file_base = config_file.substr(0, pos);
@@ -1488,31 +1546,42 @@ bool cmFindPackageCommand::CheckVersion(std::string const& config_file)
   // Look for foo-config-version.cmake
   std::string version_file = version_file_base;
   version_file += "-version.cmake";
-  if(cmSystemTools::FileExists(version_file.c_str(), true))
+  if ((haveResult == false)
+       && (cmSystemTools::FileExists(version_file.c_str(), true)))
     {
-    return this->CheckVersionFile(version_file);
+    result = this->CheckVersionFile(version_file, version);
+    haveResult = true;
     }
 
   // Look for fooConfigVersion.cmake
   version_file = version_file_base;
   version_file += "Version.cmake";
-  if(cmSystemTools::FileExists(version_file.c_str(), true))
+  if ((haveResult == false)
+       && (cmSystemTools::FileExists(version_file.c_str(), true)))
     {
-    return this->CheckVersionFile(version_file);
+    result = this->CheckVersionFile(version_file, version);
+    haveResult = true;
     }
 
+
   // If no version was requested a versionless package is acceptable.
-  if(this->Version.empty())
+  if ((haveResult == false) && (this->Version.empty()))
     {
-    return true;
+    result = true;
+    haveResult = true;
     }
 
-  // No version file found.  Assume the version is incompatible.
-  return false;
+  ConfigFileInfo configFileInfo;
+  configFileInfo.filename = config_file;
+  configFileInfo.version = version;
+  this->ConsideredConfigs.push_back(configFileInfo);
+
+  return result;
 }
 
 //----------------------------------------------------------------------------
-bool cmFindPackageCommand::CheckVersionFile(std::string const& version_file)
+bool cmFindPackageCommand::CheckVersionFile(std::string const& version_file,
+                                            std::string& result_version)
 {
   // The version file will be loaded in an isolated scope.
   cmMakefile::ScopePushPop varScope(this->Makefile);
@@ -1585,6 +1654,12 @@ bool cmFindPackageCommand::CheckVersionFile(std::string const& version_file)
       }
     }
 
+  result_version = this->Makefile->GetSafeDefinition("PACKAGE_VERSION");
+  if (result_version.empty())
+    {
+    result_version = "unknown";
+    }
+
   // Succeed if the version is suitable.
   return suitable;
 }

+ 5 - 1
Source/cmFindPackageCommand.h

@@ -98,7 +98,8 @@ private:
   bool CheckDirectory(std::string const& dir);
   bool FindConfigFile(std::string const& dir, std::string& file);
   bool CheckVersion(std::string const& config_file);
-  bool CheckVersionFile(std::string const& version_file);
+  bool CheckVersionFile(std::string const& version_file,
+                        std::string& result_version);
   bool SearchPrefix(std::string const& prefix);
   bool SearchFrameworkPrefix(std::string const& prefix_in);
   bool SearchAppBundlePrefix(std::string const& prefix_in);
@@ -137,6 +138,9 @@ private:
   std::vector<std::string> Names;
   std::vector<std::string> Configs;
   std::set<std::string> IgnoredPaths;
+
+  struct ConfigFileInfo { std::string filename; std::string version; };
+  std::vector<ConfigFileInfo> ConsideredConfigs;
 };
 
 #endif