logo
Kurashizu Blogwhere ideas flow
  • Home
  • News
  • Blog
  • About
  • Home
  • News
  • Blog
  • About

© 2026 Kurashizu. All rights reserved.

Admin·New Post·Service Status
Powered by Cloudflare·31.10.26
← Back to news

The tilde in your PATH may not be your HOME

Original article
disconnect3d.pl|152 points|86 comments|by arusekk|Oct 11, 2026

The tilde in your PATH may not be your HOME

Posted on 2026-10-02 • Tags: #shell, #bash, #zsh, #security

While experimenting with the nono sandboxing utility, I encountered a rather peculiar warning:

PATH entries the sandbox can write to: ~/.local/bin/

At first glance, this seemed odd. Why would a sandbox be able to write to my home directory's bin folder? This led me to a realization about how shells handle the tilde (~) character.

The Core Issue: Tilde Expansion

If you have a line like this in your ~/.bashrc or ~/.zshrc:

export PATH = " $PATH :~/.local/bin/"

You might assume the ~ automatically converts to your home directory. It does not. Tilde expansion only occurs when the character is unquoted. As the official Bash documentation clarifies:

If a word begins with an unquoted tilde character (‘~’), all of the characters up to the first unquoted slash (…) are considered a tilde-prefix.

(…) Bash checks each variable assignment for unquoted tilde-prefixes immediately following a ‘:’ or the first ‘=’, and performs tilde expansion in these cases.

Mathematically, we can view the expansion function EEE as: E(" ")=HOMEif unquotedE(\text{"~"}) = \text{HOME} \quad \text{if unquoted}E(" ")=HOMEif unquoted E(" ")=" "if quotedE(\text{"~"}) = \text{"~"} \quad \text{if quoted}E(" ")=" "if quoted

Consequently, instead of adding /home/user/.local/bin/ to your environment, you are actually adding a literal path: ./~/.local/bin/.

Comparison of Methods

SyntaxResultStatusNote
PATH="$PATH:~/.local/bin/"Literal ~❌ WrongQuoted tildes don't expand.
PATH=$PATH:~/.local/binExpanded Path✅ WorksUnquoted expansion is active.
PATH="$PATH:$HOME/.local/bin/"Expanded Path🌟 BestExplicit and safe.

Relying on unquoted assignments is a great idea →\rightarrow→ Actually, it is fragile. For instance, adding a single accidental whitespace will break the variable assignment entirely.

Proof of Concept

To demonstrate this, I created a scenario where a binary is executed from a literal tilde directory rather than the actual home folder:

# Create a literal directory named '~' in the current folder
$ mkdir -p ./~/.local/bin/ 

# Compile a simple C program into that directory
$ printf '#include stdio.h \nint main() { puts("hello"); }' a.c 
$ gcc a.c -o ./~/.local/bin/kek 

# Set PATH to the literal tilde path and run the binary
$ PATH = "~/.local/bin/" 
$ kek 
hello

The resulting directory structure looks like this:

As shown by the tree -f . output, the kek binary was found and executed from ./~/.local/bin/. The actual $HOME directory was never accessed.

Demo showing that a literal tilde in PATH resolves to a ./~/ directory in the current working directory

How to Audit and Fix Your Setup

You can verify if your PATH is contaminated with literal tildes using these commands:

  • Quick check: echo "$PATH" | grep -- '~'
  • Detailed list: echo "$PATH" | tr ':' '\n' | grep '~'

If you see ~/.local/bin/ (or similar) in the output, follow these steps:

  • Open your configuration file (.bashrc, .zshrc, or .profile).
  • Locate the PATH export line.
  • Replace ~ with the $HOME variable.
  • Restart your shell or run source ~/.bashrc.

nono warning about PATH entries the sandbox can write to

Finally, a shout-out to the nono tool for flagging this security quirk, although the warning message could be a bit more descriptive (I'll be submitting a PR to improve it!).