Security Advisory: `makeBinaryWrapper`: empty PATH segments enable current-directory hijacking

Security Advisory: `makeBinaryWrapper`: empty PATH segments enable current-directory hijacking

Announcements - NixOS Discourse

Summary

makeBinaryWrapper/makeCWrapper implements --prefix/ --suffix by concatenating the given value onto a search-path environment variable (PATH, LD_LIBRARY_PATH…) without checking whether that value is empty.

When the value is empty (e.g. because the provided value was the result of lib.makeBinPath over an empty list) an empty path segment will be added into the variable. POSIX shells and execvp() will consider the empty path segment as the current working directory.

Impact

An attacker who can place a file with a specific name in a directory the victim later runs an affected tool from (an untrusted git checkout, a downloaded archive…) can get that file silently executed or loaded as a library.Go ErrDot for example).

Am I affected?

You are impacted if you are using a package using makeBinaryWrapper with --prefix/--suffix on a path value variable that can be empty during the build.

The nixpkgs security team identified the following impacted packages:

  • zellij
  • treefmt.withConfig (limited DoS due to Go restrictions)
  • docker CLI (limited DoS due to Go restrictions)
  • buildah (only for Darwin and limited DoS due to Go restrictions)
  • lispWithPackages
  • qt6Packages.fcitx5-with-addons
  • ocelot-desktop (only for x86_64-darwin)

zellij is the most critical one in the packages we identified due to its nature and the absence of other mitigations.

Note the list might not be exhaustive due to the large nixpkgs package set and potential usages outside of nixpkgs.

You can use the following script to identify binaries in your /nix/store that might be impacted by the issue:

#! /usr/bin/env nix-shell
#! nix-shell -i bash --pure
#! nix-shell -p findutils gnugrep gawk binutils

set -uo pipefail

STORE="${1:-/nix/store}"

printf 'BINARY\tFLAG\tENV_VAR\tVALUE\n'

while read -r f; do
grep -qF 'makeCWrapper' "$f" || continue

strings -a -- "$f" | awk -F"'" -v bin="$f" '
/--prefix |--suffix / {
flag = ($0 ~ /--prefix /) ? "--prefix" : "--suffix"
env = $2
sep = $4
val = $6
if (sep == "") next
wrapped_val = sep val sep
doubled = sep sep
if (index(wrapped_val, doubled) > 0) {
printf "%s\t%s\t%s\t[%s]\n", bin, flag, env, val
found = 1
}
}
END { exit (found ? 0 : 1) }
'
done < <(find "$STORE" -type f -executable)

What do I need to do?

Update, you can track the progress of the different pull-requests below.

Fixes:

Acknowledgement

Thank you to cielavenir for reporting the issue with the docker CLI to the nixpkgs security team.

Reference

1 post - 1 participant

Read full topic

Report Page