Skip to content
zhou.
← Blog

Setting up VPN service based on VLESS + Reality and HYSTERIA2

4 Aug 2026 · 2 views

Intro

As everyone knows, hy2 and VLESS + Reality are the two most commonly used setups for getting online. If you're using an existing service it doesn't really matter — there's not much you can change anyway — but when you're self-hosting, this is something you often have to think about.

Config

The machine is still the ancestral Dutch GCP Compute Engine box handed down through the generations: 1 CPU core, 100 GB disk, 8 GB RAM. It's even running a pile of other services, but thankfully the load is very low (is that a good thing?), so we can ignore that. RTT from the Netherlands to Shanghai is roughly 250 ms — a textbook long fat network. I rented in the Netherlands because I was in London at the time and wanted to dodge the Online Safety Act (and I also signed a one-year indenture contract, running 24/7, no stopping — because even if I stop it, the charges keep coming).

The framework is sing-box, installed straight from the 233boy script. It really is an incredibly convenient script; it's just a pain when you want to fine-tune parameters.

VPN

First I brought up VLESS + Reality, with all kernel networking and TCP settings left at their defaults. Connecting from my phone, it was almost completely unusable — a pitiful ~1 KB/s. There is one odd thing here though: on mobile data the bandwidth is somewhat better, while my work laptop and my own machine on wired Ethernet both get terrible throughput. I haven't figured out why yet.

The first optimization was enabling BBR. As everyone knows, the bandwidth of a single TCP connection = cwnd / RTT, so the only way to speed things up is to make cwnd bigger. Traditional CUBIC treats packet loss as congestion, so a loss rate of just a fraction of a percent is enough to tank a connection's throughput. BBR ignores loss and models the connection using other signals, so it can push the window much larger — the gap can be more than tenfold. Alongside BBR I also tuned a handful of kernel network parameters and bumped up the network buffer sizes.

net.core.rmem_max = 67108864
net.core.wmem_max = 67108864
net.ipv4.tcp_rmem = 4096 87380 67108864
net.ipv4.tcp_wmem = 4096 65536 67108864

The effect was immediate. Downloading a game from the App Store as a test, I got roughly 100–200 KB/s, and YouTube became basically watchable — at least not so stuttery. On top of that, thanks to Reality's SNI masquerading, this setup is considerably stealthier. Still, that kind of bandwidth is too awkward to live with as a daily driver, so I spun up an hy2 config as well.

hy2 is built on QUIC, and its specialty is grabbing bandwidth over poor-quality links — perfect for long fat pipes. In practice, even when your server is close by, hy2 is usually what you'd use: latency is almost always lower and throughput is often higher. Its Brutal congestion control has no honor whatsoever — you declare the bandwidth you want, and hy2 just hammers away at it, relying on QUIC retransmission to recover whatever gets dropped.

After bringing up hy2, throughput shot straight to 10 MB/s, which is more than enough for everyday use like pulling down dependencies.

As for overhead: VLESS relies on in-kernel TCP while hy2 runs QUIC in userspace, so in theory the latter should burn more CPU — but in my measurements both were sitting at essentially zero.

End of day...

It's a good practice to set up your own VPN service. Not only for a private ip or stuff like that. It gives you exposure to the world of network, as well as its mechanism and optimization.