Issue: fzf tmux integration broken with uutils-coreutils
Problem Description
fzf key bindings (Ctrl-T, Ctrl-R) stopped working in tmux sessions after adding uutils-coreutils-noprefix to home-manager configuration. The error manifested as:
mkfifo: invalid mode: invalid digit found in string
fzf-file-widget:zle:3: widgets can only be called when ZLE is active
Initial Investigation Path
1. Suspected tmux Configuration Issues
- Hypothesis: tmux prefix key (C-s) was capturing key range
- Investigation: Checked tmux key bindings and configuration
- Result: ❌ Not the root cause - tmux config was correct
2. Suspected tmux 3.5a Breaking Changes
- Hypothesis: Recent tmux version changes affected shell integration
- Investigation: Found home-manager issue #5952 about tmux 3.5a shell handling changes
- Result: ❌ Related but not the direct cause
3. Suspected fzf Shell Integration
- Investigation:
- Verified fzf functions were loaded (
fzf-file-widget exists)
- Confirmed key bindings were correct (
"^T" fzf-file-widget)
- Tested ZLE status (was active:
$options[zle] = on)
- Result: ❌ Shell integration was working correctly
4. Environment Comparison Testing
- Method: Tested fzf behavior inside vs outside tmux
- Discovery: Same
mkfifo error occurred in both environments
- Key insight: Issue wasn't tmux-specific
Root Cause Discovery
The Breakthrough
During testing, user mentioned recently adding:
uutils-coreutils-noprefix # Rust rewrite of the GNU coreutils
Confirmation Test
Commenting out uutils-coreutils-noprefix immediately fixed the issue, confirming the root cause.
Technical Analysis
The issue occurred because:
- GNU vs Rust syntax differences: fzf shell integration uses
mkfifo -m o+w (GNU syntax)
- uutils-coreutils incompatibility: The Rust implementation expects octal modes like
-m 622
- Argument parsing failure:
mkfifo -m o+w caused "invalid mode" error in uutils implementation
Solutions Explored
Solution 1: Remove Problematic Package ✅ (Temporary)
# uutils-coreutils-noprefix # Commented out
- Pros: Immediate fix
- Cons: Lose performance benefits of Rust coreutils
Solution 2: Remove Only mkfifo ✅ (Simple)
uutils-coreutils-no-mkfifo = pkgs.uutils-coreutils-noprefix.overrideAttrs (oldAttrs: {
postInstall = (oldAttrs.postInstall or "") + ''
rm -f $out/bin/mkfifo # Let system use GNU version
'';
});
- Pros: Keep Rust performance for other tools, simple implementation
- Cons: Lose Rust implementation for mkfifo entirely
Solution 3: GNU Compatibility Wrapper ✅ (Elegant)
uutils-coreutils-fzf-compat = pkgs.uutils-coreutils-noprefix.overrideAttrs (oldAttrs: {
postInstall = (oldAttrs.postInstall or "") + ''
# Create GNU-compatible wrapper for mkfifo
mv $out/bin/mkfifo $out/bin/.mkfifo-uutils
cat > $out/bin/mkfifo << 'EOF'
#!/usr/bin/env bash
set -euo pipefail
# Find the actual uutils coreutils multicall binary
uutils_coreutils="$(dirname "$(readlink -f "$0")")/.mkfifo-uutils"
# Handle GNU coreutils compatibility for fzf
if [[ $# -ge 2 && "$1" == "-m" && "$2" == "o+w" ]]; then
# Convert GNU syntax to octal: o+w = 622 (owner rw, group w, other w)
shift 2
exec "$uutils_coreutils" mkfifo -m 622 "$@"
else
# Pass through all other arguments unchanged
exec "$uutils_coreutils" mkfifo "$@"
fi
EOF
chmod +x $out/bin/mkfifo
'';
});
Key Technical Insights
uutils-coreutils Architecture
- Uses multicall binary approach (single
coreutils executable)
- Determines tool behavior via symlink name or explicit subcommand
- When calling directly:
coreutils mkfifo -m 622 file (not just coreutils -m 622 file)
Wrapper Design Patterns
- Hidden file pattern:
mv mkfifo .mkfifo-uutils (dot prefix hides implementation detail)
- Runtime path resolution:
$(dirname "$(readlink -f "$0")") for build-time → runtime compatibility
- Transparent compatibility: Wrapper intercepts specific GNU syntax while passing through everything else
Permission Translation
- GNU syntax:
-m o+w (symbolic: owner+group+other write)
- Octal equivalent:
-m 622 (owner: rw-, group: -w-, other: -w-)
Debugging Methodology Learnings
- Start with recent changes: "What changed recently?" led to the breakthrough
- Environment isolation: Testing inside/outside tmux helped rule out tmux-specific issues
- Incremental hypothesis testing: Systematically ruled out configuration, version, and integration issues
- Binary inspection: Understanding the multicall binary architecture was crucial for the final solution
Impact & Resolution
- Root cause: Package compatibility issue, not configuration problem
- Final solution: Elegant wrapper maintaining Rust performance with GNU compatibility
- Broader lesson: Alternative coreutils implementations can have subtle compatibility differences
This issue demonstrates the importance of compatibility layers when adopting modern tool replacements in complex environments.
Issue: fzf tmux integration broken with uutils-coreutils
Problem Description
fzf key bindings (Ctrl-T, Ctrl-R) stopped working in tmux sessions after adding
uutils-coreutils-noprefixto home-manager configuration. The error manifested as:Initial Investigation Path
1. Suspected tmux Configuration Issues
2. Suspected tmux 3.5a Breaking Changes
3. Suspected fzf Shell Integration
fzf-file-widgetexists)"^T" fzf-file-widget)$options[zle] = on)4. Environment Comparison Testing
mkfifoerror occurred in both environmentsRoot Cause Discovery
The Breakthrough
During testing, user mentioned recently adding:
Confirmation Test
Commenting out
uutils-coreutils-noprefiximmediately fixed the issue, confirming the root cause.Technical Analysis
The issue occurred because:
mkfifo -m o+w(GNU syntax)-m 622mkfifo -m o+wcaused "invalid mode" error in uutils implementationSolutions Explored
Solution 1: Remove Problematic Package ✅ (Temporary)
# uutils-coreutils-noprefix # Commented outSolution 2: Remove Only mkfifo ✅ (Simple)
Solution 3: GNU Compatibility Wrapper ✅ (Elegant)
Key Technical Insights
uutils-coreutils Architecture
coreutilsexecutable)coreutils mkfifo -m 622 file(not justcoreutils -m 622 file)Wrapper Design Patterns
mv mkfifo .mkfifo-uutils(dot prefix hides implementation detail)$(dirname "$(readlink -f "$0")")for build-time → runtime compatibilityPermission Translation
-m o+w(symbolic: owner+group+other write)-m 622(owner: rw-, group: -w-, other: -w-)Debugging Methodology Learnings
Impact & Resolution
This issue demonstrates the importance of compatibility layers when adopting modern tool replacements in complex environments.