zsvo/pkg/debian/dep_resolver.go
itexpert228 fbe74e8a87
Improve dependency resolver and fix critical bugs
- Add comprehensive Debian dependency resolver (400+ package mappings)

- Implement automatic recursive dependency resolution for build dependencies

- Fix logic errors in install.go: allowFailure handling, ensureBuildDependency

- Fix install-script.sh PKGDIR environment variable handling

- Fix hardcoded /tmp/install-script.sh path in autoRecipeFromDebian

- Fix wrong yyjson URL

- Increase build timeout from 30min to 2 hours

- Improve command validation security

- Fix temporary directory leaks in installer

- Update .gitignore to include zsvo-test binary
2026-03-14 19:54:49 +03:00

1173 lines
21 KiB
Go

package debian
import (
"bufio"
"fmt"
"io"
"net/http"
"regexp"
"strings"
"sync"
"time"
"github.com/ulikunitz/xz"
)
// DependencyResolver provides comprehensive Debian dependency resolution
type DependencyResolver struct {
resolver *Resolver
cache *dependencyCache
httpClient *http.Client
mirrors []string
suites []string
components []string
arch string
}
// dependencyCache caches resolved dependencies
type dependencyCache struct {
mu sync.RWMutex
deps map[string]*PackageDeps
srcMap map[string]string // binary pkg name -> source pkg name
}
// PackageDeps represents Debian package dependencies
type PackageDeps struct {
Package string
Source string
Version string
Depends []string
BuildDepends []string
Suggests []string
Recommends []string
Conflicts []string
Provides []string
}
// NewDependencyResolver creates a comprehensive Debian dependency resolver
func NewDependencyResolver() *DependencyResolver {
return &DependencyResolver{
resolver: NewResolver(),
cache: &dependencyCache{
deps: make(map[string]*PackageDeps),
srcMap: make(map[string]string),
},
httpClient: &http.Client{
Timeout: 30 * time.Second,
},
mirrors: []string{
"https://deb.debian.org/debian",
"https://ftp.debian.org/debian",
"https://mirrors.kernel.org/debian",
},
suites: []string{"sid", "unstable", "testing", "stable"},
components: []string{"main", "contrib", "non-free"},
arch: "amd64",
}
}
// ResolveDependencies resolves all dependencies for a Debian binary package
func (r *DependencyResolver) ResolveDependencies(pkgName string) (*PackageDeps, error) {
// Check cache first
if cached := r.cache.get(pkgName); cached != nil {
return cached, nil
}
// Try to find in Sources files (for build-deps) or Packages files (for runtime deps)
deps, err := r.resolveFromDebian(pkgName)
if err != nil {
return nil, err
}
// Cache result
r.cache.set(pkgName, deps)
return deps, nil
}
// BinaryToSource maps a Debian binary package name to its source package name
func (r *DependencyResolver) BinaryToSource(binaryPkg string) (string, error) {
// Check cache
if src := r.cache.getSource(binaryPkg); src != "" {
return src, nil
}
// Try built-in mappings first (fast path)
if src := mapBinaryToSourceFast(binaryPkg); src != "" {
r.cache.setSource(binaryPkg, src)
return src, nil
}
// Look up in Debian Sources
srcInfo, err := r.resolver.ResolveSource(binaryPkg)
if err != nil {
return "", fmt.Errorf("cannot resolve source for %s: %w", binaryPkg, err)
}
r.cache.setSource(binaryPkg, srcInfo.SourcePackage)
return srcInfo.SourcePackage, nil
}
// ResolveDependencyChain resolves full dependency chain for a package
func (r *DependencyResolver) ResolveDependencyChain(rootPkg string, includeBuildDeps bool) ([]string, error) {
visited := make(map[string]bool)
result := make([]string, 0)
queue := []string{rootPkg}
for len(queue) > 0 {
pkg := queue[0]
queue = queue[1:]
if visited[pkg] {
continue
}
visited[pkg] = true
// Get package dependencies
deps, err := r.ResolveDependencies(pkg)
if err != nil {
// Try to resolve as source package
srcPkg, srcErr := r.BinaryToSource(pkg)
if srcErr != nil {
continue // Skip unresolved
}
if !visited[srcPkg] {
result = append(result, srcPkg)
}
continue
}
result = append(result, pkg)
// Add runtime dependencies
for _, dep := range deps.Depends {
depName := r.extractDepName(dep)
if !visited[depName] {
queue = append(queue, depName)
}
}
// Add build dependencies if requested
if includeBuildDeps {
for _, dep := range deps.BuildDepends {
depName := r.extractDepName(dep)
if !visited[depName] {
queue = append(queue, depName)
}
}
}
}
return result, nil
}
// extractDepName extracts package name from dependency string (e.g., "pkg (>= 1.0)" -> "pkg")
func (r *DependencyResolver) extractDepName(dep string) string {
// Remove version constraints
re := regexp.MustCompile(`^([a-zA-Z0-9+.-]+)`)
matches := re.FindStringSubmatch(dep)
if len(matches) > 1 {
return matches[1]
}
return dep
}
// resolveFromDebian attempts to resolve dependencies from Debian repository
func (r *DependencyResolver) resolveFromDebian(pkgName string) (*PackageDeps, error) {
// Try to find binary package info from Packages files
for _, mirror := range r.mirrors {
for _, suite := range r.suites {
for _, component := range r.components {
deps, err := r.fetchBinaryPackageInfo(mirror, suite, component, pkgName)
if err == nil && deps != nil {
return deps, nil
}
}
}
}
return nil, fmt.Errorf("package %s not found in Debian repositories", pkgName)
}
// fetchBinaryPackageInfo fetches package info from Packages.xz
func (r *DependencyResolver) fetchBinaryPackageInfo(mirror, suite, component, pkgName string) (*PackageDeps, error) {
url := fmt.Sprintf("%s/dists/%s/%c%s/binary-%s/Packages.xz",
mirror, suite, component[0], component[1:], r.arch)
resp, err := r.httpClient.Get(url)
if err != nil {
return nil, err
}
defer resp.Body.Close()
if resp.StatusCode != http.StatusOK {
return nil, fmt.Errorf("HTTP %d", resp.StatusCode)
}
// Decompress xz
xzReader, err := xz.NewReader(resp.Body)
if err != nil {
return nil, err
}
// Parse Packages file looking for our package
return r.parsePackagesFile(xzReader, pkgName)
}
// parsePackagesFile parses Debian Packages file to find package info
func (dr *DependencyResolver) parsePackagesFile(reader io.Reader, targetPkg string) (*PackageDeps, error) {
scanner := bufio.NewScanner(reader)
var currentPkg *PackageDeps
inTarget := false
for scanner.Scan() {
line := scanner.Text()
// Empty line = end of paragraph
if line == "" {
if inTarget && currentPkg != nil {
return currentPkg, nil
}
currentPkg = nil
inTarget = false
continue
}
// Check if this is our target package
if strings.HasPrefix(line, "Package: ") {
pkg := strings.TrimPrefix(line, "Package: ")
if pkg == targetPkg {
inTarget = true
currentPkg = &PackageDeps{Package: pkg}
}
}
if !inTarget || currentPkg == nil {
continue
}
// Parse fields
switch {
case strings.HasPrefix(line, "Source: "):
currentPkg.Source = strings.TrimPrefix(line, "Source: ")
case strings.HasPrefix(line, "Version: "):
currentPkg.Version = strings.TrimPrefix(line, "Version: ")
case strings.HasPrefix(line, "Depends: "):
currentPkg.Depends = dr.parseDepLine(strings.TrimPrefix(line, "Depends: "))
case strings.HasPrefix(line, "Suggests: "):
currentPkg.Suggests = dr.parseDepLine(strings.TrimPrefix(line, "Suggests: "))
case strings.HasPrefix(line, "Recommends: "):
currentPkg.Recommends = dr.parseDepLine(strings.TrimPrefix(line, "Recommends: "))
case strings.HasPrefix(line, "Conflicts: "):
currentPkg.Conflicts = dr.parseDepLine(strings.TrimPrefix(line, "Conflicts: "))
case strings.HasPrefix(line, "Provides: "):
currentPkg.Provides = dr.parseDepLine(strings.TrimPrefix(line, "Provides: "))
}
}
if err := scanner.Err(); err != nil {
return nil, err
}
if inTarget && currentPkg != nil {
return currentPkg, nil
}
return nil, fmt.Errorf("package not found")
}
// parseDepLine parses dependency line (handles alternatives with |)
func (r *DependencyResolver) parseDepLine(line string) []string {
result := make([]string, 0)
// Split by comma (separate dependencies)
parts := strings.Split(line, ",")
for _, part := range parts {
part = strings.TrimSpace(part)
if part != "" {
result = append(result, part)
}
}
return result
}
// Cache methods
func (c *dependencyCache) get(pkg string) *PackageDeps {
c.mu.RLock()
defer c.mu.RUnlock()
return c.deps[pkg]
}
func (c *dependencyCache) set(pkg string, deps *PackageDeps) {
c.mu.Lock()
defer c.mu.Unlock()
c.deps[pkg] = deps
}
func (c *dependencyCache) getSource(binary string) string {
c.mu.RLock()
defer c.mu.RUnlock()
return c.srcMap[binary]
}
func (c *dependencyCache) setSource(binary, source string) {
c.mu.Lock()
defer c.mu.Unlock()
c.srcMap[binary] = source
}
// mapBinaryToSourceFast provides fast static mappings for common packages
func mapBinaryToSourceFast(binary string) string {
// Comprehensive mapping of Debian binary packages to source packages
mappings := map[string]string{
// Essential build tools
"cmake": "cmake",
"ninja-build": "ninja-build",
"meson": "meson",
"pkg-config": "pkgconf",
"pkgconf": "pkgconf",
// Compilers
"gcc": "gcc-defaults",
"g++": "gcc-defaults",
"clang": "llvm-defaults",
// SSL/TLS
"libssl-dev": "openssl",
"libssl3": "openssl",
"openssl": "openssl",
// Compression
"zlib1g-dev": "zlib",
"zlib1g": "zlib",
"libbz2-dev": "bzip2",
"liblzma-dev": "xz-utils",
"libzstd-dev": "zstd",
// XML
"libxml2-dev": "libxml2",
"libxml2": "libxml2",
"libxslt1-dev": "libxslt",
// JSON
"libjson-c-dev": "json-c",
"libjson-c5": "json-c",
// cURL
"libcurl4-openssl-dev": "curl",
"libcurl4-gnutls-dev": "curl",
"curl": "curl",
// Database
"libsqlite3-dev": "sqlite3",
"libsqlite3-0": "sqlite3",
// Terminal/UI
"libncurses-dev": "ncurses",
"libncurses6": "ncurses",
"libreadline-dev": "readline",
"libreadline8": "readline",
// Image
"libpng-dev": "libpng1.6",
"libpng16-16": "libpng1.6",
"libjpeg-dev": "libjpeg-turbo",
"libtiff-dev": "tiff",
// Crypto
"libgcrypt20-dev": "libgcrypt20",
"libgpg-error-dev": "libgpg-error",
// GNUTLS
"libgnutls28-dev": "gnutls28",
// PCRE
"libpcre3-dev": "pcre3",
"libpcre2-dev": "pcre2",
// Expat
"libexpat1-dev": "expat",
// FFI
"libffi-dev": "libffi",
// UUID
"libuuid-dev": "util-linux",
// Git
"git": "git",
// Flex/Bison
"flex": "flex",
"bison": "bison",
"m4": "m4",
// Autotools
"autoconf": "autoconf",
"automake": "automake",
"libtool": "libtool",
// Gettext
"gettext": "gettext",
"libgettextpo-dev": "gettext",
// Lua
"liblua5.1-dev": "lua5.1",
"liblua5.4-dev": "lua5.4",
// Python
"python3-dev": "python3-defaults",
"python3": "python3-defaults",
// Perl
"perl": "perl",
// Procps
"procps": "procps-ng",
// Iconv
"libiconv-hook-dev": "libiconv",
// ICU
"libicu-dev": "icu",
// HarfBuzz
"libharfbuzz-dev": "harfbuzz",
// FontConfig
"libfontconfig-dev": "fontconfig",
// Freetype
"libfreetype-dev": "freetype",
// Cairo
"libcairo2-dev": "cairo",
// Pango
"libpango1.0-dev": "pango1.0",
// GDK-Pixbuf
"libgdk-pixbuf-2.0-dev": "gdk-pixbuf",
// GLib
"libglib2.0-dev": "glib2.0",
// GObject introspection
"gobject-introspection": "gobject-introspection",
// ATK
"libatk1.0-dev": "atk1.0",
// GTK
"libgtk-3-dev": "gtk+3.0",
"libgtk-4-dev": "gtk4",
// GLibmm
"libglibmm-2.4-dev": "glibmm2.4",
// X11
"libx11-dev": "libx11",
"libxext-dev": "libxext",
"libxrender-dev": "libxrender",
"libxft-dev": "libxft",
"libxpm-dev": "libxpm",
"libxmu-dev": "libxmu",
"libxaw7-dev": "libxaw",
"libxfixes-dev": "libxfixes",
"libxinerama-dev": "libxinerama",
"libxrandr-dev": "libxrandr",
"libxcursor-dev": "libxcursor",
"libxcomposite-dev": "libxcomposite",
"libxdamage-dev": "libxdamage",
"libxkbfile-dev": "libxkbfile",
// XCB
"libxcb1-dev": "libxcb",
"libxcb-keysyms1-dev": "xcb-util-keysyms",
// Xt
"libxt-dev": "libxt",
// SM/ICE
"libsm-dev": "libsm",
"libice-dev": "libice",
// Xtrans
"libxtrans-dev": "libxtrans",
// X11proto
"x11proto-dev": "xorgproto",
"xorg-sgml-doctools": "xorg-sgml-doctools",
// Wayland
"libwayland-dev": "wayland",
"wayland-protocols": "wayland-protocols",
// OpenGL
"libgl-dev": "libglvnd",
"libgl1-mesa-dev": "mesa",
"libegl1-mesa-dev": "mesa",
"libgbm-dev": "mesa",
// Vulkan
"libvulkan-dev": "vulkan-loader",
// Shaderc
"libshaderc-dev": "shaderc",
// SPIRV
"libspirv-tools-dev": "spirv-tools",
// PulseAudio
"libpulse-dev": "pulseaudio",
// ALSA
"libasound2-dev": "alsa-lib",
// JACK
"libjack-dev": "jack-audio-connection-kit",
// PipeWire
"libpipewire-0.3-dev": "pipewire",
// D-Bus
"libdbus-1-dev": "dbus",
// GMP
"libgmp-dev": "gmp",
// MPFR
"libmpfr-dev": "mpfr",
// MPC
"libmpc-dev": "mpc",
// GPGME
"libgpgme-dev": "gpgme1.0",
// Assuan
"libassuan-dev": "libassuan",
// KSBA
"libksba-dev": "libksba",
// NTBTLS
"libntbtls-dev": "ntbtls",
// OpenLDAP
"libldap2-dev": "openldap",
// SASL
"libsasl2-dev": "cyrus-sasl2",
// Kerberos
"libkrb5-dev": "krb5",
// Keyutils
"libkeyutils-dev": "keyutils",
// Nettle
"libnettle-dev": "nettle",
// Hogweed
"libhogweed6": "nettle",
// TASN1
"libtasn1-6-dev": "libtasn1-6",
// IDN2
"libidn2-dev": "libidn2",
// Unistring
"libunistring-dev": "libunistring",
// PSL
"libpsl-dev": "libpsl",
// BROTLI
"libbrotli-dev": "brotli",
// NGHTTP2
"libnghttp2-dev": "nghttp2",
// Systemd
"libsystemd-dev": "systemd",
// Elogind
"libelogind-dev": "elogind",
// UPower
"libupower-glib-dev": "upower",
// UDisks
"libudisks2-dev": "udisks2",
// Polkit
"libpolkit-gobject-1-dev": "policykit-1",
// ConsoleKit
"libck-connector-dev": "consolekit",
// UDEV
"libudev-dev": "systemd",
// Eudev
"libeudev-dev": "eudev",
// KMod
"libkmod-dev": "kmod",
// PCIUtils
"libpci-dev": "pciutils",
// USBUtils
"libusb-1.0-0-dev": "usbutils",
// Libusb
"libusb-1.0-dev": "libusb-1.0",
// HIDAPI
"libhidapi-dev": "hidapi",
// SDL2
"libsdl2-dev": "sdl2",
// OpenAL
"libopenal-dev": "openal-soft",
// Ogg
"libogg-dev": "libogg",
// Vorbis
"libvorbis-dev": "libvorbis",
// FLAC
"libflac-dev": "flac",
// Opus
"libopus-dev": "opus",
// Theora
"libtheora-dev": "libtheora",
// VPX
"libvpx-dev": "libvpx",
// AOM
"libaom-dev": "aom",
// DAV1D
"libdav1d-dev": "dav1d",
// FFmpeg
"libavcodec-dev": "ffmpeg",
"libavformat-dev": "ffmpeg",
"libavutil-dev": "ffmpeg",
// X264
"libx264-dev": "x264",
// X265
"libx265-dev": "x265",
// WebP
"libwebp-dev": "libwebp",
// OpenEXR
"libopenexr-dev": "openexr",
// Imath
"libimath-dev": "imath",
// OpenJPEG
"libopenjp2-7-dev": "openjpeg2",
// LittleCMS
"liblcms2-dev": "lcms2",
// "libreadline-dev": "readline",
// History
"libhistory-dev": "readline",
// Termcap
"libtinfo-dev": "ncurses",
// Curses
"libcurses-dev": "ncurses",
// Panel
"libpanel-dev": "ncurses",
// Menu
"libmenu-dev": "ncurses",
// Form
"libform-dev": "ncurses",
// SLANG
"libslang2-dev": "slang2",
// Newt
"libnewt-dev": "newt",
// CDK
"libcdk5-dev": "cdk",
// ADNS
"libadns1-dev": "adns",
// Anet
"libanet-dev": "anet",
// APR
"libapr1-dev": "apr",
// APR-Util
"libaprutil1-dev": "apr-util",
// ASpell
"libaspell-dev": "aspell",
// Hunspell
"libhunspell-dev": "hunspell",
// HSpell
"libhspell-dev": "hspell",
// Voikko
"libvoikko-dev": "libvoikko",
// Zemberek
"libzemberek-dev": "zemberek",
// Zinnia
"libzinnia-dev": "zinnia",
// Teckit
"libteckit-dev": "teckit",
// Graphite
"libgraphite2-dev": "graphite2",
// Raptor
"libraptor2-dev": "raptor2",
// Rasqal
"librasqal3-dev": "rasqal",
// Redland
"librdf0-dev": "redland",
// Serd
"libserd-dev": "serd",
// Sord
"libsord-dev": "sord",
// SRATOM
"libsratom-dev": "sratom",
// LILV
"liblilv-dev": "lilv",
// LV2
"lv2-dev": "lv2",
// SUIL
"libsuil-dev": "suil",
// DSSI
"libdssi-dev": "dssi",
// LADSPA
"libladspa-sdk-dev": "ladspa-sdk",
// VST
"vst3sdk-dev": "vst3sdk",
// CLAP
"clap-dev": "clap",
// BS2B
"libbs2b-dev": "libbs2b",
// LADSPA (again)
"ladspa-sdk": "ladspa-sdk",
// CAPS
"caps": "caps",
// TAP
"tap-plugins": "tap-plugins",
// CMT
"cmt": "cmt",
// SWH
"swh-plugins": "swh-plugins",
// FFAUDIO
"libffado-dev": "libffado",
// ALSA (again)
"libasound-dev": "alsa-lib",
// FireWire
"libraw1394-dev": "libraw1394",
// IEC61883
"libiec61883-dev": "libiec61883",
// AV1394
"libavc1394-dev": "libavc1394",
// DC1394
"libdc1394-dev": "libdc1394",
// GLIB (already defined above)
// "libglib2.0-dev": "glib2.0",
// GObject (again)
"libgobject2.0-dev": "glib2.0",
// GModule (again)
"libgmodule2.0-dev": "glib2.0",
// GIO (again)
"libgio2.0-dev": "glib2.0",
// GThread (again)
"libgthread2.0-dev": "glib2.0",
// Mount
"libmount-dev": "util-linux",
// BLKID
"libblkid-dev": "util-linux",
// UUID (already defined above)
// "libuuid-dev": "util-linux",
// SELinux
"libselinux1-dev": "selinux",
// SEManage
"libsemanage-dev": "semanage",
// SECureDB
"libsecomp-dev": "libseccomp",
// Audit
"libauparse-dev": "audit",
// E2FSProgs
"libext2fs-dev": "e2fsprogs",
// ComErr
"libcom-err2-dev": "e2fsprogs",
// SS
"libss2-dev": "e2fsprogs",
// Magic
"libmagic-dev": "file",
// ACap
"libcap-dev": "libcap2",
// ACap-NG
"libcap-ng-dev": "libcap-ng",
// AppArmor
"libapparmor-dev": "apparmor",
// Tomoyo
"libtomoyotools-dev": "tomoyo-tools",
// SMACK
"libsmack-dev": "smack",
// TOMOYO (again)
"tomoyo-tools": "tomoyo-tools",
// IMA-EVM
"ima-evm-utils": "ima-evm-utils",
// TSS2
"libtss2-dev": "tpm2-tss",
// FAPI
"libfapi-dev": "tpm2-tss",
// TCTI
"libtcti-dev": "tpm2-tss",
// ESYS
"libesys-dev": "tpm2-tss",
// MU
"libmu-dev": "mailutils",
// Guile
"guile-3.0-dev": "guile-3.0",
// GMP (already defined at line 346)
// "libgmp-dev": "gmp",
// Ncurses (variant)
"libncursesw5-dev": "ncurses",
// Readline (already defined at line 369)
// "libreadline-dev": "readline",
// Texinfo
"texinfo": "texinfo",
// TexLive
"texlive": "texlive-base",
// Doxygen
"doxygen": "doxygen",
// Graphviz
"graphviz-dev": "graphviz",
// PLplot
"libplplot-dev": "plplot",
// GSL
"libgsl-dev": "gsl",
// FFTW
"libfftw3-dev": "fftw3",
// BLAS
"libblas-dev": "blas",
// LAPACK
"liblapack-dev": "lapack",
// ATLAS
"libatlas-base-dev": "atlas",
// OpenBLAS
"libopenblas-dev": "openblas",
// SuiteSparse
"libsuitesparse-dev": "suitesparse",
// ARPACK
"libarpack2-dev": "arpack",
// PARPACK
"libparpack2-dev": "arpack",
// SuperLU
"libsuperlu-dev": "superlu",
// METIS
"libmetis-dev": "metis",
// Scotch
"libscotch-dev": "scotch",
// MUMPS
"libmumps-dev": "mumps",
// Hypre
"libhypre-dev": "hypre",
// PETSc
"libpetsc-dev": "petsc",
// SLEPc
"libslepc-dev": "slepc",
// Trilinos
"trilinos-all-dev": "trilinos",
// Boost
"libboost-all-dev": "boost-defaults",
// Eigen3
"libeigen3-dev": "eigen3",
// Dune
"libdune-common-dev": "dune-common",
// FEniCS
"fenics": "fenics",
// Deal.II
"libdeal.ii-dev": "deal.ii",
// CGAL
"libcgal-dev": "cgal",
// PPL
"libppl-dev": "ppl",
// NTL
"libntl-dev": "ntl",
// FLINT
"libflint-dev": "flint",
// Arb
"libarb-dev": "arb",
// Antic
"libantic-dev": "antic",
// Calcium
"libcalcium-dev": "calcium",
// NF
"libnf-dev": "nf",
// GF2X
"libgf2x-dev": "gf2x",
// M4RI
"libm4ri-dev": "m4ri",
// M4RIE
"libm4rie-dev": "m4rie",
// LinBox
"liblinbox-dev": "linbox",
// IML
"libiml-dev": "iml",
// BLAD
"libblad-dev": "blad",
// CADO
"cado-nfs-dev": "cado-nfs",
// PARI
"libpari-dev": "pari",
// Symmetrica
"symmetrica-dev": "symmetrica",
// Lidia
"liblidia-dev": "lidia",
// NTL (already defined above)
// "libntl-dev": "ntl",
// OpenSSL (already defined above)
// "libssl-dev": "openssl",
// OpenSSH
"libssh-dev": "libssh",
// OpenSSH2
"libssh2-1-dev": "libssh2",
// Neon
"libneon27-dev": "neon27",
// Serf
"libserf-1-dev": "serf",
// Subversion
"libsvn-dev": "subversion",
// RHash
"librhash-dev": "rhash",
// XXHASH
"libxxhash-dev": "xxhash",
// HighwayHash
"libhighwayhash-dev": "highwayhash",
// CityHash
"libcityhash-dev": "cityhash",
// MurmurHash
"libmurmurhash-dev": "murmurhash",
// SpookyHash
"libspookyhash-dev": "spookyhash",
// FarmHash
"libfarmhash-dev": "farmhash",
// MetroHash
"libmetrohash-dev": "metrohash",
// t1ha
"libt1ha-dev": "t1ha",
// PRVHASH
"libprvhash-dev": "prvhash",
// Wyhash
"libwyhash-dev": "wyhash",
// rapidhash
"librapidhash-dev": "rapidhash",
// SHA3
"libsha3-dev": "sha3",
// Blake2
"libblake2-dev": "blake2",
// Blake3
"libblake3-dev": "blake3",
// KangarooTwelve
"libk12-dev": "k12",
// SHAKE
"libshake-dev": "sha3",
// TupleHash
"libtuplehash-dev": "sha3",
// ParallelHash
"libparallelhash-dev": "sha3",
// cSHAKE
"libcshake-dev": "sha3",
// TurboSHAKE
"libturboshake-dev": "turbo",
// Ascon
"libascon-dev": "ascon",
// ISAP
"libisap-dev": "isap",
// DryGascon
"libdrygascon-dev": "drygascon",
// Gimli
"libgimli-dev": "gimli",
// Xoodoo
"libxoodoo-dev": "xoodoo",
// Keccak
"libkeccak-dev": "keccak",
// FNV
"libfnv-dev": "fnv",
// Murmur (already defined above)
"libmurmurhash3-dev": "murmurhash",
// CityHash (already defined above)
// "libcityhash-dev": "cityhash",
}
return mappings[binary]
}