Quote:
Originally Posted by ntubski
I think this is a buffering issue: depending on which buffer mode the shell is reading, it might read past the exit command so that other shells don't get the chance to read the whole file.
|
That would make a lot of sense, especially if
bash < bash-nest.txt replaces standard input with a descriptor to the regular file; however, I'd expect to see "level 1 destroy" instead of "level 3 destroy" in that case.
To explain the ouput in the first case, the initial process would have to read only until line 2, "level 1" to line 7, "level 2" to line 12, but "level 3" must read until at least line 31 to prevent the others from reading anything else.
Code:
1 # ===============
2 bash
3 echo level 1 create
4 echo $$ # This prints the PID of the current shell
5 echo
6
7 bash
8 echo level 2 create
9 echo $$
10 echo
11
12 bash
13 echo level 3 create
14 echo $$
15 echo
16
17 # ===============
18
19 echo level 3 destroy
20 echo $$
21 echo
22 exit
23
24 echo level 2 destroy
25 echo $$
26 echo
27 exit
28
29 echo level 1 destroy
30 echo $$
31 echo
32 exit
33
34 # ===============
The results are too uniform between our three systems; therefore, my next guess was it has to do with process control. Keep reading, though!
"level 3" doesn't read ahead like would happen if read-ahead was the issue; this is apparent if you replace the first
exit with
cat -n:
Code:
level 1 create
4826
level 2 create
4827
level 3 create
4828
level 3 destroy
4828
1
2 echo level 2 destroy
3 echo $$
4 echo
5 exit
6
7 echo level 1 destroy
8 echo $$
9 echo
10 exit
11
12 # ===============
This lead me to believe that the issue arises when the first input descriptor is closed; I thought
bash might have set the file position to the end. But again, here is a counter-example:
Code:
#something.txt
bash
echo $$
dd bs=1 count=1 &> /dev/null; exit
#echo something bad
echo $$
Code:
bash < something.txt
Code:
4899
something bad
4898
If you take out the
dd call, you don't see the output of the last
echo $$; my final final guess, then, is that
bash uses some
fcntl or
ioctl that makes other
bash instances exit (or run out of input) when the descriptor is closed, but only if nothing other-than the interpreter has touched it*. Additionally, this has no effect if the input descriptor is a pipe.
Kevin Barry
*I initially said "if non-
bash programs haven't touched it", but then I replaced the
dd call with
read something, which uses a
bash built-in, and the last
echo $$ showed up.