What is a valid use case for an "execute only" file permission?
Shell scripts require the read permission to be executed, but binary files do not:
$ cat hello.cpp
#include<iostream>
int main() {
std::cout << "Hello, world!" << std::endl;
return 0;
}
$ g++ -o hello hello.cpp
$ chmod 100 hello
$ ./hello
Hello, world!
$ file hello
hello: executable, regular file, no read permission
Displaying the contents of a file and executing them are two different things. With shell scripts, these things are related because they are "executed" by "reading" them into a new shell (or the current one), if you'll forgive the simplification. This is why you need to be able to read them. Binaries don't use that mechanism.
For directories, the execute permission is a little different; it means you can do things to files within that directory (e. g. read or execute them). So let's say you have a set of tools in /tools
that you want people to be able to use, but only if they know about them. chmod 711 /tools
. Then executable things in /tools
can be run explicitly (e. g. /tools/mytool
), but ls /tools/
will be denied. Similarly, documents could be stored in /private-docs
which could be read if and only if the file names are known.
On Gentoo, executable programs that are setuid (set to run with the permissions of their owner instead of their invoker) are denied read access (mode 4711). This is to add a layer of protection against exploitation of bugs to aid in privilege escalation.
If an unprivileged attacker can read a setuid file, and knows of a bug that allows a return-to-libc-style attack, they may be able to use the contents of the file to predict where certain useful functions or libraries are likely to be placed in memory when the program is invoked.
Modern systems often include additional protections that are more effective, such as ASLR, but the restrictions present in 32-bit platforms may leave them more easily exploitable.