TCP connection, bash only

2019-03-08 19:56发布

问题:

I found this line in a script. While I globally understand what it does--opening a bidirectional TCP connection--, I need some explanations on the syntax. Here's the line:

exec 5<>"/dev/tcp/${SERVER}/${PORT}"

And my questions:

  1. < and > are usually used to redirect IOs. What does it mean there? Is it usable in another context? How?
  2. Why does it work, while /dev/tcp doesn't exists?
  3. Why 5? Can it be another number? What are the values allowed?
  4. Why is exec necessary? (given nothing is actually executed)

Thanks.

回答1:

< and > are usually used to redirect IOs. What does it mean there? Is it usable in another context? How?

It's the same - input and output is redirected to fd 5.

Why does it work, while /dev/tcp doesn't exists?

It's a special file: If host is a valid hostname or Internet address, and port is an integer port number or service name, bash attempts to open a TCP connection to the corresponding socket.

Why 5? Can it be another number? What are the values allowed?

Yes, it can be any value, but you need to ensure you don't use an fd already in use.

Why is exec necessary? (given nothing is actually executed)

exec means the redirection happens in the current shell, not within a subshell.



回答2:

I can only answer for the exec part:

exec without a command given may be used to change I/O redirections. <> in this case means open for read+write. 5 is the channel number (or file descriptor). This makes sense if other commands send their output / read their input from channel 5.

For "/dev/tcp/${SERVER}/${PORT}" I don't know if it's a feature of a specific Linux version or if it's a bash feature (I assume the latter).

-- EDIT: from the bash manual page: --

 Bash handles several filenames specially when they are  used
 in redirections, as described in the following table:

      /dev/fd/fd
           If fd is a valid integer, file  descriptor  fd  is
           duplicated.
      /dev/stdin
           File descriptor 0 is duplicated.
      /dev/stdout
           File descriptor 1 is duplicated.
      /dev/stderr
           File descriptor 2 is duplicated.
      /dev/tcp/host/port
           If host is a valid hostname or  Internet  address,
           and  port  is  an  integer  port number or service
           name, bash attempts to open a  TCP  connection  to
           the corresponding socket.
      /dev/udp/host/port
           If host is a valid hostname or  Internet  address,
           and  port  is  an  integer  port number or service
           name, bash attempts to open a  UDP  connection  to
           the corresponding socket.