[arch-projects] [initscripts] [PATCH] Setting Locale: fix status reporting FAIL erroneously

Dave Reisner d at falconindy.com
Sun Jun 26 10:06:45 EDT 2011


On Sun, Jun 26, 2011 at 03:12:24PM +0200, Kurt J. Bosch wrote:
> Tom Gundersen, 2011-06-26 13:51:
> >On Sun, Jun 26, 2011 at 1:03 PM, Kurt J. Bosch
> ><kjb-temp-2009 at alpenjodel.de>  wrote:
> >>The following test case (run in a terminal)
> >>
> >>#!/bin/bash
> >>
> >># custom override example
> >>stat_busy() {
> >>        if (( PUSH_MSG )); then
> >>                # This triggers the error in "$@" below
> >>                # actual code was:
> >>                # echo set message "$1">  "$spl_fifo"&
> >>                :&
> >>        fi
> >>        echo "$1" BUSY
> >>}
> >>
> >>status() {
> >>        stat_busy "$1"
> >>        shift
> >>        "$@"
> >>        local retval=$?
> >>        (( retval == 0 ))&&  echo DONE || echo FAIL "($retval)"
> >>}
> >>
> >>PUSH_MSG=0 status "test #0" cat<(echo foo)
> >>PUSH_MSG=1 status "test #1" cat<(echo foo)
> >
> >[...]
> >
> >>CCing Tom Gundersen.
> >
> >Thanks.
> >
> >I have not figured it out, but here is a more minimal test:
> >
> >
> >#!/bin/bash
> >
> >
> >test_one() {
> >        : &
> >        "$@"
> >}
> >
> >test_two() {
> >        :
> >        "$@"
> >}
> >
> ># working
> >test_one eval 'cat<(echo foo)'
> >test_two cat<(echo foo)
> >
> >#not working
> >test_one cat<(echo foo)
> 
> Confirmed.
> 
> -- 
> Kurt

Now I see it (at least in Tom's example). It's expected behavior. You're
only allowed to read the file descriptor created by a PE once. However,
because file descriptors are inherited by subshells, when the subshell
ends, the file descriptor is closed and it goes away. Look at what
happens when you modify the script slightly:

-------------------

#!/bin/bash

test_one() {
  ls /dev/fd/
  : &
  ls /dev/fd/
  "$@"
}

test_one cat <(echo foo)

-------------------

And then run it with debug output....

+foo[11]: test_one cat /dev/fd/63
+foo[4]: ls /dev/fd/
++foo[11]: echo foo
0  1  2  3  63
+foo[6]: ls /dev/fd/
+foo[5]: :
0  1  2  3
+foo[7]: cat /dev/fd/63
cat: /dev/fd/63: No such file or directory

The subshell inherits the descriptor and closes it on exit, destroying
it for the parent. The eval "works" because the FD for the process
substitution isn't created until _after_ the subshell.

Can we _not_ do this? Our old solution didn't require voodoo like this,
and it worked just fine (albeit a few more SLOC). Not everything needs
to be a one line operation. Perhaps we could just write a simple
function to take care of all these 1 line files that we write to:

write_oneline_file() {
  local file=$1 line=$2 mode=$3

  printf '%s\n' "$line" >"$file"
  [[ $mode ]] && chmod "$mode" "$file"
}

Which satisfies both parties, as it appears to be a one liner in
execution, but it's actually sane on the back end.

d



More information about the arch-projects mailing list