So i want socat to persistently listen for connections, get the first x lines and reply back with a message. Ideally i want to use a user defined function to handle that logic but i couldn't find a way to achieve that.

My scenario:

client 1:

cat <(printf "line1\nline2\n") -|nc socat_server socat_port

client 2:

cat <(printf "line3\nline4\n") -|nc socat_server socat_port

I want to get: line1 and line3 and the clients a message (e.g. EXIT)

I've tried with:

exec {fd}> >(my_custom_function)
socat tcp-listen:10000,reuseaddr,fork system:"head -n1>&$fd;echo EXIT;exit"

but i get "Bad fd number". Any ways around this?

  • Pipe the output through head
    – roaima
    Nov 15, 2020 at 13:18
  • thanks, i have updated the post to include more infomration
    – tturbox
    Nov 15, 2020 at 15:12
  • So you want a reusable/repeating connection listener that only outputs the first line. What fd do you want the output written to - stdout?
    – roaima
    Nov 15, 2020 at 15:19
  • yes, but i want it to print a message to the client as well, e.g. echo exit
    – tturbox
    Nov 15, 2020 at 15:20
  • Please say that in your question. There's nothing there that says you want the input written back
    – roaima
    Nov 15, 2020 at 15:20

1 Answer 1


With {fd}> file, the value of $fd will be greater than 9.

With system:shell-code, socat invokes sh to interpret that shell code.

sh implementations are not required to support fds above 9 in their redirection operators. Implementations such as dash or mksh don't. Also note that ksh93 (one of the three shells with zsh and bash that supports that syntax) marks the fd obtained with exec {fd}> file with the close-on-exec flag, so won't be inherited by socat there.

So, here, you'd want to use a fd below 10:

exec 4> >(my_custom_function)
socat tcp-listen:10000,reuseaddr,fork system:"head -n1>&4;echo EXIT;exit"

Or invoke a shell that you know supports fds above 9 like zsh:

exec {fd}> >(my_custom_function)
socat tcp-listen:10000,reuseaddr,fork "exec:'zsh -c \"head -n1>&$fd;echo EXIT;exit\"'"

(not from ksh93).

  • so shouldn't the second solution be affected by the close-on-exec flag? (i tested it and it doesn't)
    – tturbox
    Nov 15, 2020 at 18:46
  • 1
    @tturbox, close-on-exec only affects ksh93 (hence my not from ksh93); zsh and bash don't set the close-on-exec flag. ksh93 will also set the close-on-exec flag on fd 4 in the first approach. Anyway ksh93 doesn't support redirecting to a process substitution. Nov 15, 2020 at 18:56
  • thanks btw i suppose another solution to the problem would be to change the default shell in which socat runs the "SYSTEM" commands since is more related with sh right?
    – tturbox
    Nov 15, 2020 at 23:17

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .