CMakeDetermineVSServicePack.cmake 6.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187
  1. # - Includes a public function for assisting users in trying to determine the
  2. # Visual Studio service pack in use.
  3. #
  4. # Sets the passed in variable to one of the following values or an empty
  5. # string if unknown.
  6. # vc80
  7. # vc80sp1
  8. # vc90
  9. # vc90sp1
  10. # vc100
  11. # vc100sp1
  12. #
  13. # Usage:
  14. # ===========================
  15. #
  16. # if(MSVC)
  17. # include(CMakeDetermineVSServicePack)
  18. # DetermineVSServicePack( my_service_pack )
  19. #
  20. # if( my_service_pack )
  21. # message(STATUS "Detected: ${my_service_pack}")
  22. # endif()
  23. # endif()
  24. #
  25. # ===========================
  26. #=============================================================================
  27. # Copyright 2009-2011 Kitware, Inc.
  28. # Copyright 2009-2010 Philip Lowman <[email protected]>
  29. # Copyright 2010-2011 Aaron C. meadows <[email protected]>
  30. #
  31. # Distributed under the OSI-approved BSD License (the "License");
  32. # see accompanying file Copyright.txt for details.
  33. #
  34. # This software is distributed WITHOUT ANY WARRANTY; without even the
  35. # implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  36. # See the License for more information.
  37. #=============================================================================
  38. # (To distribute this file outside of CMake, substitute the full
  39. # License text for the above reference.)
  40. # [INTERNAL]
  41. # Please do not call this function directly
  42. function(_DetermineVSServicePackFromCompiler _OUT_VAR _cl_version)
  43. if (${_cl_version} VERSION_EQUAL "14.00.50727.42")
  44. set(_version "vc80")
  45. elseif(${_cl_version} VERSION_EQUAL "14.00.50727.762")
  46. set(_version "vc80sp1")
  47. elseif(${_cl_version} VERSION_EQUAL "15.00.21022.08")
  48. set(_version "vc90")
  49. elseif(${_cl_version} VERSION_EQUAL "15.00.30729.01")
  50. set(_version "vc90sp1")
  51. elseif(${_cl_version} VERSION_EQUAL "16.00.30319.01")
  52. set(_version "vc100")
  53. elseif(${_cl_version} VERSION_EQUAL "16.00.40219.01")
  54. set(_version "vc100sp1")
  55. else()
  56. set(_version "")
  57. endif()
  58. set(${_OUT_VAR} ${_version} PARENT_SCOPE)
  59. endfunction()
  60. ############################################################
  61. # [INTERNAL]
  62. # Please do not call this function directly
  63. function(_DetermineVSServicePack_FastCheckVersionWithCompiler _SUCCESS_VAR _VERSION_VAR)
  64. if(EXISTS ${CMAKE_CXX_COMPILER})
  65. execute_process(
  66. COMMAND ${CMAKE_CXX_COMPILER} /?
  67. ERROR_VARIABLE _output
  68. OUTPUT_QUIET
  69. )
  70. string(REGEX MATCH "Compiler Version [0-9]+.[0-9]+.[0-9]+.[0-9]+"
  71. _cl_version "${_output}")
  72. if(_cl_version)
  73. string(REGEX MATCHALL "[0-9]+"
  74. _cl_version_list "${_cl_version}")
  75. list(GET _cl_version_list 0 _major)
  76. list(GET _cl_version_list 1 _minor)
  77. list(GET _cl_version_list 2 _patch)
  78. list(GET _cl_version_list 3 _tweak)
  79. if("${_major}${_minor}" STREQUAL "${MSVC_VERSION}")
  80. set(_cl_version ${_major}.${_minor}.${_patch}.${_tweak})
  81. else()
  82. unset(_cl_version)
  83. endif()
  84. endif()
  85. if(_cl_version)
  86. set(${_SUCCESS_VAR} true PARENT_SCOPE)
  87. set(${_VERSION_VAR} ${_cl_version} PARENT_SCOPE)
  88. endif()
  89. endif()
  90. endfunction()
  91. ############################################################
  92. # [INTERNAL]
  93. # Please do not call this function directly
  94. function(_DetermineVSServicePack_CheckVersionWithTryCompile _SUCCESS_VAR _VERSION_VAR)
  95. file(WRITE "${CMAKE_BINARY_DIR}/return0.cc"
  96. "int main() { return 0; }\n")
  97. try_compile(
  98. _CompileResult
  99. "${CMAKE_BINARY_DIR}"
  100. "${CMAKE_BINARY_DIR}/return0.cc"
  101. OUTPUT_VARIABLE _output
  102. COPY_FILE "${CMAKE_BINARY_DIR}/return0.cc")
  103. file(REMOVE "${CMAKE_BINARY_DIR}/return0.cc")
  104. string(REGEX MATCH "Compiler Version [0-9]+.[0-9]+.[0-9]+.[0-9]+"
  105. _cl_version "${_output}")
  106. if(_cl_version)
  107. string(REGEX MATCHALL "[0-9]+"
  108. _cl_version_list "${_cl_version}")
  109. list(GET _cl_version_list 0 _major)
  110. list(GET _cl_version_list 1 _minor)
  111. list(GET _cl_version_list 2 _patch)
  112. list(GET _cl_version_list 3 _tweak)
  113. set(${_SUCCESS_VAR} true PARENT_SCOPE)
  114. set(${_VERSION_VAR} ${_major}.${_minor}.${_patch}.${_tweak} PARENT_SCOPE)
  115. endif()
  116. endfunction()
  117. ############################################################
  118. # [INTERNAL]
  119. # Please do not call this function directly
  120. function(_DetermineVSServicePack_CheckVersionWithTryRun _SUCCESS_VAR _VERSION_VAR)
  121. file(WRITE "${CMAKE_BINARY_DIR}/return0.cc"
  122. "#include <stdio.h>\n\nconst unsigned int CompilerVersion=_MSC_FULL_VER;\n\nint main(int argc, char* argv[])\n{\n int M( CompilerVersion/10000000);\n int m((CompilerVersion%10000000)/100000);\n int b(CompilerVersion%100000);\n\n printf(\"%d.%02d.%05d.01\",M,m,b);\n return 0;\n}\n")
  123. try_run(
  124. _RunResult
  125. _CompileResult
  126. "${CMAKE_BINARY_DIR}"
  127. "${CMAKE_BINARY_DIR}/return0.cc"
  128. RUN_OUTPUT_VARIABLE _runoutput
  129. )
  130. file(REMOVE "${CMAKE_BINARY_DIR}/return0.cc")
  131. string(REGEX MATCH "[0-9]+.[0-9]+.[0-9]+.[0-9]+"
  132. _cl_version "${_runoutput}")
  133. if(_cl_version)
  134. set(${_SUCCESS_VAR} true PARENT_SCOPE)
  135. set(${_VERSION_VAR} ${_cl_version} PARENT_SCOPE)
  136. endif()
  137. endfunction()
  138. #
  139. # A function to call to determine the Visual Studio service pack
  140. # in use. See documentation above.
  141. function(DetermineVSServicePack _pack)
  142. if(NOT DETERMINED_VS_SERVICE_PACK OR NOT ${_pack})
  143. _DetermineVSServicePack_FastCheckVersionWithCompiler(DETERMINED_VS_SERVICE_PACK _cl_version)
  144. if(NOT DETERMINED_VS_SERVICE_PACK)
  145. _DetermineVSServicePack_CheckVersionWithTryCompile(DETERMINED_VS_SERVICE_PACK _cl_version)
  146. if(NOT DETERMINED_VS_SERVICE_PACK)
  147. _DetermineVSServicePack_CheckVersionWithTryRun(DETERMINED_VS_SERVICE_PACK _cl_version)
  148. endif()
  149. endif()
  150. if(DETERMINED_VS_SERVICE_PACK)
  151. if(_cl_version)
  152. # Call helper function to determine VS version
  153. _DetermineVSServicePackFromCompiler(_sp "${_cl_version}")
  154. if(_sp)
  155. set(${_pack} ${_sp} CACHE INTERNAL
  156. "The Visual Studio Release with Service Pack")
  157. endif()
  158. endif()
  159. endif()
  160. endif()
  161. endfunction()