| git.druid.rocks | index | druid520 | mp | docs/ | reference/ | slots.btft |
docs/reference/slots.btft
[table class="topnav"]
[tr]
[td class="logotab"]mp[e]
[td][see name="index"]index[e][e]
[td][see name="guide/index"]guide[e][e]
[td][see name="reference/index"]reference[e][e]
[e]
[e]
[h1]slot[e]
guide/writing-a-port.html and guide/using-mp.html cover SLOT from a port-author and a user's perspective. this page is the resolution mechanics: how mp actually computes an effective slot, and how a dependency ends up linked against the exact variant it named.
[h2]resolve_slot: static + use-driven composition[e]
resolve_slot (mplib::portformat.pm) computes a port's effective slot from two independent inputs:
pkg_slot -- a plain, static string ("12"), or nothing at all (the unslotted default).
[br]
pkg_slot_use -- a space-separated list of USE flags whose enabled state each contributes a "-flag" suffix, in declared order, skipping any flag that's disabled.
[code]
sub resolve_slot {
my ($pc, $basename) = @_;
my $slot = $pc->{pkg_slot} || '';
return $slot unless $pc->{pkg_slot_use};
my $en = enabled_use($basename);
my @suffix = grep { $en->{$_} } split ' ', $pc->{pkg_slot_use};
return join('-', grep { $_ ne '' } ($slot, @suffix));
}
[e]
enabled_use is read under the port's BARE name, never the composed slot -- "curl:ssl" doesn't exist as a config section until curl has actually been resolved with ssl on, so the bare name is the only thing a USE= setting could plausibly have been written against. every other slotted lookup in mp (HOLD, MASK, hook_<phase>=, DEPS overrides) falls back to the same bare name for the identical reason -- see pconf_lookup/pconf_section in reference/architecture.html's util.pm section.
a compound slot ("12-glibc-znver3-O3") needs no special-case code anywhere: it's just a string. gcc versions, libcs, microarches, and optimization levels can all vary independently and coexist, each its own slot -- referenced as gcc:12-glibc-znver3-O3, same as any other slot.
[h2]buildlink wiring: dep_slot_prefixes[e]
a dependency reference that names a slot explicitly (pkg_deps="curl:ssl") needs more than "install curl:ssl" -- the DEPENDENT build has to actually find curl:ssl's headers and libs, not whichever curl happens to sit on the default search path. resolved_slotted_deps walks a port's own effective_deps, resolves each %tag/bare reference to the concrete db key it's actually installed under, and keeps only the ones that resolved to a real (non-"0") slot. dep_slot_prefixes then maps each of those to its install prefix (INSTPREFIX/base-slot), and mpx.c's runsh turns the resulting colon-joined MP_DEP_PREFIXES list into one -I/-L/-Wl,-rpath/PKG_CONFIG_PATH entry per prefix -- see reference/architecture.html's mpx.c section for the actual flag construction.
a bare, unqualified dependency (pkg_deps="curl", no slot) is unaffected by any of this: resolved by pkg_pref among installed candidates, exactly like before SLOT existed at all.
[h2]conflicts, checked slot-aware[e]
check_static_conflicts matches a pkg_conflicts entry against the db two ways: an exact match (an entry that itself names a slot, "somepkg:variant", matches only that one installed variant), or a bare-name match against ANY installed slot of that name (the common case -- an author writes pkg_conflicts="other-libc" once, and it correctly conflicts with other-libc regardless of which slot happens to be installed). see ports/libcs/musl and glibc for the canonical two-libcs-can't-coexist case.
[h2]revdep: the removal safety net[e]
removing a slot something else still links against (via the buildlink wiring above) is blocked by default:
[code]
err: curl:ssl cannot be removed: still linked against by: somepkg (--force to override)
[e]
"mp revdep curl:ssl" shows the same "who's linked against this" list without attempting a remove, so you can check before deciding. this is tracked in linkdeps.db, written by write_linkdeps_for alongside the normal install db entry -- one more piece of per-package state, same lifecycle as the install db and file manifest.
[h2]backtracking and %tag resolution[e]
pick_provider (used whenever a %tag dependency isn't pinned by TARGET_<tag>=) tries providers lowest-pkg_pref-first, and if the lowest would conflict with something already installed, tries the next one instead of failing outright -- this is a plain provider-choice search, not slot-specific, but it interacts with SLOT whenever the providers themselves are different slots of the same underlying port. if every provider conflicts, mp prompts interactively at a terminal, or fails cleanly with no prompt otherwise.