VirtualBox

Opened 15 months ago

#21850 new defect

NAT (slirp.c) may corrupt incoming data when followed by close.

Reported by: henryk paluch Owned by:
Component: network/NAT Version: VirtualBox-7.0.10
Keywords: nat slirp truncated shifted skewed Cc: kabat, paluch
Guest type: other Host type: Windows

Description

When using guest with "NAT" interface and connecting to remote TCP server, it may happen that when server closes connection right after sending data, the data in guest will be corrupted. First byte will be removed and length will be one byte less.

Example:

  • correct data read from server (returned most of time): ABCD
  • but sometimes guest get just BCD

Tip: all test files and proposed patch are also available on public GitHub page: https://github.com/hpaluch-pil/vbox-nat-bug-test provided under MIT license (to no CLA needed).

How to reproduce:

  1. setup Remote server with Linux or any other OS that is capable to run PERL
  2. run provided perl script tcp_service.pl on that remote host.
  3. Setup Linux (or any other OS with PERL 5) as VirtualBox Guest (tested 7.0.10) and ensure that "NAT" interface is used to access remote server.
  4. Run provided perl script tcp_client.pl with arguments like:
./tcp_client.pl IP_OF_REMOTE_HOST 99999
  1. It will run for some time receiving correct data (no error reported). For example:
    Iteration #179...
      Connected from 10.0.2.15:55642 to 192.168.10.54:9999.
      <- data from server: 'ABCDEFGH' 8 bytes
      Data OK.
      Closing connection...
    
  2. But sooner or later it will fail with error:
    Iteration #180...
      Connected from 10.0.2.15:55648 to 192.168.10.54:9999.
      <- data from server: 'BCDEFGH' 7 bytes
    Unexpected data 'BCDEFGH' <> 'ABCDEFGH' at ./tcp_client.pl line 59.
    

As can be clearly seen, 1st byte of data is missing entirely and total received data length is 1 byte shorter.

After lot of debug logging I have found that there is a bug in slirp.c where it may try to close socket too eagerly even when received data was not yet processed by tcp_input. It can be easily identified by evaluating so->so_state which will be 0 (which means - unknown/uninitialized).

Therefore I created patch that defers close of such sockets until they were at least once processed by tcp_input. It is provided in patch file close-fix-slirp.c.patch. However it needs more testing.

Attachments (3)

tcp_service.pl (1.3 KB ) - added by henryk paluch 15 months ago.
Example Tcp Server to be run on remote Linux Host
tcp_client.pl (2.1 KB ) - added by henryk paluch 15 months ago.
Example Tcp Client to be run as VirtualBox Guest and have to use "NAT" Interface to access remote Server
close-fix-slirp.c.patch (644 bytes ) - added by henryk paluch 15 months ago.
Proposed fix for slirp.c

Download all attachments as: .zip

Change History (3)

by henryk paluch, 15 months ago

Attachment: tcp_service.pl added

Example Tcp Server to be run on remote Linux Host

by henryk paluch, 15 months ago

Attachment: tcp_client.pl added

Example Tcp Client to be run as VirtualBox Guest and have to use "NAT" Interface to access remote Server

by henryk paluch, 15 months ago

Attachment: close-fix-slirp.c.patch added

Proposed fix for slirp.c

Note: See TracTickets for help on using tickets.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette