Skip to content

tool_shadow_path Misses a Doubled-Slash or Dot-Segment Spelling of BIN_DIR #1865

Description

@ptr727

What Happens

tool_shadow_path (host-setup/linux/install-tools.sh, fixed for plain PATH ordering and a single
trailing slash in #1644) still compares a PATH entry to $BIN_DIR with a literal string equality,
[[ $dir == "$BIN_DIR" ]]. A PATH entry that names the same directory through a different but
equivalent spelling, a doubled slash (/usr/local/bin//) or a dot segment (/usr/local/./bin),
does not match, so the walk treats $BIN_DIR's own managed binary as a shadow of itself.

The Property That Triggers It

A PATH containing $BIN_DIR spelled with a doubled slash or a . segment, ahead of the plain
spelling or with no plain spelling present at all. type -P, which the pre-#1644 code called,
already resolved this identically (type -P also returns the doubled or dotted spelling verbatim
for such an entry), so this is a pre-existing defect rather than one #1644 introduced.

Impact

tool_note reports the managed copy as "installed outside $BIN_DIR" or as shadowing itself.
apply_tool in --upgrade mode calls tool_unshadow, which prompts to remove the very binary
--upgrade is about to reinstall over. The user-visible effect is a confusing, spurious
remove-then-reinstall prompt rather than data loss, since the same file is what gets reinstalled
immediately after, but it undermines the report's claim that the location it names is a problem.

Repro (constructed, no host tool touched)

BIN_DIR=/usr/local/bin
mkdir -p /tmp/probe && printf '#!/bin/sh\necho ok\n' > /tmp/probe/widget && chmod +x /tmp/probe/widget
ln -s /tmp/probe /usr/local/bin_probe 2>/dev/null || true   # illustrative only, not required to repro
PATH="/usr/local/bin//:$PATH" type -P widget   # a real host would substitute the actual tool name

A PATH entry spelled $BIN_DIR// or $BIN_DIR/. produces a candidate path that string-compares
unequal to $BIN_DIR even though it names the same directory.

Suggested Fix

Normalize both sides before comparing, or use [[ $dir -ef $BIN_DIR ]] (bash's file-identity test,
confirmed to work on directories) as an additional check alongside the literal comparison, so a
directory that resolves to the same inode as $BIN_DIR is never reported as its own shadow.

Found during the local-strict-review pass on #1864 (the PR fixing #1644), scoped out of that PR
since it is a narrower, pre-existing edge case rather than part of the ordering defect #1644 fixed.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't workingscriptA defect in hub tooling

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions