VPN on a ship

There are many reasons for a VPN on a ship, and I was quite impressed that my other hack for UDP over fake TCP worked at all.

It did work, but was slightly strange. The experience was that normally VPN (via UDP or TCP) worked, but had 700ms latency round trip.

However, some of the time, the ship would have packet loss on the back haul, and then things changed. The UDP VPN would lose enough packets that normal TCP really struggled. Indeed, some times the VPN itself struggled to establish or stay up. It was actually for this reason that we even tried the TCP based solution.

However, in such cases, the TCP based VPN is special. It is very reliable, but has silly latency (up to many seconds).

The reason is what the satellite link it doing behind the scenes with TCP. It is doing an accelerator, which (I assume) is some level of local ACK combined with some internal re-transmission for dropped packets. But this means our VPN over TCP has the problems of doing TCP properly rather than faked, in that dropped packets result in high latency for every following packet.

Given the "cleverness" going on, it is amazing our faked TCP was good enough at all!

However, we like to have proper IP addresses here. There are a lot of reasons for that, but one of them is simple, it puts us, and our apple TV, geo-located at home. This was rather important for watching the episodes of Picard as they came out, even when in the middle of the Pacific.

So the challenge was proper UK IP addresses but still using the ship's TCP acceleration.

The solution was to de-NAT the traffic. The local brick here would NAT and send via ship's internet, which NATs again, but we change the destination IP to go to a brick in the UK. That then de-NATs, mapping back to original source and destination IP addresses and ports, or NAT the source. This works a treat, but you may have spotted the challenge here... How does the far end know where you wanted to send the packets in the first place?

The answer was to tack them on to the TCP SYN and look a them at the remote end!

My first thought was push them in to TCP options, but that is a challenge as there are only 40 bytes, and MSS takes 4 of those, leaving not enough bytes for two IPv6 addresses and ports. We could for IPv4, or we could just send target IP/port and NAT in UK. So we tried that.

The buggers NOP out any TCP option they do not understand, arrrg!

Alternative was put actual data in the initial SYN. To our surprise that worked, and as a SYN does not normally carry data, it works well (it is one of those theoretical TCP things I have never seen used). But it survives, and does not have the small size limit. We do have to move the SEQ back to allow for it, and strip out at the far end before sending on, but end result is public IPv4 and public IPv6 here, working. There is even space to add some authentication. (Note, this is not encrypted as assumes we will encrypt over it with TLS/https, ssh, etc).

Sadly sessions do not persist over glitches, and no incoming sessions, but I could watch Picard, so mission accomplished.

P.S. We have a choice of how to connect now, VPN over UDP, TCP (faked), relayed TCP, or just NAT on to ship's network raw (no good for Apple TV). Today we found UDP the best - the ship's TCP was unbearably slow (relaying, or not), but UDP was way better. To be honest this is much more what we are used to - everyone on the ship saying internet is crap and we're like "high latency, but not bad really" because the UDP based VPN works so well. The main thing is we can switch between different approaches as needed on a trip like this.


  1. "Alternative was put actual data in the initial SYN. To our surprise that worked, and as a SYN does not normally carry data, it works well (it is one of those theoretical TCP things I have never seen used)"

    I'm sure data with SYN has been at least proposed to reduce RTTs for HTTPS etc. Don't know if it's in widespread use yet ...

    1. Ah, it seems to be called "TCP Fast Open" these days - https://tools.ietf.org/html/rfc7413 I'm surprised to discover it's *not* part of TLS 1.3 or 0-RTT. So 0-RTT is really 1-RTT and TLS 1.3 still 2-RTT (and that's without actually sending an HTTP request ...) More reasons why QUIC / HTTP/3 will win out, I guess.


Comments are moderated purely to filter out obvious spam, but it means they may not show immediately.

NOTSCO (Not TOTSCO) One Touch Switching test platform (now launched)

I posted about how inept TOTSCO seem to be, and the call today with them was no improvement. It seems they have test stages... A "simul...