One is a stub ld-linux.so.5 that gets mad at you and exits. If you just compile a short program that write()s an error message with gcc -static -fPIC, it "works" as an interpreter.
The other option, which I think is a little more suitable, is to address this at the kernel level. The current code path in fs/binfmt_elf.c attempts to find the interpreter specified in the file, and if this returns an error, that errno returned is returned directly by exec. We can translate ENOENT (and perhaps other errors?) to ENOEXEC before returning. The patch attached has been tested on Intrepid, and should actually apply to kernel 2.6.20 onwards.
unpatched$ sed "s/ld-linux.so.2/ld-linux.so.1/" < /bin/ls > ls && chmod +x ls && ./ls
bash: ./ls: No such file or directory
patched$ sed "s/ld-linux.so.2/ld-linux.so.1/" < /bin/ls > ls && chmod +x ls && ./ls
-bash: ./ls: cannot execute binary file
According to the Open Group's copy of POSIX at http://opengroup.org/onlinepubs/009695399/functions/exec.html
ENOENT is only to be returned from execve if "path" or "file" doesn't exist, and ENOEXEC indicates the binary has an "unrecognized format".
So this seems like a reasonable (and very tiny) change to make. Could we get it in Ubuntu's kernel? I also plan to submit this to the LKML.
So I was looking into two workarounds for this.
One is a stub ld-linux.so.5 that gets mad at you and exits. If you just compile a short program that write()s an error message with gcc -static -fPIC, it "works" as an interpreter.
The other option, which I think is a little more suitable, is to address this at the kernel level. The current code path in fs/binfmt_elf.c attempts to find the interpreter specified in the file, and if this returns an error, that errno returned is returned directly by exec. We can translate ENOENT (and perhaps other errors?) to ENOEXEC before returning. The patch attached has been tested on Intrepid, and should actually apply to kernel 2.6.20 onwards.
unpatched$ sed "s/ld-linux. so.2/ld- linux.so. 1/" < /bin/ls > ls && chmod +x ls && ./ls
bash: ./ls: No such file or directory
patched$ sed "s/ld-linux. so.2/ld- linux.so. 1/" < /bin/ls > ls && chmod +x ls && ./ls
-bash: ./ls: cannot execute binary file
According to the Open Group's copy of POSIX at opengroup. org/onlinepubs/ 009695399/ functions/ exec.html
http://
ENOENT is only to be returned from execve if "path" or "file" doesn't exist, and ENOEXEC indicates the binary has an "unrecognized format".
So this seems like a reasonable (and very tiny) change to make. Could we get it in Ubuntu's kernel? I also plan to submit this to the LKML.