microsoft / vcpkg

C++ Library Manager for Windows, Linux, and MacOS
MIT License
22.78k stars 6.3k forks source link

Can't Reuse Binary Cache genearte from Linux on a macos host for abi mismatch #39401

Open vimerzhao opened 2 months ago

vimerzhao commented 2 months ago

Describe the bug

Environment

To Reproduce for example:

  1. ./vcpkg install fmt:arm64-android (On Linux)
  2. ./vcpkg install fmt:arm64-android (On Mac, Use same vcpkg version and same ndk version)
  3. fmt will rebuild because of binarycache mismatch.
  4. it's vcpkg-cmake's abi mismatch (because of different triplet ) result in fnt abi mismatch. However, vcpkg-cmake seem has no releation with host, they use same cmake code on linux and mac.

Expected behavior

  1. ./vcpkg install fmt:arm64-android (On Linux)
  2. ./vcpkg install fmt:arm64-android (On Mac, Use same vcpkg version and same ndk version)
  3. step2 will use fmt's binarycache

Failure logs -(please attached failure logs)

Additional context

image
Osyotr commented 2 months ago

Could have been workarounded by https://github.com/microsoft/vcpkg-tool/pull/816

Neumann-A commented 2 months ago

Create a host triplet: x64-linux-macos. Use set(VCPKG_DISABLE_COMPILER_TRACKING ON) for the script ports in question (using per port customization). Use some magic to set VCPKG_CMAKE_SYSTEM_NAME correctly.

Then you might get the same host script abi hashes unless I forgot something (of course using --x-abi-tools-use-exact-versions is also required )

vimerzhao commented 2 months ago

Create a host triplet: x64-linux-macos. Use set(VCPKG_DISABLE_COMPILER_TRACKING ON) for the script ports in question (using per port customization). Use some magic to set VCPKG_CMAKE_SYSTEM_NAME correctly.

Then you might get the same host script abi hashes unless I forgot something (of course using --x-abi-tools-use-exact-versions is also required )

actually, my project has 6 platform to share , this solution may result in lots of "magic work"

vimerzhao commented 2 months ago

Create a host triplet: x64-linux-macos. Use set(VCPKG_DISABLE_COMPILER_TRACKING ON) for the script ports in question (using per port customization). Use some magic to set VCPKG_CMAKE_SYSTEM_NAME correctly.

Then you might get the same host script abi hashes unless I forgot something (of course using --x-abi-tools-use-exact-versions is also required )

I do think vcpkg should enable "custom ignore" some dependency's abi

WangWeiLin-MV commented 2 months ago

@vimerzhao Here is a temporary workaround:

pseudocode-change-host-to-target.ps1 (Please check and test before running)

Get-ChildItem -Directory -Path .\ports\ | % { Join-Path $_ vcpkg.json } | % { (cat -Raw $_) -replace ('{1}{0}\s+"name": "vcpkg-cmake",{0}\s+"host": true{0}\s+{2}' -f "`n","`{","`}"), "`"vcpkg-cmake`"" -replace ('{1}{0}\s+"name": "vcpkg-cmake-config",{0}\s+"host": true{0}\s+{2}' -f "`n","`{","`}"), "`"vcpkg-cmake-config`"" | Set-Content -NoNewline $_ }

which change vcpkg-cmake and vcpkg-cmake-config dependency from host to normal

Hope it helps you.


These tool-port actually just copy script files when installed, so their vcpkg_abi_info should not be related to triplet. These need to be changed in vcpkg-tool sources. If there are any changes, I will update here.

P.S. Unless any platform-related or are used in portfile.cmake, they will need to be recorded in vcpkg_abi_info. Any external programs that are actually used and have potential impact should also be recorded in the abi, not just compiler, cmake, and powershell.

WangWeiLin-MV commented 2 months ago

For a broader summary, host-port, like compilers and external programs, provides functionality, i.e. API, rather than ABI.

So one possible change is:

Identify binary cache and build artifact by both ABI and API, with API coming from the hash content in its vcpkg_abi_info excluding compiler, triplets, etc.

The consumer port's vcpkg_abi_info only needs to record the API, not the ABI of host-port dependency.

dg0yt commented 2 months ago

change vcpkg-cmake and vcpkg-cmake-config dependency from host to normal

This won't help much as long as the compiler binary is still tracked for the target - linux and osx don't use the same binaries.

And all these approaches will fail as as soon as you need a real host executable from a port (sqlite3, pkgconf, gn, qmake, ...). You cannot let vcpkg install the wrong binary.