You are not logged in.

#1 2011-12-12 04:56:10

fsckd
Forum Fellow
Registered: 2009-06-15
Posts: 4,173

Leave out the hashbang...

Or mangle the hashbang, etc.

This piques my interest,

falconindy wrote:

Lack of a (valid) interpreter causes the kernel to invoke the script with /bin/sh.

Example code (with exec bit set in mode) could be something like,

echo $(date)

fish shell gives this output when I try to run,

fish: Failed to execute process './foo'. Reason:
exec: Exec format error
fish: The file './foo' is marked as an executable but could not be run by the operating system.

and bash runs as if everything is fine giving the current date and time as output.

So what is the difference between the two shells? Clearly they are either using different calls or handling the error differently.

fish calls execve for which this error can be given,

man 3 execve wrote:

ENOEXEC    An executable is not in a recognized format, is for the wrong architecture, or has some other format error that means it cannot be executed.

That would be what fish gets when it tries to call a script with a mangled/absent hashbang.

bash has this comment in it's source,

   1) fork ()
   2) connect pipes
   3) look up the command
   4) do redirections
   5) execve ()
   6) If the execve failed, see if the file has executable mode set.
   If so, and it isn't a directory, then execute its contents as
   a shell script.

That's what seems to happen with the actual call occurring in a function named shell_execve. bash handles the error quite differently from fish and makes several more tries to exec the file.

I may be totally mistaken and that function is never used in the running code, left as a honeytrap for lazy tramps such as myself. Anyhow, this was enlightening. I'm fairly certain tcsh also does not throw an error as fish does. Perhaps tomorrow...


aur S & M :: forum rules :: Community Ethos
Resources for Women, POC, LGBT*, and allies

Offline

#2 2011-12-12 10:52:31

falconindy
Developer
From: New York, USA
Registered: 2009-10-22
Posts: 4,111
Website

Re: Leave out the hashbang...

fsckd wrote:

bash has this comment in it's source,

   1) fork ()
   2) connect pipes
   3) look up the command
   4) do redirections
   5) execve ()
   6) If the execve failed, see if the file has executable mode set.
   If so, and it isn't a directory, then execute its contents as
   a shell script.

That's what seems to happen with the actual call occurring in a function named shell_execve. bash handles the error quite differently from fish and makes several more tries to exec the file.

Neat. I clearly don't dive into Bash source enough. This also appears to be a "feature" of POSIX shells (e.g. dash supports the final check).

Last edited by falconindy (2011-12-12 11:00:27)

Offline

#3 2011-12-26 10:10:19

jnjackins
Member
From: Calgary, Alberta
Registered: 2009-12-05
Posts: 9
Website

Re: Leave out the hashbang...

This goes further back, to the Bourne shell, and I would guess it worked this way in Ken's sh too. The chapter on shell programming in The Unix Programming Environment by Kernighan and Pike describes writing shell programs in this way. (I don't think it makes any mention of using a #! line.)

Offline

Board footer

Powered by FluxBB