FindWindowsSDK.cmake 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323
  1. # - Find the Windows SDK aka Platform SDK
  2. #
  3. # Relevant Wikipedia article: http://en.wikipedia.org/wiki/Microsoft_Windows_SDK
  4. #
  5. # Variables:
  6. # WINDOWSSDK_FOUND - if any version of the windows or platform SDK was found that is usable with the current version of visual studio
  7. # WINDOWSSDK_LATEST_DIR
  8. # WINDOWSSDK_LATEST_NAME
  9. # WINDOWSSDK_FOUND_PREFERENCE - if we found an entry indicating a "preferred" SDK listed for this visual studio version
  10. # WINDOWSSDK_PREFERRED_DIR
  11. # WINDOWSSDK_PREFERRED_NAME
  12. #
  13. # WINDOWSSDK_DIRS - contains no duplicates, ordered most recent first.
  14. # WINDOWSSDK_PREFERRED_FIRST_DIRS - contains no duplicates, ordered with preferred first, followed by the rest in descending recency
  15. #
  16. # Functions:
  17. # windowssdk_name_lookup(<directory> <output variable>) - Find the name corresponding with the SDK directory you pass in, or
  18. # NOTFOUND if not recognized. Your directory must be one of WINDOWSSDK_DIRS for this to work.
  19. #
  20. # get_windowssdk_from_component(<file or dir> <output variable>) - Given a library or include dir,
  21. # find the Windows SDK root dir corresponding to it, or NOTFOUND if unrecognized.
  22. #
  23. # get_windowssdk_library_dirs(<directory> <output variable>) - Find the architecture-appropriate
  24. # library directories corresponding to the SDK directory you pass in (or NOTFOUND if none)
  25. #
  26. # get_windowssdk_include_dirs(<directory> <output variable>) - Find the
  27. # include directories corresponding to the SDK directory you pass in (or NOTFOUND if none)
  28. #
  29. # Requires these CMake modules:
  30. # FindPackageHandleStandardArgs (known included with CMake >=2.6.2)
  31. #
  32. # Original Author:
  33. # 2012 Ryan Pavlik <rpavlik@iastate.edu> <abiryan@ryand.net>
  34. # http://academic.cleardefinition.com
  35. # Iowa State University HCI Graduate Program/VRAC
  36. #
  37. # Copyright Iowa State University 2012.
  38. # Distributed under the Boost Software License, Version 1.0.
  39. # (See accompanying file LICENSE_1_0.txt or copy at
  40. # http://www.boost.org/LICENSE_1_0.txt)
  41. set(_preferred_sdk_dirs)
  42. set(_win_sdk_dirs)
  43. set(_win_sdk_versanddirs)
  44. if(MSVC_VERSION GREATER 1310) # Newer than VS .NET/VS Toolkit 2003
  45. # Environment variable for SDK dir
  46. if(EXISTS "$ENV{WindowsSDKDir}" AND (NOT "$ENV{WindowsSDKDir}" STREQUAL ""))
  47. message(STATUS "Got $ENV{WindowsSDKDir} - Windows/Platform SDK directories: ${_win_sdk_dirs}")
  48. list(APPEND _preferred_sdk_dirs "$ENV{WindowsSDKDir}")
  49. endif()
  50. if(MSVC_VERSION LESS 1600)
  51. # Per-user current Windows SDK for VS2005/2008
  52. get_filename_component(_sdkdir
  53. "[HKEY_CURRENT_USER\\Software\\Microsoft\\Microsoft SDKs\\Windows;CurrentInstallFolder]"
  54. ABSOLUTE)
  55. if(EXISTS "${_sdkdir}")
  56. list(APPEND _preferred_sdk_dirs "${_sdkdir}")
  57. endif()
  58. # System-wide current Windows SDK for VS2005/2008
  59. get_filename_component(_sdkdir
  60. "[HKEY_LOCAL_MACHINE\\SOFTWARE\\Microsoft\\Microsoft SDKs\\Windows;CurrentInstallFolder]"
  61. ABSOLUTE)
  62. if(EXISTS "${_sdkdir}")
  63. list(APPEND _preferred_sdk_dirs "${_sdkdir}")
  64. endif()
  65. endif()
  66. if(MSVC_VERSION LESS 1700)
  67. # VC 10 and older has broad target support
  68. set(_winsdk_vistaonly)
  69. else()
  70. # VC 11 by default targets Vista and later only, so we can add a few more SDKs that (might?) only work on vista+
  71. if("${CMAKE_VS_PLATFORM_TOOLSET}" MATCHES "_xp")
  72. # This is the XP-compatible v110 toolset
  73. elseif("${CMAKE_VS_PLATFORM_TOOLSET}" STREQUAL "v100")
  74. # This is the VS2010 toolset
  75. else()
  76. if(NOT WINDOWSSDK_FOUND AND NOT WindowsSDK_FIND_QUIETLY)
  77. message(STATUS "FindWindowsSDK: Detected Visual Studio 2012 or newer, not using the _xp toolset variant: including SDK versions that drop XP support in search!")
  78. endif()
  79. # These versions have no XP (and possibly Vista pre-SP1) support
  80. set(_winsdk_vistaonly)
  81. if(NOT MSVC_VERSION LESS 1800)
  82. list(APPEND _winsdk_vistaonly
  83. # Windows Software Development Kit (SDK) for Windows 8.1
  84. # http://msdn.microsoft.com/en-gb/windows/desktop/bg162891
  85. v8.1)
  86. endif()
  87. list(APPEND _winsdk_vistaonly
  88. # Included in Visual Studio 2012
  89. v8.0A
  90. # Microsoft Windows SDK for Windows 8 and .NET Framework 4.5
  91. # This is the first version to also include the DirectX SDK
  92. # http://msdn.microsoft.com/en-US/windows/desktop/hh852363.aspx
  93. v8.0
  94. # Microsoft Windows SDK for Windows 7 and .NET Framework 4
  95. # http://www.microsoft.com/downloads/en/details.aspx?FamilyID=6b6c21d2-2006-4afa-9702-529fa782d63b
  96. v7.1
  97. )
  98. endif()
  99. endif()
  100. foreach(_winsdkver
  101. ${_winsdk_vistaonly}
  102. # Included in Visual Studio 2013
  103. # Includes the v120_xp toolset
  104. v8.1A
  105. # Included with VS 2012 Update 1 or later
  106. # Introduces v110_xp toolset
  107. v7.1A
  108. # Included with VS 2010
  109. v7.0A
  110. # Windows SDK for Windows 7 and .NET Framework 3.5 SP1
  111. # Works with VC9
  112. #http://www.microsoft.com/en-us/download/details.aspx?id=18950
  113. v7.0
  114. # Two versions call themselves "v6.1":
  115. # Older:
  116. # Windows Vista Update & .NET 3.0 SDK
  117. # http://www.microsoft.com/en-us/download/details.aspx?id=14477
  118. # Newer:
  119. # Windows Server 2008 & .NET 3.5 SDK
  120. # may have broken VS9SP1? they recommend v7.0 instead, or a KB...
  121. # http://www.microsoft.com/en-us/download/details.aspx?id=24826
  122. v6.1
  123. # Included in VS 2008
  124. v6.0A
  125. # Microsoft Windows Software Development Kit for Windows Vista and .NET Framework 3.0 Runtime Components
  126. # http://blogs.msdn.com/b/stanley/archive/2006/11/08/microsoft-windows-software-development-kit-for-windows-vista-and-net-framework-3-0-runtime-components.aspx
  127. v6.0)
  128. get_filename_component(_sdkdir
  129. "[HKEY_LOCAL_MACHINE\\SOFTWARE\\Microsoft\\Microsoft SDKs\\Windows\\${_winsdkver};InstallationFolder]"
  130. ABSOLUTE)
  131. if(EXISTS "${_sdkdir}")
  132. list(APPEND _win_sdk_dirs "${_sdkdir}")
  133. list(APPEND
  134. _win_sdk_versanddirs
  135. "Windows SDK ${_winsdkver}"
  136. "${_sdkdir}")
  137. endif()
  138. endforeach()
  139. endif()
  140. if(MSVC_VERSION GREATER 1200)
  141. foreach(_platformsdkinfo
  142. "D2FF9F89-8AA2-4373-8A31-C838BF4DBBE1_Microsoft Platform SDK for Windows Server 2003 R2"
  143. "8F9E5EF3-A9A5-491B-A889-C58EFFECE8B3_Microsoft Platform SDK for Windows Server 2003 SP1")
  144. string(SUBSTRING "${_platformsdkinfo}" 0 36 _platformsdkguid)
  145. string(SUBSTRING "${_platformsdkinfo}" 37 -1 _platformsdkname)
  146. foreach(HIVE HKEY_LOCAL_MACHINE HKEY_CURRENT_USER)
  147. get_filename_component(_sdkdir
  148. "[${HIVE}\\SOFTWARE\\Microsoft\\MicrosoftSDK\\InstalledSDKs\\${_platformsdkguid};Install Dir]"
  149. ABSOLUTE)
  150. if(EXISTS "${_sdkdir}")
  151. list(APPEND _win_sdk_dirs "${_sdkdir}")
  152. list(APPEND _win_sdk_versanddirs "${_platformsdkname}" "${_sdkdir}")
  153. endif()
  154. endforeach()
  155. endforeach()
  156. endif()
  157. set(_win_sdk_versanddirs
  158. "${_win_sdk_versanddirs}"
  159. CACHE
  160. INTERNAL
  161. "mapping between windows sdk version locations and names"
  162. FORCE)
  163. function(windowssdk_name_lookup _dir _outvar)
  164. list(FIND _win_sdk_versanddirs "${_dir}" _diridx)
  165. math(EXPR _nameidx "${_diridx} - 1")
  166. if(${_nameidx} GREATER -1)
  167. list(GET _win_sdk_versanddirs ${_nameidx} _sdkname)
  168. else()
  169. set(_sdkname "NOTFOUND")
  170. endif()
  171. set(${_outvar} "${_sdkname}" PARENT_SCOPE)
  172. endfunction()
  173. if(_win_sdk_dirs)
  174. # Remove duplicates
  175. list(REMOVE_DUPLICATES _win_sdk_dirs)
  176. list(GET _win_sdk_dirs 0 WINDOWSSDK_LATEST_DIR)
  177. windowssdk_name_lookup("${WINDOWSSDK_LATEST_DIR}"
  178. WINDOWSSDK_LATEST_NAME)
  179. set(WINDOWSSDK_DIRS ${_win_sdk_dirs})
  180. endif()
  181. if(_preferred_sdk_dirs)
  182. list(GET _preferred_sdk_dirs 0 WINDOWSSDK_PREFERRED_DIR)
  183. windowssdk_name_lookup("${WINDOWSSDK_LATEST_DIR}"
  184. WINDOWSSDK_PREFERRED_NAME)
  185. set(WINDOWSSDK_PREFERRED_FIRST_DIRS
  186. ${_preferred_sdk_dirs}
  187. ${_win_sdk_dirs})
  188. list(REMOVE_DUPLICATES WINDOWSSDK_PREFERRED_FIRST_DIRS)
  189. set(WINDOWSSDK_FOUND_PREFERENCE ON)
  190. # In case a preferred dir was found that isn't found otherwise
  191. #set(WINDOWSSDK_DIRS ${WINDOWSSDK_DIRS} ${WINDOWSSDK_PREFERRED_FIRST_DIRS})
  192. #list(REMOVE_DUPLICATES WINDOWSSDK_DIRS)
  193. else()
  194. set(WINDOWSSDK_PREFERRED_DIR "${WINDOWSSDK_LATEST_DIR}")
  195. set(WINDOWSSDK_PREFERRED_NAME "${WINDOWSSDK_LATEST_NAME}")
  196. set(WINDOWSSDK_PREFERRED_FIRST_DIRS ${WINDOWSSDK_DIRS})
  197. set(WINDOWSSDK_FOUND_PREFERENCE OFF)
  198. endif()
  199. include(FindPackageHandleStandardArgs)
  200. find_package_handle_standard_args(WindowsSDK
  201. "No compatible version of the Windows SDK or Platform SDK found."
  202. WINDOWSSDK_DIRS)
  203. if(WINDOWSSDK_FOUND)
  204. if(NOT _winsdk_remembered_dirs STREQUAL WINDOWSSDK_DIRS)
  205. set(_winsdk_remembered_dirs
  206. "${WINDOWSSDK_DIRS}"
  207. CACHE
  208. INTERNAL
  209. ""
  210. FORCE)
  211. if(NOT WindowsSDK_FIND_QUIETLY)
  212. foreach(_sdkdir ${WINDOWSSDK_DIRS})
  213. windowssdk_name_lookup("${_sdkdir}" _sdkname)
  214. message(STATUS " - Found ${_sdkname} at ${_sdkdir}")
  215. endforeach()
  216. endif()
  217. endif()
  218. # Internal: Architecture-appropriate library directory names.
  219. if("${CMAKE_VS_PLATFORM_NAME}" STREQUAL "ARM")
  220. set(_winsdk_archbare /arm) # what the architecture used to be called in oldest SDKs
  221. set(_winsdk_arch arm) # what the architecture used to be called
  222. set(_winsdk_arch8 arm) # what the WDK for Win8+ calls this architecture
  223. else()
  224. if(CMAKE_SIZEOF_VOID_P MATCHES "8")
  225. set(_winsdk_archbare /x64) # what the architecture used to be called in oldest SDKs
  226. set(_winsdk_arch amd64) # what the architecture used to be called
  227. set(_winsdk_arch8 x64) # what the WDK for Win8+ calls this architecture
  228. else()
  229. set(_winsdk_archbare ) # what the architecture used to be called in oldest SDKs
  230. set(_winsdk_arch i386) # what the architecture used to be called
  231. set(_winsdk_arch8 x86) # what the WDK for Win8+ calls this architecture
  232. endif()
  233. endif()
  234. function(get_windowssdk_from_component _component _var)
  235. get_filename_component(_component "${_component}" ABSOLUTE)
  236. file(TO_CMAKE_PATH "${_component}" _component)
  237. foreach(_sdkdir ${WINDOWSSDK_DIRS})
  238. get_filename_component(_sdkdir "${_sdkdir}" ABSOLUTE)
  239. string(LENGTH "${_sdkdir}" _sdklen)
  240. file(RELATIVE_PATH _rel "${_sdkdir}" "${_component}")
  241. # If we don't have any "parent directory" items...
  242. if(NOT "${_rel}" MATCHES "[.][.]")
  243. set(${_var} "${_sdkdir}" PARENT_SCOPE)
  244. return()
  245. endif()
  246. endforeach()
  247. # Fail.
  248. set(${_var} "NOTFOUND" PARENT_SCOPE)
  249. endfunction()
  250. function(get_windowssdk_library_dirs _winsdk_dir _var)
  251. set(_result)
  252. foreach(_suffix
  253. "lib${_winsdk_archbare}" # SDKs like 7.1A
  254. "lib/w2k/${_winsdk_arch}" # Win2k min requirement
  255. "lib/wxp/${_winsdk_arch}" # WinXP min requirement
  256. "lib/wnet/${_winsdk_arch}" # Win Server 2003 min requirement
  257. "lib/wlh/${_winsdk_arch}" # Win Vista ("Long Horn") min requirement
  258. "lib/wlh/um/${_winsdk_arch8}" # Win Vista ("Long Horn") min requirement
  259. "lib/win7/${_winsdk_arch}" # Win 7 min requirement
  260. "lib/win7/um/${_winsdk_arch8}" # Win 7 min requirement
  261. "lib/win8/um/${_winsdk_arch8}" # Win 8 min requirement
  262. "lib/win8/km/${_winsdk_arch8}" # Win 8 min requirement
  263. "lib/winv6.3/km/${_winsdk_arch8}" # Win 8.1 min requirement
  264. "lib/winv6.3/um/${_winsdk_arch8}" # Win 8.1 min requirement
  265. )
  266. # Check to see if a library actually exists here.
  267. file(GLOB _libs "${_winsdk_dir}/${_suffix}/*.lib")
  268. if(_libs)
  269. list(APPEND _result "${_winsdk_dir}/${_suffix}")
  270. endif()
  271. endforeach()
  272. if(NOT _result)
  273. set(_result NOTFOUND)
  274. endif()
  275. set(${_var} ${_result} PARENT_SCOPE)
  276. endfunction()
  277. function(get_windowssdk_include_dirs _winsdk_dir _var)
  278. set(_result)
  279. foreach(_suffix
  280. "Include"
  281. "Include/shared"
  282. "Include/um"
  283. "Include/winrt"
  284. "Include/km"
  285. "Include/wdf"
  286. )
  287. # Check to see if a header file actually exists here.
  288. file(GLOB _headers "${_winsdk_dir}/${_suffix}/*.h")
  289. if(_headers)
  290. list(APPEND _result "${_winsdk_dir}/${_suffix}")
  291. endif()
  292. endforeach()
  293. if(NOT _result)
  294. set(_result NOTFOUND)
  295. endif()
  296. set(${_var} ${_result} PARENT_SCOPE)
  297. endfunction()
  298. endif()