Discussion:
Best way to suppress the error message in $(< nonexistent_file)
(too old to reply)
Peng Yu
2018-11-28 12:01:31 UTC
Permalink
Hi,

I only find the exec way to suppress the error message of $(<
nonexistent_file). But the syntax doesn't look very nice. Is there a
better way to do so? Thanks.

x=$(< nonexistent_file) 2> /dev/null # This doesn't work.

exec 3>&2 2>&- # This works
x=$(< nonexistent_file)
exec 2>&3 3>&-
--
Regards,
Peng
Pierre Gaston
2018-11-28 12:04:39 UTC
Permalink
Post by Peng Yu
Hi,
I only find the exec way to suppress the error message of $(<
nonexistent_file). But the syntax doesn't look very nice. Is there a
better way to do so? Thanks.
x=$(< nonexistent_file) 2> /dev/null # This doesn't work.
exec 3>&2 2>&- # This works
x=$(< nonexistent_file)
exec 2>&3 3>&-
--
Regards,
Peng
{ x=$( <doesnotexist) ;} 2>&-
Peng Yu
2018-11-28 13:59:10 UTC
Permalink
Post by Pierre Gaston
{ x=$( <doesnotexist) ;} 2>&-
OK. Thanks. BTW, I think that 2>&- the same as 2>/dev/null
semantically the same. Is it so? Regarding the underlying operations,
are they exactly the same or they are slightly different? My
understanding is the former sets stderr to a null handle, but the
latter set stderr to an existing file handle, but the file handle is
/dev/null. So I'd think the former is a little faster. Is it? Thanks.
--
Regards,
Peng
Greg Wooledge
2018-11-28 14:11:53 UTC
Permalink
Post by Peng Yu
Post by Pierre Gaston
{ x=$( <doesnotexist) ;} 2>&-
OK. Thanks. BTW, I think that 2>&- the same as 2>/dev/null
semantically the same. Is it so?
No. One of them redirects stderr to /dev/null and the other closes
stderr completely.

In the general case, commands that expect to be able to write error
messages to stderr will blow up if you use 2>&-. It may work HERE
since there is no external command being invoked. It's still a really
bad practice, and you SHOULD NOT get into the habit of doing it.

https://mywiki.wooledge.org/BashPitfalls#pf55
Pierre Gaston
2018-11-28 14:12:33 UTC
Permalink
Post by Peng Yu
Post by Pierre Gaston
{ x=$( <doesnotexist) ;} 2>&-
OK. Thanks. BTW, I think that 2>&- the same as 2>/dev/null
semantically the same. Is it so? Regarding the underlying operations,
are they exactly the same or they are slightly different? My
understanding is the former sets stderr to a null handle, but the
latter set stderr to an existing file handle, but the file handle is
/dev/null. So I'd think the former is a little faster. Is it? Thanks.
No it's not the same. File descriptors are like pointers to structures the
kernel uses to track
the status of files,
When you do >/dev/null you "open" a new file descriptor that points to a
special file.
The applications then write to this file normally.

On the contrary 2>&- closes the file descriptor so your descriptor does not
refer to anything
and you get an error if you try to use the descriptor:

$ echo >&-
-bash: echo: write error: Bad file descriptor

So an application using this descriptor may eg. crash.
Peng Yu
2018-11-28 15:56:30 UTC
Permalink
Post by Pierre Gaston
$ echo >&-
-bash: echo: write error: Bad file descriptor
So an application using this descriptor may eg. crash.
I don't quite understand. Why this command does not cause any error?

{ x=$( <doesnotexist) ;} 2>&-
--
Regards,
Peng
Chet Ramey
2018-11-28 16:41:09 UTC
Permalink
Post by Peng Yu
Post by Pierre Gaston
$ echo >&-
-bash: echo: write error: Bad file descriptor
So an application using this descriptor may eg. crash.
I don't quite understand. Why this command does not cause any error?
{ x=$( <doesnotexist) ;} 2>&-
Because the error message is written while stderr is still closed. It's
not restored until the group command completes.
--
``The lyf so short, the craft so long to lerne.'' - Chaucer
``Ars longa, vita brevis'' - Hippocrates
Chet Ramey, UTech, CWRU ***@case.edu http://tiswww.cwru.edu/~chet/
Loading...