1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 535 536 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566 567 568 569 570 571 572 573 574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647 648 649 650 651 652 653 654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714 715 716 717 718 719 720 721 722 723 724 725 726 727 728 729 730 731 732 733 734 735 736 737 738 739 740 741 742 743 744 745 746 747 748 749 750 751 752 753 754 755 756 757 758 759 760 761 762 763 764 765 766 767 768 769 770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790 791 792 793 794 795 796 797 798 799 800 801 802 803 804 805 806 807 808 809 810 811 812 813 814 815 816 817 818 819 820 821 822 823 824 825 826 827 828 829 830 831 832 833 834 835 836 837 838 839 840 841
|
#[=======================================================================[.rst:
FindRust
--------
Find Rust
This module finds an installed rustc compiler and the cargo build tool. If Rust
is managed by rustup it determines the available toolchains and returns a
concrete Rust version, not a rustup proxy.
#]=======================================================================]
cmake_minimum_required(VERSION 3.12)
# search for Cargo here and set up a bunch of cool flags and stuff
include(FindPackageHandleStandardArgs)
list(APPEND CMAKE_MESSAGE_CONTEXT "FindRust")
# Print error message and return. Should not be used from inside functions
macro(_findrust_failed)
if("${Rust_FIND_REQUIRED}")
message(FATAL_ERROR ${ARGN})
elseif(NOT "${Rust_FIND_QUIETLY}")
message(WARNING ${ARGN})
endif()
set(Rust_FOUND "")
return()
endmacro()
# Checks if the actual version of a Rust toolchain matches the VERSION requirements specified in find_package.
function(_findrust_version_ok ACTUAL_VERSION OUT_IS_OK)
if(DEFINED Rust_FIND_VERSION_RANGE)
if(Rust_FIND_VERSION_RANGE_MAX STREQUAL "INCLUDE")
set(COMPARSION_OPERATOR "VERSION_LESS_EQUAL")
elseif(Rust_FIND_VERSION_RANGE_MAX STREQUAL "EXCLUDE")
set(COMPARSION_OPERATOR "VERSION_LESS")
else()
message(FATAL_ERROR "Unexpected value in `<PackageName>_FIND_VERSION_RANGE_MAX`: "
"`${Rust_FIND_VERSION_RANGE_MAX}`.")
endif()
if(("${ACTUAL_VERSION}" VERSION_GREATER_EQUAL "${Rust_FIND_VERSION_RANGE_MIN}")
AND
( "${ACTUAL_VERSION}" ${COMPARSION_OPERATOR} "${Rust_FIND_VERSION_RANGE_MAX}" )
)
set("${OUT_IS_OK}" TRUE PARENT_SCOPE)
else()
set("${OUT_IS_OK}" FALSE PARENT_SCOPE)
endif()
elseif(DEFINED Rust_FIND_VERSION)
if(Rust_VERSION_EXACT)
set(COMPARISON_OPERATOR VERSION_EQUAL)
else()
set(COMPARISON_OPERATOR VERSION_GREATER_EQUAL)
endif()
if(_TOOLCHAIN_${_TOOLCHAIN_SELECTED}_VERSION "${COMPARISON_OPERATOR}" Rust_FIND_VERSION)
set("${OUT_IS_OK}" TRUE PARENT_SCOPE)
else()
set("${OUT_IS_OK}" FALSE PARENT_SCOPE)
endif()
else()
# if no VERSION requirement was specified, the version is always okay.
set("${OUT_IS_OK}" TRUE PARENT_SCOPE)
endif()
endfunction()
function(_corrosion_strip_target_triple input_triple_or_path output_triple)
# If the target_triple is a path to a custom target specification file, then strip everything
# except the filename from `target_triple`.
get_filename_component(target_triple_ext "${input_triple_or_path}" EXT)
set(target_triple "${input_triple_or_path}")
if(target_triple_ext)
if(target_triple_ext STREQUAL ".json")
get_filename_component(target_triple "${input_triple_or_path}" NAME_WE)
endif()
endif()
set(${output_triple} "${target_triple}" PARENT_SCOPE)
endfunction()
function(_corrosion_parse_target_triple target_triple out_arch out_vendor out_os out_env)
_corrosion_strip_target_triple(${target_triple} target_triple)
# The vendor part may be left out from the target triple, and since `env` is also optional,
# we determine if vendor is present by matching against a list of known vendors.
set(known_vendors
"apple"
"esp[a-z0-9]*" # espressif, e.g. riscv32imc-esp-espidf or xtensa-esp32s3-none-elf
"fortanix"
"kmc"
"pc"
"nintendo"
"nvidia"
"openwrt"
"alpine"
"chimera"
"unikraft"
"unknown"
"uwp" # aarch64-uwp-windows-msvc
"wrs" # e.g. aarch64-wrs-vxworks
"sony"
"sun"
)
# todo: allow users to add additional vendors to the list via a cmake variable.
list(JOIN known_vendors "|" known_vendors_joined)
# vendor is optional - We detect if vendor is present by matching against a known list of
# vendors. The next field is the OS, which we assume to always be present, while the last field
# is again optional and contains the environment.
string(REGEX MATCH
"^([a-z0-9_\.]+)-((${known_vendors_joined})-)?([a-z0-9_]+)(-([a-z0-9_]+))?$"
whole_match
"${target_triple}"
)
if((NOT whole_match) AND (NOT CORROSION_NO_WARN_PARSE_TARGET_TRIPLE_FAILED))
message(WARNING "Failed to parse target-triple `${target_triple}`."
"Corrosion determines some information about the output artifacts based on OS "
"specified in the Rust target-triple.\n"
"Currently this is relevant for windows and darwin (mac) targets, since file "
"extensions differ.\n"
"Note: If you are targeting a different OS you can suppress this warning by"
" setting the CMake cache variable "
"`CORROSION_NO_WARN_PARSE_TARGET_TRIPLE_FAILED`."
"Please consider opening an issue on github if you you need to add a new vendor to the list."
)
endif()
message(DEBUG "Parsed Target triple: arch: ${CMAKE_MATCH_1}, vendor: ${CMAKE_MATCH_3}, "
"OS: ${CMAKE_MATCH_4}, env: ${CMAKE_MATCH_6}")
set("${out_arch}" "${CMAKE_MATCH_1}" PARENT_SCOPE)
set("${out_vendor}" "${CMAKE_MATCH_3}" PARENT_SCOPE)
set("${out_os}" "${CMAKE_MATCH_4}" PARENT_SCOPE)
set("${out_env}" "${CMAKE_MATCH_6}" PARENT_SCOPE)
endfunction()
function(_corrosion_determine_libs_new target_triple out_libs out_flags)
set(package_dir "${CMAKE_BINARY_DIR}/corrosion/required_libs")
# Cleanup on reconfigure to get a cleans state (in case we change something in the future)
file(REMOVE_RECURSE "${package_dir}")
file(MAKE_DIRECTORY "${package_dir}")
set(manifest "[package]\nname = \"required_libs\"\nedition = \"2018\"\nversion = \"0.1.0\"\n")
string(APPEND manifest "\n[lib]\ncrate-type=[\"staticlib\"]\npath = \"lib.rs\"\n")
string(APPEND manifest "\n[workspace]\n")
file(WRITE "${package_dir}/Cargo.toml" "${manifest}")
file(WRITE "${package_dir}/lib.rs" "pub fn add(left: usize, right: usize) -> usize {left + right}\n")
execute_process(
COMMAND ${CMAKE_COMMAND} -E env
"CARGO_BUILD_RUSTC=${Rust_COMPILER_CACHED}"
${Rust_CARGO_CACHED} rustc --verbose --color never --target=${target_triple} -- --print=native-static-libs
WORKING_DIRECTORY "${CMAKE_BINARY_DIR}/corrosion/required_libs"
RESULT_VARIABLE cargo_build_result
ERROR_VARIABLE cargo_build_error_message
)
if(cargo_build_result)
message(DEBUG "Determining required native libraries - failed: ${cargo_build_result}.")
message(TRACE "The cargo build error was: ${cargo_build_error_message}")
message(DEBUG "Note: This is expected for Rust targets without std support")
return()
else()
# The pattern starts with `native-static-libs:` and goes to the end of the line.
if(cargo_build_error_message MATCHES "native-static-libs: ([^\r\n]+)\r?\n")
string(REPLACE " " ";" "libs_list" "${CMAKE_MATCH_1}")
set(stripped_lib_list "")
set(flag_list "")
set(was_last_framework OFF)
foreach(lib ${libs_list})
# merge -framework;lib -> "-framework lib" as CMake does de-duplication of link libraries, and -framework prefix is required
if (lib STREQUAL "-framework")
set(was_last_framework ON)
continue()
endif()
if (was_last_framework)
list(APPEND stripped_lib_list "-framework ${lib}")
set(was_last_framework OFF)
continue()
endif()
# Flags start with / for MSVC
if (lib MATCHES "^/" AND ${target_triple} MATCHES "msvc$")
# Windows GNU uses the compiler to invoke the linker, so -Wl, prefix is needed
# https://gitlab.kitware.com/cmake/cmake/-/blob/9bed4f4d817f139f0c2e050d7420e1e247949fe4/Modules/Platform/Windows-GNU.cmake#L156
if (CMAKE_CXX_COMPILER_FRONTEND_VARIANT STREQUAL "GNU")
list(APPEND flag_list "-Wl,${lib}")
else()
list(APPEND flag_list "${lib}")
endif()
else()
# Strip leading `-l` (unix) and potential .lib suffix (windows)
string(REGEX REPLACE "^-l" "" "stripped_lib" "${lib}")
string(REGEX REPLACE "\.lib$" "" "stripped_lib" "${stripped_lib}")
list(APPEND stripped_lib_list "${stripped_lib}")
endif()
endforeach()
set(libs_list "${stripped_lib_list}")
# We leave it up to the C/C++ executable that links in the Rust static-library
# to determine which version of the msvc runtime library it should select.
list(FILTER libs_list EXCLUDE REGEX "^msvcrtd?")
list(FILTER flag_list EXCLUDE REGEX "^(-Wl,)?/defaultlib:msvcrtd?")
else()
message(DEBUG "Determining required native libraries - failed: Regex match failure.")
message(DEBUG "`native-static-libs` not found in: `${cargo_build_error_message}`")
return()
endif()
endif()
set("${out_libs}" "${libs_list}" PARENT_SCOPE)
set("${out_flags}" "${flag_list}" PARENT_SCOPE)
endfunction()
if (NOT "${Rust_TOOLCHAIN}" STREQUAL "$CACHE{Rust_TOOLCHAIN}")
# Promote Rust_TOOLCHAIN to a cache variable if it is not already a cache variable
set(Rust_TOOLCHAIN ${Rust_TOOLCHAIN} CACHE STRING "Requested rustup toolchain" FORCE)
endif()
set(_RESOLVE_RUSTUP_TOOLCHAINS_DESC "Indicates whether to descend into the toolchain pointed to by rustup")
set(Rust_RESOLVE_RUSTUP_TOOLCHAINS ON CACHE BOOL ${_RESOLVE_RUSTUP_TOOLCHAINS_DESC})
# This block checks to see if we're prioritizing a rustup-managed toolchain.
if (DEFINED Rust_TOOLCHAIN)
# If the user specifies `Rust_TOOLCHAIN`, then look for `rustup` first, rather than `rustc`.
find_program(Rust_RUSTUP rustup PATHS "$ENV{HOME}/.cargo/bin")
if(NOT Rust_RUSTUP)
if(NOT "${Rust_FIND_QUIETLY}")
message(
WARNING "CMake variable `Rust_TOOLCHAIN` specified, but `rustup` was not found. "
"Ignoring toolchain and looking for a Rust toolchain not managed by rustup.")
endif()
endif()
else()
# If we aren't definitely using a rustup toolchain, look for rustc first - the user may have
# a toolchain installed via a method other than rustup higher in the PATH, which should be
# preferred. However, if the first-found rustc is a rustup proxy, then we'll revert to
# finding the preferred toolchain via rustup.
# Uses `Rust_COMPILER` to let user-specified `rustc` win. But we will still "override" the
# user's setting if it is pointing to `rustup`. Default rustup install path is provided as a
# backup if a toolchain cannot be found in the user's PATH.
if (DEFINED Rust_COMPILER)
set(_Rust_COMPILER_TEST "${Rust_COMPILER}")
set(_USER_SPECIFIED_RUSTC ON)
if(NOT (EXISTS "${_Rust_COMPILER_TEST}" AND NOT IS_DIRECTORY "${_Rust_COMPILER_TEST}"))
set(_ERROR_MESSAGE "Rust_COMPILER was set to `${Rust_COMPILER}`, but this file does "
"not exist."
)
_findrust_failed(${_ERROR_MESSAGE})
return()
endif()
else()
find_program(_Rust_COMPILER_TEST rustc PATHS "$ENV{HOME}/.cargo/bin")
if(NOT EXISTS "${_Rust_COMPILER_TEST}")
set(_ERROR_MESSAGE "`rustc` not found in PATH or `$ENV{HOME}/.cargo/bin`.\n"
"Hint: Check if `rustc` is in PATH or manually specify the location "
"by setting `Rust_COMPILER` to the path to `rustc`.")
_findrust_failed(${_ERROR_MESSAGE})
endif()
endif()
# Check if the discovered rustc is actually a "rustup" proxy.
execute_process(
COMMAND
${CMAKE_COMMAND} -E env
RUSTUP_FORCE_ARG0=rustup
"${_Rust_COMPILER_TEST}" --version
OUTPUT_VARIABLE _RUSTC_VERSION_RAW
ERROR_VARIABLE _RUSTC_VERSION_STDERR
RESULT_VARIABLE _RUSTC_VERSION_RESULT
)
if(NOT (_RUSTC_VERSION_RESULT EQUAL "0"))
_findrust_failed("`${_Rust_COMPILER_TEST} --version` failed with ${_RUSTC_VERSION_RESULT}\n"
"rustc stderr:\n${_RUSTC_VERSION_STDERR}"
)
endif()
if (_RUSTC_VERSION_RAW MATCHES "rustup [0-9\\.]+")
if (_USER_SPECIFIED_RUSTC)
message(
WARNING "User-specified Rust_COMPILER pointed to rustup's rustc proxy. Corrosion's "
"FindRust will always try to evaluate to an actual Rust toolchain, and so the "
"user-specified Rust_COMPILER will be discarded in favor of the default "
"rustup-managed toolchain."
)
unset(Rust_COMPILER)
unset(Rust_COMPILER CACHE)
endif()
# Get `rustup` next to the `rustc` proxy
get_filename_component(_RUST_PROXIES_PATH "${_Rust_COMPILER_TEST}" DIRECTORY)
find_program(Rust_RUSTUP rustup HINTS "${_RUST_PROXIES_PATH}" NO_DEFAULT_PATH)
endif()
unset(_Rust_COMPILER_TEST CACHE)
endif()
# At this point, the only thing we should have evaluated is a path to `rustup` _if that's what the
# best source for a Rust toolchain was determined to be_.
if (NOT Rust_RUSTUP)
set(Rust_RESOLVE_RUSTUP_TOOLCHAINS OFF CACHE BOOL ${_RESOLVE_RUSTUP_TOOLCHAINS_DESC} FORCE)
endif()
# List of user variables that will override any toolchain-provided setting
set(_Rust_USER_VARS Rust_COMPILER Rust_CARGO Rust_CARGO_TARGET Rust_CARGO_HOST_TARGET)
foreach(_VAR ${_Rust_USER_VARS})
if (DEFINED "${_VAR}")
set(${_VAR}_CACHED "${${_VAR}}" CACHE INTERNAL "Internal cache of ${_VAR}")
else()
unset(${_VAR}_CACHED CACHE)
endif()
endforeach()
# Discover what toolchains are installed by rustup, if the discovered `rustc` is a proxy from
# `rustup` and the user hasn't explicitly requested to override this behavior, then select either
# the default toolchain, or the requested toolchain Rust_TOOLCHAIN
if (Rust_RESOLVE_RUSTUP_TOOLCHAINS)
execute_process(
COMMAND
"${Rust_RUSTUP}" toolchain list --verbose
OUTPUT_VARIABLE _TOOLCHAINS_RAW
)
string(REPLACE "\n" ";" _TOOLCHAINS_RAW "${_TOOLCHAINS_RAW}")
set(_DISCOVERED_TOOLCHAINS "")
set(_DISCOVERED_TOOLCHAINS_RUSTC_PATH "")
set(_DISCOVERED_TOOLCHAINS_CARGO_PATH "")
set(_DISCOVERED_TOOLCHAINS_VERSION "")
foreach(_TOOLCHAIN_RAW ${_TOOLCHAINS_RAW})
if (_TOOLCHAIN_RAW MATCHES "([a-zA-Z0-9\\._\\-]+)[ \t\r\n]?(\\(active\\)|\\(active, default\\)|\\(default\\) \\(override\\)|\\(default\\)|\\(override\\))?[ \t\r\n]+(.+)")
set(_TOOLCHAIN "${CMAKE_MATCH_1}")
set(_TOOLCHAIN_TYPE "${CMAKE_MATCH_2}")
set(_TOOLCHAIN_PATH "${CMAKE_MATCH_3}")
set(_TOOLCHAIN_${_TOOLCHAIN}_PATH "${CMAKE_MATCH_3}")
if (_TOOLCHAIN_TYPE MATCHES ".*\\((active, )?default\\).*")
set(_TOOLCHAIN_DEFAULT "${_TOOLCHAIN}")
endif()
if (_TOOLCHAIN_TYPE MATCHES ".*\\((active|override)\\).*")
set(_TOOLCHAIN_OVERRIDE "${_TOOLCHAIN}")
endif()
execute_process(
COMMAND
"${_TOOLCHAIN_PATH}/bin/rustc" --version
OUTPUT_VARIABLE _TOOLCHAIN_RAW_VERSION
)
if (_TOOLCHAIN_RAW_VERSION MATCHES "rustc ([0-9]+)\\.([0-9]+)\\.([0-9]+)(-nightly)?")
list(APPEND _DISCOVERED_TOOLCHAINS "${_TOOLCHAIN}")
list(APPEND _DISCOVERED_TOOLCHAINS_RUSTC_PATH "${_TOOLCHAIN_PATH}/bin/rustc")
list(APPEND _DISCOVERED_TOOLCHAINS_VERSION "${CMAKE_MATCH_1}.${CMAKE_MATCH_2}.${CMAKE_MATCH_3}")
# We need this variable to determine the default toolchain, since `foreach(... IN ZIP_LISTS ...)`
# requires CMake 3.17. As a workaround we define this variable to lookup the version when iterating
# through the `_DISCOVERED_TOOLCHAINS` lists.
set(_TOOLCHAIN_${_TOOLCHAIN}_VERSION "${CMAKE_MATCH_1}.${CMAKE_MATCH_2}.${CMAKE_MATCH_3}")
if(CMAKE_MATCH_4)
set(_TOOLCHAIN_${_TOOLCHAIN}_IS_NIGHTLY "TRUE")
else()
set(_TOOLCHAIN_${_TOOLCHAIN}_IS_NIGHTLY "FALSE")
endif()
if(EXISTS "${_TOOLCHAIN_PATH}/bin/cargo")
list(APPEND _DISCOVERED_TOOLCHAINS_CARGO_PATH "${_TOOLCHAIN_PATH}/bin/cargo")
else()
list(APPEND _DISCOVERED_TOOLCHAINS_CARGO_PATH "NOTFOUND")
endif()
else()
message(AUTHOR_WARNING "Unexpected output from `rustc --version` for Toolchain `${_TOOLCHAIN}`: "
"`${_TOOLCHAIN_RAW_VERSION}`.\n"
"Ignoring this toolchain."
)
endif()
else()
message(AUTHOR_WARNING "Didn't recognize toolchain: ${_TOOLCHAIN_RAW}. Ignoring this toolchain.\n"
"Rustup toolchain list output( `${Rust_RUSTUP} toolchain list --verbose`):\n"
"${_TOOLCHAINS_RAW}"
)
endif()
endforeach()
# Expose a list of available rustup toolchains.
list(LENGTH _DISCOVERED_TOOLCHAINS _toolchain_len)
list(LENGTH _DISCOVERED_TOOLCHAINS_RUSTC_PATH _toolchain_rustc_len)
list(LENGTH _DISCOVERED_TOOLCHAINS_CARGO_PATH _toolchain_cargo_len)
list(LENGTH _DISCOVERED_TOOLCHAINS_VERSION _toolchain_version_len)
if(NOT
(_toolchain_len EQUAL _toolchain_rustc_len
AND _toolchain_cargo_len EQUAL _toolchain_version_len
AND _toolchain_len EQUAL _toolchain_cargo_len)
)
message(FATAL_ERROR "Internal error - list length mismatch."
"List lengths: ${_toolchain_len} toolchains, ${_toolchain_rustc_len} rustc, ${_toolchain_cargo_len} cargo,"
" ${_toolchain_version_len} version. The lengths should be the same."
)
endif()
set(Rust_RUSTUP_TOOLCHAINS CACHE INTERNAL "List of available Rustup toolchains" "${_DISCOVERED_TOOLCHAINS}")
set(Rust_RUSTUP_TOOLCHAINS_RUSTC_PATH
CACHE INTERNAL
"List of the rustc paths corresponding to the toolchain at the same index in `Rust_RUSTUP_TOOLCHAINS`."
"${_DISCOVERED_TOOLCHAINS_RUSTC_PATH}"
)
set(Rust_RUSTUP_TOOLCHAINS_CARGO_PATH
CACHE INTERNAL
"List of the cargo paths corresponding to the toolchain at the same index in `Rust_RUSTUP_TOOLCHAINS`. \
May also be `NOTFOUND` if the toolchain does not have a cargo executable."
"${_DISCOVERED_TOOLCHAINS_CARGO_PATH}"
)
set(Rust_RUSTUP_TOOLCHAINS_VERSION
CACHE INTERNAL
"List of the rust toolchain version corresponding to the toolchain at the same index in \
`Rust_RUSTUP_TOOLCHAINS`."
"${_DISCOVERED_TOOLCHAINS_VERSION}"
)
# Rust_TOOLCHAIN is preferred over a requested version if it is set.
if (NOT DEFINED Rust_TOOLCHAIN)
if (NOT DEFINED _TOOLCHAIN_OVERRIDE)
set(_TOOLCHAIN_SELECTED "${_TOOLCHAIN_DEFAULT}")
else()
set(_TOOLCHAIN_SELECTED "${_TOOLCHAIN_OVERRIDE}")
endif()
# Check default toolchain first.
_findrust_version_ok("_TOOLCHAIN_${_TOOLCHAIN_SELECTED}_VERSION" _VERSION_OK)
if(NOT "${_VERSION_OK}")
foreach(_TOOLCHAIN "${_DISCOVERED_TOOLCHAINS}")
_findrust_version_ok("_TOOLCHAIN_${_TOOLCHAIN}_VERSION" _VERSION_OK)
if("${_VERSION_OK}")
set(_TOOLCHAIN_SELECTED "${_TOOLCHAIN}")
break()
endif()
endforeach()
# Check if we found a suitable version in the for loop.
if(NOT "${_VERSION_OK}")
string(REPLACE ";" "\n" _DISCOVERED_TOOLCHAINS "${_DISCOVERED_TOOLCHAINS}")
_findrust_failed("Failed to find a Rust toolchain matching the version requirements of "
"${Rust_FIND_VERSION}. Available toolchains: ${_DISCOVERED_TOOLCHAINS}")
endif()
endif()
endif()
set(Rust_TOOLCHAIN "${_TOOLCHAIN_SELECTED}" CACHE STRING "The rustup toolchain to use")
set_property(CACHE Rust_TOOLCHAIN PROPERTY STRINGS "${_DISCOVERED_TOOLCHAINS}")
if(NOT Rust_FIND_QUIETLY)
message(STATUS "Rust Toolchain: ${Rust_TOOLCHAIN}")
endif()
if (NOT Rust_TOOLCHAIN IN_LIST _DISCOVERED_TOOLCHAINS)
# If the precise toolchain wasn't found, try appending the default host
execute_process(
COMMAND
"${Rust_RUSTUP}" show
RESULT_VARIABLE _SHOW_RESULT
OUTPUT_VARIABLE _SHOW_RAW
)
if(NOT "${_SHOW_RESULT}" EQUAL "0")
_findrust_failed("Command `${Rust_RUSTUP} show` failed")
endif()
if (_SHOW_RAW MATCHES "Default host: ([a-zA-Z0-9_\\-]*)\n")
set(_DEFAULT_HOST "${CMAKE_MATCH_1}")
else()
_findrust_failed("Failed to parse \"Default host\" from `${Rust_RUSTUP} show`. Got: ${_SHOW_RAW}")
endif()
if (NOT "${Rust_TOOLCHAIN}-${_DEFAULT_HOST}" IN_LIST _DISCOVERED_TOOLCHAINS)
set(_NOT_FOUND_MESSAGE "Could not find toolchain '${Rust_TOOLCHAIN}'\n"
"Available toolchains:\n"
)
foreach(_TOOLCHAIN ${_DISCOVERED_TOOLCHAINS})
list(APPEND _NOT_FOUND_MESSAGE " `${_TOOLCHAIN}`\n")
endforeach()
_findrust_failed(${_NOT_FOUND_MESSAGE})
endif()
set(_RUSTUP_TOOLCHAIN_FULL "${Rust_TOOLCHAIN}-${_DEFAULT_HOST}")
else()
set(_RUSTUP_TOOLCHAIN_FULL "${Rust_TOOLCHAIN}")
endif()
set(_RUST_TOOLCHAIN_PATH "${_TOOLCHAIN_${_RUSTUP_TOOLCHAIN_FULL}_PATH}")
if(NOT "${Rust_FIND_QUIETLY}")
message(VERBOSE "Rust toolchain ${_RUSTUP_TOOLCHAIN_FULL}")
message(VERBOSE "Rust toolchain path ${_RUST_TOOLCHAIN_PATH}")
endif()
# Is overridden if the user specifies `Rust_COMPILER` explicitly.
find_program(
Rust_COMPILER_CACHED
rustc
HINTS "${_RUST_TOOLCHAIN_PATH}/bin"
NO_DEFAULT_PATH)
elseif (Rust_RUSTUP)
get_filename_component(_RUST_TOOLCHAIN_PATH "${Rust_RUSTUP}" DIRECTORY)
get_filename_component(_RUST_TOOLCHAIN_PATH "${_RUST_TOOLCHAIN_PATH}" DIRECTORY)
find_program(
Rust_COMPILER_CACHED
rustc
HINTS "${_RUST_TOOLCHAIN_PATH}/bin"
NO_DEFAULT_PATH)
else()
find_program(Rust_COMPILER_CACHED rustc)
if (EXISTS "${Rust_COMPILER_CACHED}")
# rustc is expected to be at `<toolchain_path>/bin/rustc`.
get_filename_component(_RUST_TOOLCHAIN_PATH "${Rust_COMPILER_CACHED}" DIRECTORY)
get_filename_component(_RUST_TOOLCHAIN_PATH "${_RUST_TOOLCHAIN_PATH}" DIRECTORY)
endif()
endif()
if (NOT EXISTS "${Rust_COMPILER_CACHED}")
set(_NOT_FOUND_MESSAGE "The rustc executable was not found. "
"Rust not installed or ~/.cargo/bin not added to path?\n"
"Hint: Consider setting `Rust_COMPILER` to the absolute path of `rustc`."
)
_findrust_failed(${_NOT_FOUND_MESSAGE})
endif()
if (Rust_RESOLVE_RUSTUP_TOOLCHAINS)
set(_NOT_FOUND_MESSAGE "Rust was detected to be managed by rustup, but failed to find `cargo` "
"next to `rustc` in `${_RUST_TOOLCHAIN_PATH}/bin`. This can happen for custom toolchains, "
"if cargo was not built. "
"Please manually specify the path to a compatible `cargo` by setting `Rust_CARGO`."
)
find_program(
Rust_CARGO_CACHED
cargo
HINTS "${_RUST_TOOLCHAIN_PATH}/bin"
NO_DEFAULT_PATH
)
# note: maybe can use find_package_handle_standard_args here, if we remove the _CACHED postfix.
# not sure why that is here...
if(NOT EXISTS "${Rust_CARGO_CACHED}")
_findrust_failed(${_NOT_FOUND_MESSAGE})
endif()
set(Rust_TOOLCHAIN_IS_RUSTUP_MANAGED TRUE CACHE INTERNAL "" FORCE)
else()
set(_NOT_FOUND_MESSAGE "Failed to find `cargo` in PATH and `${_RUST_TOOLCHAIN_PATH}/bin`.\n"
"Please ensure cargo is in PATH or manually specify the path to a compatible `cargo` by "
"setting `Rust_CARGO`."
)
# On some systems (e.g. NixOS) cargo is not managed by rustup and also not next to rustc.
find_program(
Rust_CARGO_CACHED
cargo
HINTS "${_RUST_TOOLCHAIN_PATH}/bin"
)
# note: maybe can use find_package_handle_standard_args here, if we remove the _CACHED postfix.
# not sure why that is here...
if(NOT EXISTS "${Rust_CARGO_CACHED}")
_findrust_failed(${_NOT_FOUND_MESSAGE})
endif()
endif()
execute_process(
COMMAND "${Rust_CARGO_CACHED}" --version --verbose
OUTPUT_VARIABLE _CARGO_VERSION_RAW
RESULT_VARIABLE _CARGO_VERSION_RESULT
)
# todo: check if cargo is a required component!
if(NOT ( "${_CARGO_VERSION_RESULT}" EQUAL "0" ))
_findrust_failed("Failed to get cargo version.\n"
"`${Rust_CARGO_CACHED} --version` failed with error: `${_CARGO_VERSION_RESULT}"
)
endif()
# todo: don't set cache variables here, but let find_package_handle_standard_args do the promotion
# later.
if (_CARGO_VERSION_RAW MATCHES "cargo ([0-9]+)\\.([0-9]+)\\.([0-9]+)")
set(Rust_CARGO_VERSION_MAJOR "${CMAKE_MATCH_1}" CACHE INTERNAL "" FORCE)
set(Rust_CARGO_VERSION_MINOR "${CMAKE_MATCH_2}" CACHE INTERNAL "" FORCE)
set(Rust_CARGO_VERSION_PATCH "${CMAKE_MATCH_3}" CACHE INTERNAL "" FORCE)
set(Rust_CARGO_VERSION "${Rust_CARGO_VERSION_MAJOR}.${Rust_CARGO_VERSION_MINOR}.${Rust_CARGO_VERSION_PATCH}" CACHE INTERNAL "" FORCE)
# Workaround for the version strings where the `cargo ` prefix is missing.
elseif(_CARGO_VERSION_RAW MATCHES "([0-9]+)\\.([0-9]+)\\.([0-9]+)")
set(Rust_CARGO_VERSION_MAJOR "${CMAKE_MATCH_1}" CACHE INTERNAL "" FORCE)
set(Rust_CARGO_VERSION_MINOR "${CMAKE_MATCH_2}" CACHE INTERNAL "" FORCE)
set(Rust_CARGO_VERSION_PATCH "${CMAKE_MATCH_3}" CACHE INTERNAL "" FORCE)
set(Rust_CARGO_VERSION "${Rust_CARGO_VERSION_MAJOR}.${Rust_CARGO_VERSION_MINOR}.${Rust_CARGO_VERSION_PATCH}" CACHE INTERNAL "" FORCE)
else()
_findrust_failed(
"Failed to parse cargo version. `cargo --version` evaluated to (${_CARGO_VERSION_RAW}). "
"Expected a <Major>.<Minor>.<Patch> version triple."
)
endif()
execute_process(
COMMAND "${Rust_COMPILER_CACHED}" --version --verbose
OUTPUT_VARIABLE _RUSTC_VERSION_RAW
RESULT_VARIABLE _RUSTC_VERSION_RESULT
)
if(NOT ( "${_RUSTC_VERSION_RESULT}" EQUAL "0" ))
_findrust_failed("Failed to get rustc version.\n"
"${Rust_COMPILER_CACHED} --version failed with error: `${_RUSTC_VERSION_RESULT}`")
endif()
if (_RUSTC_VERSION_RAW MATCHES "rustc ([0-9]+)\\.([0-9]+)\\.([0-9]+)(-nightly)?")
set(Rust_VERSION_MAJOR "${CMAKE_MATCH_1}" CACHE INTERNAL "" FORCE)
set(Rust_VERSION_MINOR "${CMAKE_MATCH_2}" CACHE INTERNAL "" FORCE)
set(Rust_VERSION_PATCH "${CMAKE_MATCH_3}" CACHE INTERNAL "" FORCE)
set(Rust_VERSION "${Rust_VERSION_MAJOR}.${Rust_VERSION_MINOR}.${Rust_VERSION_PATCH}" CACHE INTERNAL "" FORCE)
if(CMAKE_MATCH_4)
set(Rust_IS_NIGHTLY 1 CACHE INTERNAL "" FORCE)
else()
set(Rust_IS_NIGHTLY 0 CACHE INTERNAL "" FORCE)
endif()
else()
_findrust_failed("Failed to parse rustc version. `${Rust_COMPILER_CACHED} --version --verbose` "
"evaluated to:\n`${_RUSTC_VERSION_RAW}`"
)
endif()
if (_RUSTC_VERSION_RAW MATCHES "host: ([a-zA-Z0-9_\\-]*)\n")
set(Rust_DEFAULT_HOST_TARGET "${CMAKE_MATCH_1}")
set(Rust_CARGO_HOST_TARGET_CACHED "${Rust_DEFAULT_HOST_TARGET}" CACHE STRING "Host triple")
else()
_findrust_failed(
"Failed to parse rustc host target. `rustc --version --verbose` evaluated to:\n${_RUSTC_VERSION_RAW}"
)
endif()
if (_RUSTC_VERSION_RAW MATCHES "LLVM version: ([0-9]+)\\.([0-9]+)(\\.([0-9]+))?")
set(Rust_LLVM_VERSION_MAJOR "${CMAKE_MATCH_1}" CACHE INTERNAL "" FORCE)
set(Rust_LLVM_VERSION_MINOR "${CMAKE_MATCH_2}" CACHE INTERNAL "" FORCE)
# With the Rust toolchain 1.44.1 the reported LLVM version is 9.0, i.e. without a patch version.
# Since cmake regex does not support non-capturing groups, just ignore Match 3.
set(Rust_LLVM_VERSION_PATCH "${CMAKE_MATCH_4}" CACHE INTERNAL "" FORCE)
set(Rust_LLVM_VERSION "${Rust_LLVM_VERSION_MAJOR}.${Rust_LLVM_VERSION_MINOR}.${Rust_LLVM_VERSION_PATCH}" CACHE INTERNAL "" FORCE)
elseif(NOT Rust_FIND_QUIETLY)
message(
WARNING
"Failed to parse rustc LLVM version. `rustc --version --verbose` evaluated to:\n${_RUSTC_VERSION_RAW}"
)
endif()
if (NOT Rust_CARGO_TARGET_CACHED)
unset(_CARGO_ARCH)
unset(_CARGO_ABI)
if (WIN32)
if (CMAKE_VS_PLATFORM_NAME)
string(TOLOWER "${CMAKE_VS_PLATFORM_NAME}" LOWER_VS_PLATFORM_NAME)
if ("${LOWER_VS_PLATFORM_NAME}" STREQUAL "win32")
set(_CARGO_ARCH i686)
elseif("${LOWER_VS_PLATFORM_NAME}" STREQUAL "x64")
set(_CARGO_ARCH x86_64)
elseif("${LOWER_VS_PLATFORM_NAME}" STREQUAL "arm64")
set(_CARGO_ARCH aarch64)
else()
message(WARNING "VS Platform '${CMAKE_VS_PLATFORM_NAME}' not recognized")
endif()
endif()
# Fallback path
if(NOT DEFINED _CARGO_ARCH)
# Possible values for windows when not cross-compiling taken from here:
# https://learn.microsoft.com/en-us/windows/win32/winprog64/wow64-implementation-details
# When cross-compiling the user is expected to supply the value, so we match more variants.
if(CMAKE_SYSTEM_PROCESSOR MATCHES "^(AMD64|amd64|x86_64)$")
set(_CARGO_ARCH x86_64)
elseif(CMAKE_SYSTEM_PROCESSOR MATCHES "^(ARM64|arm64|aarch64)$")
set(_CARGO_ARCH aarch64)
elseif(CMAKE_SYSTEM_PROCESSOR MATCHES "^(X86|x86|i686)$")
set(_CARGO_ARCH i686)
elseif(CMAKE_SYSTEM_PROCESSOR STREQUAL "i586")
set(_CARGO_ARCH i586)
elseif(CMAKE_SYSTEM_PROCESSOR STREQUAL "IA64")
message(FATAL_ERROR "No rust target for Intel Itanium.")
elseif(NOT "${CMAKE_SYSTEM_PROCESSOR}")
message(WARNING "Failed to detect target architecture. Please set `CMAKE_SYSTEM_PROCESSOR`"
" to your target architecture or set `Rust_CARGO_TARGET` to your cargo target triple."
)
else()
message(WARNING "Failed to detect target architecture. Please set "
"`Rust_CARGO_TARGET` to your cargo target triple."
)
endif()
endif()
set(_CARGO_VENDOR "pc-windows")
# The MSVC Generators will always target the msvc ABI.
# For other generators we check the compiler ID and compiler target (if present)
# If no compiler is set and we are not cross-compiling then we just choose the
# default rust host target.
if(DEFINED MSVC
OR "${CMAKE_CXX_COMPILER_ID}" STREQUAL "MSVC"
OR "${CMAKE_C_COMPILER_ID}" STREQUAL "MSVC"
OR "${CMAKE_CXX_COMPILER_TARGET}" MATCHES "-msvc$"
OR "${CMAKE_C_COMPILER_TARGET}" MATCHES "-msvc$"
)
set(_CARGO_ABI msvc)
elseif("${CMAKE_CXX_COMPILER_ID}" STREQUAL "GNU"
OR "${CMAKE_C_COMPILER_ID}" STREQUAL "GNU"
OR "${CMAKE_CXX_COMPILER_TARGET}" MATCHES "-gnu$"
OR "${CMAKE_C_COMPILER_TARGET}" MATCHES "-gnu$"
OR (NOT CMAKE_CROSSCOMPILING AND "${Rust_DEFAULT_HOST_TARGET}" MATCHES "-gnu$")
)
set(_CARGO_ABI gnu)
elseif(NOT "${CMAKE_CROSSCOMPILING}" AND "${Rust_DEFAULT_HOST_TARGET}" MATCHES "-msvc$")
# We first check if the gnu branch matches to ensure this fallback is only used
# if no compiler is enabled.
set(_CARGO_ABI msvc)
else()
message(WARNING "Could not determine the target ABI. Please specify `Rust_CARGO_TARGET` manually.")
endif()
if(DEFINED _CARGO_ARCH AND DEFINED _CARGO_VENDOR AND DEFINED _CARGO_ABI)
set(Rust_CARGO_TARGET_CACHED "${_CARGO_ARCH}-${_CARGO_VENDOR}-${_CARGO_ABI}"
CACHE STRING "Target triple")
endif()
elseif (ANDROID)
if (CMAKE_ANDROID_ARCH_ABI STREQUAL armeabi-v7a)
if (CMAKE_ANDROID_ARM_MODE)
set(_Rust_ANDROID_TARGET armv7-linux-androideabi)
else ()
set(_Rust_ANDROID_TARGET thumbv7neon-linux-androideabi)
endif()
elseif (CMAKE_ANDROID_ARCH_ABI STREQUAL arm64-v8a)
set(_Rust_ANDROID_TARGET aarch64-linux-android)
elseif (CMAKE_ANDROID_ARCH_ABI STREQUAL x86)
set(_Rust_ANDROID_TARGET i686-linux-android)
elseif (CMAKE_ANDROID_ARCH_ABI STREQUAL x86_64)
set(_Rust_ANDROID_TARGET x86_64-linux-android)
endif()
if (_Rust_ANDROID_TARGET)
set(Rust_CARGO_TARGET_CACHED "${_Rust_ANDROID_TARGET}" CACHE STRING "Target triple")
endif()
elseif("${CMAKE_SYSTEM_NAME}" STREQUAL "OHOS")
if(CMAKE_OHOS_ARCH_ABI STREQUAL arm64-v8a)
set(_RUST_OHOS_TARGET aarch64-unknown-linux-ohos)
elseif(CMAKE_OHOS_ARCH_ABI STREQUAL armeabi-v7a)
set(_RUST_OHOS_TARGET armv7-unknown-linux-ohos)
elseif(CMAKE_OHOS_ARCH_ABI STREQUAL x86_64)
set(_RUST_OHOS_TARGET x86_64-unknown-linux-ohos)
else()
message(WARNING "unrecognized OHOS architecture: ${OHOS_ARCH}")
endif()
if(_RUST_OHOS_TARGET)
set(Rust_CARGO_TARGET_CACHED "${_RUST_OHOS_TARGET}" CACHE STRING "Target triple")
endif()
endif()
# Fallback to the default host target
if(NOT Rust_CARGO_TARGET_CACHED)
if(CMAKE_CROSSCOMPILING)
message(WARNING "CMake is in cross-compiling mode, but the cargo target-triple could not be inferred."
"Falling back to the default host target. Please consider manually setting `Rust_CARGO_TARGET`."
)
endif()
set(Rust_CARGO_TARGET_CACHED "${Rust_DEFAULT_HOST_TARGET}" CACHE STRING "Target triple")
endif()
message(STATUS "Rust Target: ${Rust_CARGO_TARGET_CACHED}")
endif()
if(Rust_CARGO_TARGET_CACHED STREQUAL Rust_DEFAULT_HOST_TARGET)
set(Rust_CROSSCOMPILING FALSE CACHE INTERNAL "Rust is configured for cross-compiling")
else()
set(Rust_CROSSCOMPILING TRUE CACHE INTERNAL "Rust is configured for cross-compiling")
endif()
_corrosion_parse_target_triple("${Rust_CARGO_TARGET_CACHED}" rust_arch rust_vendor rust_os rust_env)
_corrosion_parse_target_triple("${Rust_CARGO_HOST_TARGET_CACHED}" rust_host_arch rust_host_vendor rust_host_os rust_host_env)
set(Rust_CARGO_TARGET_ARCH "${rust_arch}" CACHE INTERNAL "Target architecture")
set(Rust_CARGO_TARGET_VENDOR "${rust_vendor}" CACHE INTERNAL "Target vendor")
set(Rust_CARGO_TARGET_OS "${rust_os}" CACHE INTERNAL "Target Operating System")
set(Rust_CARGO_TARGET_ENV "${rust_env}" CACHE INTERNAL "Target environment")
set(Rust_CARGO_HOST_ARCH "${rust_host_arch}" CACHE INTERNAL "Host architecture")
set(Rust_CARGO_HOST_VENDOR "${rust_host_vendor}" CACHE INTERNAL "Host vendor")
set(Rust_CARGO_HOST_OS "${rust_host_os}" CACHE INTERNAL "Host Operating System")
set(Rust_CARGO_HOST_ENV "${rust_host_env}" CACHE INTERNAL "Host environment")
if(NOT DEFINED CACHE{Rust_CARGO_TARGET_LINK_NATIVE_LIBS})
message(STATUS "Determining required link libraries for target ${Rust_CARGO_TARGET_CACHED}")
unset(required_native_libs)
_corrosion_determine_libs_new("${Rust_CARGO_TARGET_CACHED}" required_native_libs required_link_flags)
if(DEFINED required_native_libs)
message(STATUS "Required static libs for target ${Rust_CARGO_TARGET_CACHED}: ${required_native_libs}" )
endif()
if(DEFINED required_link_flags)
message(STATUS "Required link flags for target ${Rust_CARGO_TARGET_CACHED}: ${required_link_flags}" )
endif()
# In very recent corrosion versions it is possible to override the rust compiler version
# per target, so to be totally correct we would need to determine the libraries for
# every installed Rust version, that the user could choose from.
# In practice there aren't likely going to be any major differences, so we just do it once
# for the target and once for the host target (if cross-compiling).
set(Rust_CARGO_TARGET_LINK_NATIVE_LIBS "${required_native_libs}" CACHE INTERNAL
"Required native libraries when linking Rust static libraries")
set(Rust_CARGO_TARGET_LINK_OPTIONS "${required_link_flags}" CACHE INTERNAL
"Required link flags when linking Rust static libraries")
endif()
if(Rust_CROSSCOMPILING AND NOT DEFINED CACHE{Rust_CARGO_HOST_TARGET_LINK_NATIVE_LIBS})
message(STATUS "Determining required link libraries for target ${Rust_CARGO_HOST_TARGET_CACHED}")
unset(host_libs)
_corrosion_determine_libs_new("${Rust_CARGO_HOST_TARGET_CACHED}" host_libs host_flags)
if(DEFINED host_libs)
message(STATUS "Required static libs for host target ${Rust_CARGO_HOST_TARGET_CACHED}: ${host_libs}" )
endif()
set(Rust_CARGO_HOST_TARGET_LINK_NATIVE_LIBS "${host_libs}" CACHE INTERNAL
"Required native libraries when linking Rust static libraries for the host target")
set(Rust_CARGO_HOST_TARGET_LINK_OPTIONS "${host_flags}" CACHE INTERNAL
"Required linker flags when linking Rust static libraries for the host target")
endif()
# Set the input variables as non-cache variables so that the variables are available after
# `find_package`, even if the values were evaluated to defaults.
foreach(_VAR ${_Rust_USER_VARS})
set(${_VAR} "${${_VAR}_CACHED}")
# Ensure cached variables have type INTERNAL
set(${_VAR}_CACHED "${${_VAR}_CACHED}" CACHE INTERNAL "Internal cache of ${_VAR}")
endforeach()
find_package_handle_standard_args(
Rust
REQUIRED_VARS Rust_COMPILER Rust_VERSION Rust_CARGO Rust_CARGO_VERSION Rust_CARGO_TARGET Rust_CARGO_HOST_TARGET
VERSION_VAR Rust_VERSION
)
if(NOT TARGET Rust::Rustc)
add_executable(Rust::Rustc IMPORTED GLOBAL)
set_property(
TARGET Rust::Rustc
PROPERTY IMPORTED_LOCATION "${Rust_COMPILER_CACHED}"
)
add_executable(Rust::Cargo IMPORTED GLOBAL)
set_property(
TARGET Rust::Cargo
PROPERTY IMPORTED_LOCATION "${Rust_CARGO_CACHED}"
)
set(Rust_FOUND true)
endif()
list(POP_BACK CMAKE_MESSAGE_CONTEXT)
|