Live data from Hacker News

Path Isn't Real on Linux

blog.danielh.cc

101–110 of 120 posts

Re: Path Isn't Real on Linux

#101
Uh yeah duh. But I through waiting for him to discover hash in the shell. No such luck. Guess it's in the magic somewhere. (Do man hash or something if you have no idea what I'm talking about)

Re: Path Isn't Real on Linux

#102

Earlier quoted context omitted.

Username checks out. I think one of the most surprising things I learned about bash is that you can do this: touch ./-rf rm * And now you have rm -rf'd. :)

Indeed, always prefer ./* to * I often wish there was a convenient way of doing such an operation in the shell: if path start with "/", leave it, otherwise prepend "./"

> I often wish there was a convenient way of doing such an operation in the shell: if path start with "/", leave it, otherwise prepend "./"

Both bash and zsh have enough functionality exposed via shell functions and variables for you to define a keybinding that does exactly this, interactively. Good idea.

Did you mean an interactive command? Or something else?

Re: Path Isn't Real on Linux

#103
post #7

Why would strace cat be useful here? By the time cat runs, it was obviously already found. It is basic knowledge that PATH is used by a command interpreter to locate the pathname of binaries. This is true for Window's cmd.exe as well. I never heard of a system where locating files for execution was performed by a kernel.

The kernel's job is to execute executable files, while the shell's job is to bridge the gap between a user-facing command name ("cat") and an executable file (/usr/bin/cat). The PATH environment variable provides such a good general and transparent way to control this task that most shells on most operating systems work that way.

Re: Path Isn't Real on Linux

#104
post #25

Fun fact: if you've ever had bash (or another shell) complain that a file doesn't exist, even though it's on $PATH, check if it's been cached by `hash`. If the file is moved elsewhere on $PATH and bash has the old path cached, you will get an ENOENT. The entire cache can be invalidated with `hash -r`.

I think bash has an alias “rehash” that does the same as hash -r too. But zsh doesn’t have it, so “hash -r” has entered my muscle memory, as it works in both shells. Edit: wrong shell, zsh has rehash, bash does not.

the odd thing is, at some point I ended up with `hash -R` as muscle memory that I always type before I correct it to a lower case r, and I'm not sure why, I can't remember any shell that uses `-R`.

Re: Path Isn't Real on Linux

#105

Earlier quoted context omitted.

Indeed, always prefer ./* to * I often wish there was a convenient way of doing such an operation in the shell: if path start with "/", leave it, otherwise prepend "./"

> I often wish there was a convenient way of doing such an operation in the shell: if path start with "/", leave it, otherwise prepend "./" Both bash and zsh have enough functionality exposed via shell functions and variables for you to define a keybinding that does exactly this, interactively. Good idea. Did you mean an interactive command? Or something else?

I meant non-interactive, for use in scripts which take user input. We already have "--" for end of options, but the support for it is not universal and even with that some programs will interpret certain strings in a special way. On the other hand, prepending the dot-slash should work for any program or argument passing style.

Re: Path Isn't Real on Linux

#106
post #63

The Linux kernel also doesn't have any concept of shared libraries, which are resolved by ld.so, a program that's usually shipped as part of libc. I like this approach of shunting off functionality that's important, necessary, and omnipresent across all OSes to userspace, rather than giving into the temptation to put everything and the kitchen sink into the kernel. It seems to make a more versatile and future proof O…

I've worked with "both sides" and the way ELF shared libraries on Linux work is an absolute bloody mess compared to how Windows' PE works. On Windows the same executable format and dynamic linker are usable in both user and kernel mode.

to be fair to linux, elf was bolted on after a few years, the original linux used a variant of coff without shared library support.

Re: Path Isn't Real on Linux

#107

Earlier quoted context omitted.

Bah, you’re right! I got it backwards, it’s zsh that has rehash, bash does not. And hash -r works in both. I guess I’ve been using zsh longer than I thought, because I learned about rehash first, then made the switch to hash -r later. I started using zsh 14 years ago, and bash 20+ years ago, so my brain assumed “I learned about rehash first” must have been back when I was using bash. zsh is still “that new thing” in…

If there is something nice that one has and one does not have. zsh is the one that has it.

Counterpoint, /dev/udp pseudo-devices in bash.

Re: Path Isn't Real on Linux

#108
post #63

The Linux kernel also doesn't have any concept of shared libraries, which are resolved by ld.so, a program that's usually shipped as part of libc. I like this approach of shunting off functionality that's important, necessary, and omnipresent across all OSes to userspace, rather than giving into the temptation to put everything and the kitchen sink into the kernel. It seems to make a more versatile and future proof O…

This is even reflected in the ELF format itself. There's this really arcane dichotomy between sections and segments. Sections are very detailed metadata that all sorts of things use for all sorts of purposes. Compilers use them. Debuggers use them. Static and dynamic linkers use them. Anyone can use them for any purpose whatsoever. You can easily add your own custom sections to any executable using tools like objcopy…

This is really great information. Thanks for this.

Re: Path Isn't Real on Linux

#109

The title is nonsense. PATH is the name of an environment variable (a Real Thing(TM) ) which lists a set of directories to search for an executable. It is used by shells (including those running on Linux) to locate an executable when the full path to the executable is not supplied by the user. This is needed because the exece()/execve() [2] kernel system call is unaware of things like environment variables so it will…

Reading the code to things is perfectly fine, actually.

It's fine to understand what the code is doing in a shallow way. But this leaves out a lot of important information. Information that isn't immediately obvious just by reading code, that can help you avoid problems and understand the system in-depth, without years of trial and error. Which is why they wrote a manual. You can also both read the code and the manual, but the manual will give you much more knowledge in a smaller amount of time.

Re: Path Isn't Real on Linux

#110
post #68

Earlier quoted context omitted.

Is this an old behavior? I would think ENOENT would invalidate the cache entry at least.

Isn't cache invalidation one of the hard problems?

Sure but not doing it on ENOENT suggests they’re just being completely lazy. Not to mention that they do have the tools (eg inotify watches) to proactively remove stale entries based on HD changes. Of course I’d be careful about the proactive one as it’s really easy to screw things up more (eg 100 bash instances all watching the same PATH directories might get expensive or forgetting to only do this for interactive mode connected to a TTY)
Post reply on HN