2017-05-25 14:33:16 +08:00
## # vcpkg_download_distfile
##
## Download and cache a file needed for this port.
##
2018-01-06 08:16:08 +08:00
## This helper should always be used instead of CMake's built-in `file(DOWNLOAD)` command.
##
2017-05-25 14:33:16 +08:00
## ## Usage
## ```cmake
## vcpkg_download_distfile(
## <OUT_VARIABLE>
## URLS <http://mainUrl> <http://mirror1>...
## FILENAME <output.zip>
## SHA512 <5981de...>
## )
## ```
## ## Parameters
## ### OUT_VARIABLE
## This variable will be set to the full path to the downloaded file. This can then immediately be passed in to [`vcpkg_extract_source_archive`](vcpkg_extract_source_archive.md) for sources.
##
## ### URLS
## A list of URLs to be consulted. They will be tried in order until one of the downloaded files successfully matches the SHA512 given.
##
## ### FILENAME
## The local name for the file. Files are shared between ports, so the file may need to be renamed to make it clearly attributed to this port and avoid conflicts.
##
## ### SHA512
## The expected hash for the file.
##
## If this doesn't match the downloaded version, the build will be terminated with a message describing the mismatch.
##
2017-12-30 06:21:18 +08:00
## ### SKIP_SHA512
## Skip SHA512 hash check for file.
##
2018-01-06 08:16:08 +08:00
## This switch is only valid when building with the `--head` command line flag.
##
2019-03-15 04:43:49 +08:00
## ### HEADERS
## A list of headers to append to the download request. This can be used for authentication during a download.
##
## Headers should be specified as "<header-name>: <header-value>".
##
2017-05-25 14:33:16 +08:00
## ## Notes
2018-01-06 08:16:08 +08:00
## The helper [`vcpkg_from_github`](vcpkg_from_github.md) should be used for downloading from GitHub projects.
2017-05-25 14:33:16 +08:00
##
## ## Examples
##
2018-01-06 08:16:08 +08:00
## * [apr](https://github.com/Microsoft/vcpkg/blob/master/ports/apr/portfile.cmake)
2017-05-25 14:33:16 +08:00
## * [fontconfig](https://github.com/Microsoft/vcpkg/blob/master/ports/fontconfig/portfile.cmake)
## * [openssl](https://github.com/Microsoft/vcpkg/blob/master/ports/openssl/portfile.cmake)
2016-09-19 11:50:08 +08:00
function ( vcpkg_download_distfile VAR )
2017-12-30 06:21:18 +08:00
set ( options SKIP_SHA512 )
2016-09-25 06:23:04 +08:00
set ( oneValueArgs FILENAME SHA512 )
2019-03-15 04:43:49 +08:00
set ( multipleValuesArgs URLS HEADERS )
2017-12-30 06:21:18 +08:00
cmake_parse_arguments ( vcpkg_download_distfile "${options}" "${oneValueArgs}" "${multipleValuesArgs}" ${ ARGN } )
2017-11-03 09:54:10 +08:00
2017-12-21 19:47:02 +08:00
if ( NOT DEFINED vcpkg_download_distfile_URLS )
message ( FATAL_ERROR "vcpkg_download_distfile requires a URLS argument." )
endif ( )
if ( NOT DEFINED vcpkg_download_distfile_FILENAME )
message ( FATAL_ERROR "vcpkg_download_distfile requires a FILENAME argument." )
endif ( )
2018-01-14 11:49:04 +08:00
if ( NOT _VCPKG_INTERNAL_NO_HASH_CHECK )
if ( vcpkg_download_distfile_SKIP_SHA512 AND NOT VCPKG_USE_HEAD_VERSION )
message ( FATAL_ERROR "vcpkg_download_distfile only allows SKIP_SHA512 when building with --head" )
endif ( )
if ( NOT vcpkg_download_distfile_SKIP_SHA512 AND NOT DEFINED vcpkg_download_distfile_SHA512 )
message ( FATAL_ERROR "vcpkg_download_distfile requires a SHA512 argument. If you do not know the SHA512, add it as 'SHA512 0' and re-run this command." )
endif ( )
if ( vcpkg_download_distfile_SKIP_SHA512 AND DEFINED vcpkg_download_distfile_SHA512 )
message ( FATAL_ERROR "vcpkg_download_distfile must not be passed both SHA512 and SKIP_SHA512." )
endif ( )
2017-12-21 19:47:02 +08:00
endif ( )
2016-09-24 21:23:18 +08:00
set ( downloaded_file_path ${ DOWNLOADS } / ${ vcpkg_download_distfile_FILENAME } )
2017-11-03 09:54:10 +08:00
set ( download_file_path_part "${DOWNLOADS}/temp/${vcpkg_download_distfile_FILENAME}" )
2018-08-31 06:57:37 +08:00
# Works around issue #3399
if ( IS_DIRECTORY "${DOWNLOADS}/temp" )
file ( REMOVE_RECURSE "${DOWNLOADS}/temp0" )
file ( RENAME "${DOWNLOADS}/temp" "${DOWNLOADS}/temp0" )
file ( REMOVE_RECURSE "${DOWNLOADS}/temp0" )
endif ( )
2017-11-03 09:54:10 +08:00
file ( MAKE_DIRECTORY "${DOWNLOADS}/temp" )
2016-09-25 06:36:50 +08:00
2018-03-02 03:10:19 +08:00
function ( test_hash FILE_PATH FILE_KIND CUSTOM_ERROR_ADVICE )
2018-01-06 08:16:08 +08:00
if ( _VCPKG_INTERNAL_NO_HASH_CHECK )
# When using the internal hash skip, do not output an explicit message.
return ( )
endif ( )
if ( vcpkg_download_distfile_SKIP_SHA512 )
2018-03-02 03:10:19 +08:00
message ( STATUS "Skipping hash check for ${FILE_PATH}." )
2017-11-04 05:34:08 +08:00
return ( )
endif ( )
2018-03-02 03:10:19 +08:00
file ( SHA512 ${ FILE_PATH } FILE_HASH )
2018-06-27 12:48:29 +08:00
if ( NOT FILE_HASH STREQUAL vcpkg_download_distfile_SHA512 )
2016-09-19 11:50:08 +08:00
message ( FATAL_ERROR
2016-09-24 21:23:18 +08:00
" \ n F i l e d o e s n o t h a v e e x p e c t e d h a s h : \ n "
2018-03-02 03:10:19 +08:00
" F i l e p a t h : [ $ { F I L E _ P A T H } ] \ n "
2016-09-25 06:24:38 +08:00
" E x p e c t e d h a s h : [ $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ S H A 5 1 2 } ] \ n "
" A c t u a l h a s h : [ $ { F I L E _ H A S H } ] \ n "
2016-09-25 06:36:50 +08:00
" $ { C U S T O M _ E R R O R _ A D V I C E } \ n " )
2016-09-19 11:50:08 +08:00
endif ( )
2016-09-25 06:36:50 +08:00
endfunction ( )
2018-06-27 12:48:29 +08:00
if ( EXISTS "${downloaded_file_path}" )
2016-09-25 06:36:50 +08:00
message ( STATUS "Using cached ${downloaded_file_path}" )
2018-03-02 03:10:19 +08:00
test_hash ( "${downloaded_file_path}" "cached file" "Please delete the file and retry if this file should be downloaded again." )
2016-09-19 11:50:08 +08:00
else ( )
2017-05-03 11:34:11 +08:00
if ( _VCPKG_NO_DOWNLOADS )
message ( FATAL_ERROR "Downloads are disabled, but '${downloaded_file_path}' does not exist." )
endif ( )
2016-09-24 21:23:18 +08:00
# Tries to download the file.
2018-03-07 17:57:16 +08:00
list ( GET vcpkg_download_distfile_URLS 0 SAMPLE_URL )
2018-06-27 12:48:29 +08:00
if ( _VCPKG_DOWNLOAD_TOOL STREQUAL "ARIA2" AND NOT SAMPLE_URL MATCHES "aria2" )
2018-03-07 17:57:16 +08:00
vcpkg_find_acquire_program ( "ARIA2" )
message ( STATUS "Downloading ${vcpkg_download_distfile_FILENAME}..." )
2019-03-15 04:43:49 +08:00
if ( vcpkg_download_distfile_HEADERS )
foreach ( header ${ vcpkg_download_distfile_HEADERS } )
list ( APPEND request_headers "--header=${header}" )
endforeach ( )
endif ( )
2019-08-29 02:47:17 +08:00
_execute_process (
2018-03-07 17:57:16 +08:00
C O M M A N D $ { A R I A 2 } $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ U R L S }
- o t e m p / $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ F I L E N A M E }
- l d o w n l o a d - $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ F I L E N A M E } - d e t a i l e d . l o g
2019-03-15 04:43:49 +08:00
$ { r e q u e s t _ h e a d e r s }
2018-03-07 17:57:16 +08:00
O U T P U T _ F I L E d o w n l o a d - $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ F I L E N A M E } - o u t . l o g
E R R O R _ F I L E d o w n l o a d - $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ F I L E N A M E } - e r r . l o g
R E S U L T _ V A R I A B L E e r r o r _ c o d e
W O R K I N G _ D I R E C T O R Y $ { D O W N L O A D S }
)
if ( NOT "${error_code}" STREQUAL "0" )
message ( STATUS
" D o w n l o a d i n g $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ F I L E N A M E } . . . F a i l e d . \ n "
" E x i t C o d e : $ { e r r o r _ c o d e } \ n "
" S e e l o g s f o r m o r e i n f o r m a t i o n : \ n "
" $ { D O W N L O A D S } / d o w n l o a d - $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ F I L E N A M E } - o u t . l o g \ n "
" $ { D O W N L O A D S } / d o w n l o a d - $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ F I L E N A M E } - e r r . l o g \ n "
" $ { D O W N L O A D S } / d o w n l o a d - $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ F I L E N A M E } - d e t a i l e d . l o g \ n "
)
2016-09-24 21:23:18 +08:00
set ( download_success 0 )
else ( )
2018-03-15 13:17:54 +08:00
file ( REMOVE
$ { D O W N L O A D S } / d o w n l o a d - $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ F I L E N A M E } - o u t . l o g
$ { D O W N L O A D S } / d o w n l o a d - $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ F I L E N A M E } - e r r . l o g
$ { D O W N L O A D S } / d o w n l o a d - $ { v c p k g _ d o w n l o a d _ d i s t f i l e _ F I L E N A M E } - d e t a i l e d . l o g
)
2016-09-24 21:23:18 +08:00
set ( download_success 1 )
endif ( )
2018-03-07 17:57:16 +08:00
else ( )
foreach ( url IN LISTS vcpkg_download_distfile_URLS )
message ( STATUS "Downloading ${url}..." )
2019-03-15 04:43:49 +08:00
if ( vcpkg_download_distfile_HEADERS )
foreach ( header ${ vcpkg_download_distfile_HEADERS } )
list ( APPEND request_headers HTTPHEADER ${ header } )
endforeach ( )
endif ( )
file ( DOWNLOAD ${ url } "${download_file_path_part}" STATUS download_status ${ request_headers } )
2018-03-07 17:57:16 +08:00
list ( GET download_status 0 status_code )
if ( NOT "${status_code}" STREQUAL "0" )
message ( STATUS "Downloading ${url}... Failed. Status: ${download_status}" )
set ( download_success 0 )
else ( )
set ( download_success 1 )
break ( )
endif ( )
endforeach ( url )
endif ( )
2016-09-24 21:23:18 +08:00
2017-10-12 23:22:50 +08:00
if ( NOT download_success )
2016-09-24 21:23:18 +08:00
message ( FATAL_ERROR
2018-03-02 03:10:19 +08:00
" \ n "
2016-09-24 21:23:18 +08:00
" F a i l e d t o d o w n l o a d f i l e . \ n "
2018-03-02 03:10:19 +08:00
" I f y o u u s e a p r o x y , p l e a s e s e t t h e H T T P S _ P R O X Y a n d H T T P _ P R O X Y e n v i r o n m e n t \ n "
" v a r i a b l e s t o \ " h t t p s : / / u s e r : p a s s w o r d @ y o u r - p r o x y - i p - a d d r e s s : p o r t / \ " . \ n "
" O t h e r w i s e , p l e a s e s u b m i t a n i s s u e a t h t t p s : / / g i t h u b . c o m / M i c r o s o f t / v c p k g / i s s u e s \ n " )
2016-09-24 21:23:18 +08:00
else ( )
2018-03-02 03:10:19 +08:00
test_hash ( "${download_file_path_part}" "downloaded file" "The file may have been corrupted in transit. This can be caused by proxies. If you use a proxy, please set the HTTPS_PROXY and HTTP_PROXY environment variables to \" https://user:password@your-proxy-ip-address:port/\ ".\n" )
get_filename_component ( downloaded_file_dir "${downloaded_file_path}" DIRECTORY )
file ( MAKE_DIRECTORY "${downloaded_file_dir}" )
file ( RENAME ${ download_file_path_part } ${ downloaded_file_path } )
2016-09-24 21:23:18 +08:00
endif ( )
2016-09-19 11:50:08 +08:00
endif ( )
2016-09-24 21:23:18 +08:00
set ( ${ VAR } ${ downloaded_file_path } PARENT_SCOPE )
2016-09-19 11:50:08 +08:00
endfunction ( )