Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What corner cases must we consider when parsing $PATH on Linux?

I'm working on a C application that has to walk $PATH to find full pathnames for binaries, and the only allowed dependency is glibc (i.e. no calling external programs like which). In the normal case, this just entails splitting getenv("PATH") by colons and checking each directory one by one, but I want to be sure I cover all of the possible corner cases. What gotchas should I look out for? In particular, are relative paths, paths starting with ~ meant to be expanded to $HOME, or paths containing the : char allowed?

like image 228
Shea Levy Avatar asked Aug 19 '11 12:08

Shea Levy


4 Answers

One thing that once surprised me is that the empty string in PATH means the current directory. Two adjacent colons or a colon at the end or beginning of PATH means the current directory is included. This is documented in man bash for instance.

It also is in the POSIX specification.

So

PATH=:/bin
PATH=/bin:
PATH=/bin::/usr/bin

All mean the current directory is in PATH

like image 58
heijp06 Avatar answered Oct 20 '22 15:10

heijp06


I'm not sure this is a problem with Linux in general, but make sure that your code works if PATH has some funky (like, UTF-8) encoding to deal with directories with fancy letters. I suspect this might depend on the filesystem encoding.

I remember working on a bug report of some russian guy who had fancy letters in his user name (and hence, his home directory name which appeared in PATH).

like image 40
Frerich Raabe Avatar answered Oct 20 '22 17:10

Frerich Raabe


This is minor but I'll added it since it hasn't already been mentioned. $PATH can include both absolute and relative paths. If your crawling the paths list by chdir(2)ing into each directory, you need to keep track of the original working directory (getcwd(3)) and chdir(2) back to it at each iteration of the crawl.

like image 1
Joshua Hoblitt Avatar answered Oct 20 '22 15:10

Joshua Hoblitt


The existing answers cover most of it, but it's worth covering parts of the question that wasn't answered yet:

  1. $ and ~ are not special in the value of $PATH.
  2. If $PATH is not set at all, execvp() will use a default value.
like image 1
James Youngman Avatar answered Oct 20 '22 15:10

James Youngman