Skip to content

Crash in TCP server fails to close socket #7

@bobpaul

Description

@bobpaul

The easiest way to reproduce this is with using the TCP listener in combination with the http_ws_server mock.

Computer 1

$ ./tunnel tcp:0.0.0.0:10080 -r udp:127.0.0.1:51820 -o header -v -m http_ws_server
Obfuscating packets with simple obfuscator and built-in key.
Masquerading packets into HTTP WebSocket stream.
Started TCP server at 0.0.0.0:10080
Waiting for first client...
Client connected via TCP from
Started UDP client for 127.0.0.1:51820
Performing HTTP WebSocket handshake...
Received 81 bytes from remote
Received invalid request from client: GET / HTTP/1.1
Dropping connected client.

$ sudo netstat -lnet | grep 10080

$ ./tunnel tcp:0.0.0.0:10080 -r udp:127.0.0.1:51820 -o header -v -m http_ws_server
Obfuscating packets with simple obfuscator and built-in key.
Masquerading packets into HTTP WebSocket stream.
Bind failed: Address already in use

Computer 2

$ curl http://example.com:10080 --resolve example.com:192.168.0.10 -v
* Added example.com:10080:192.168.0.10 to DNS cache
* Hostname example.com was found in DNS cache
*   Trying 192.168.0.10:10080...
* Connected to example.com (192.168.0.10) port 10080
* using HTTP/1.x
> GET / HTTP/1.1
> Host: example.com:10080
> User-Agent: curl/8.10.1
> Accept: */*
>
* Request completely sent off
< HTTP/1.1 404 Not Found
< Server: Microsoft-IIS/10.0
* no chunk, no close, no size. Assume close to signal end
<
* shutting down connection #0

Explain steps to reproduce

  1. Start the listener with the mock server.
  2. Use curl or a browser or similar to send an HTTP request to the server
  3. Observe the tunnel crashes on computer 1.
  4. Attempt to restart the tunnel application.
  5. Observe the TCP port is still held open by OS, though netstat shows no application is using the port. This is a common symptom of a program quitting without first closing the socket

Expected Behavior

  • The application should not crash
  • If the application crashes, it should close the socket before completely terminating.

Mitigation

  • The application should set the ADDRREUSE socket option which will at least allow the program to restart using the same TCP port as before without waiting for the OS to time out and fully release the socket. This would at least allow systemd, daemon-tools, etc quickly restart the tunnel if it crashes.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions