Network & delivery

6 min readUpdated

What is GRE tunneling?

Quick answer

GRE (Generic Routing Encapsulation) is a tunneling protocol that wraps one packet inside another so it can travel across an intermediate network as if the two endpoints were directly connected. In DDoS protection it is used to deliver filtered traffic: attack traffic is scrubbed on the provider's network, and what survives is encapsulated and handed to your server through the tunnel — which means your server's real address never has to appear in public routing.

01How encapsulation works

A normal packet has one IP header saying where it came from and where it is going. GRE adds an outer header around the whole original packet, so the original becomes payload.

The outer header addresses the tunnel endpoints — the provider's router and yours. Routers in between only see that outer header and forward it like any other traffic, with no knowledge of what is inside. When it reaches your end, the outer header is stripped and the original packet is processed as if it had arrived directly.

GRE is specified in RFC 2784. Its base header is 4 bytes, and the whole packet travels as IP protocol 47 rather than TCP or UDP, which is why firewalls need a rule for protocol 47, not for a port number. The result is a virtual point-to-point link between two networks that may be far apart, without either party needing a physical circuit to the other.

What a router in between actually sees
┌─────────────── outer IP header ───────────────┐
│ src: provider edge  dst: your tunnel endpoint │
│  ┌────────────── GRE header ──────────────┐   │
│  │  ┌────────── original packet ────────┐ │   │
│  │  │ src: visitor   dst: your service  │ │   │
│  │  └───────────────────────────────────┘ │   │
│  └────────────────────────────────────────┘   │
└───────────────────────────────────────────────┘

02Why DDoS protection uses it

Protecting a non-HTTP service means getting its traffic to a filtering network first, and a web proxy cannot carry it, as Layer 3/4 vs Layer 7 protection explains. DNS cannot do it either — a DNS record points a name at an address, but the packets still go wherever that address routes. GRE solves the delivery problem: the provider advertises the protected addresses, so all traffic for them arrives at the scrubbing network first.

Once filtered, the clean traffic has to reach your actual machine, which is somewhere else entirely and has a different address. The tunnel carries it there. From your server's point of view the packets arrive with their original source addresses intact, so logging, geolocation and application logic all keep working normally.

  • Works for any protocol, including UDP, which no HTTP proxy can handle
  • Your hardware stays where it is — no migration required
  • Original client addresses are preserved, so your logs stay meaningful
  • The origin address is not published, so attackers have nothing to aim at directly
Attack + usersmixed trafficScrubbing edgefilters packetsGRE tunnelYour serverstays putflooddroppedonly clean traffic continues
Traffic is scrubbed on our network, then encapsulated and delivered to your machine — which never appears in public routing.

03Return traffic: through the tunnel or direct

Inbound traffic always arrives through the provider. Replies can take one of two routes, and the choice affects latency, MTU and what your own upstream must allow.

Symmetric: replies through the tunnelDirect return: replies via your uplink
Reply pathBack to the provider, then outStraight from your server to the visitor
LatencyAdds the trip to the providerShortest path
You needPolicy routing so replies use the tunnelAn upstream that accepts the protected source addresses, and loose reverse-path filtering
Packet sizeBoth directions limited by the tunnelOnly inbound limited by the tunnel
Usual fitProvider-assigned addressesYour own prefix with a cooperative upstream

04Your own addresses, or the provider's

There are two ways to run this. With BYOIP (bring your own IP), you own an address range, in practice at least a /24 because longer prefixes are generally filtered, and authorise the provider to announce it on your behalf. Your addresses stay yours, which matters if they are baked into client configurations, allowlists or DNS you do not control. It also needs a ROA that authorises the announcing network, or networks that validate routes may reject it; what RPKI is explains how.

Alternatively the provider assigns you addresses from their own range. This is faster to set up and requires no address ownership, but the addresses are not portable — if you leave, you renumber.

05MTU, MSS and encryption

GRE adds 24 bytes to every packet on an IPv4 path: 20 for the outer IPv4 header and 4 for the GRE header. Each optional field, such as the key from RFC 2890, adds 4 more, and an IPv6 outer header makes the base overhead 44. If that is not accounted for, full-size packets fragment or are dropped, and the classic symptom is that small requests work while large uploads or TLS handshakes hang. RFC 4459 explains why path MTU discovery cannot be relied on to fix it over IPv4: firewalls and other middleboxes are often configured to drop the ICMP messages it depends on.

Set the tunnel MTU and clamp the TCP maximum segment size (MSS) on SYN packets, so connections never attempt segments that do not fit. The full arithmetic, including IPv6 inside the tunnel and the Linux commands, is in GRE vs IPIP, and the MTU and MSS calculator works the numbers out for stacked tunnels such as GRE over PPPoE.

GRE also provides no encryption or authentication of its own; it is a delivery mechanism, not a security protocol. That is rarely a problem here, because the payload is ordinary internet traffic that was never private in the first place, but it is worth being explicit about; where the link itself must be private, GRE is paired with IPsec.

TunnelOverheadTunnel MTU on a 1,500-byte pathTCP MSS, IPv4 inside
GRE over IPv424 bytes1,4761,436
GRE over IPv4 with a key28 bytes1,4721,432
GRE over IPv644 bytes1,4561,416

06Checking a GRE tunnel

Three checks confirm a tunnel passes traffic and is sized correctly. In the example, 203.0.113.1 is the provider's tunnel endpoint and 10.10.10.1 the far end of the tunnel's own /30 link; a subnet calculator helps when planning those small point-to-point ranges.

Tunnel checks (tcpdump 4.99.3, iproute2 6.1.0, iputils 20221126; run over a real GRE tunnel between two network namespaces, Debian 12)
# GRE packets from the provider's endpoint arriving on the physical interface
tcpdump -nni eth0 'ip proto 47 and src host 203.0.113.1'

# tunnel counters: RX should rise while traffic flows, errors should not
ip -s link show dev gre1

# largest unfragmented ping through a 1,476-byte tunnel: 1,476 - 28 = 1,448
ping -M do -s 1448 -c 3 10.10.10.1
# one byte more must fail locally with: message too long, mtu=1476
ping -M do -s 1449 -c 1 10.10.10.1

07Before you put a service behind a GRE tunnel

  • Allow GRE (protocol 47) only from the provider's tunnel endpoints, and the service ports only through the tunnel
  • Set the tunnel MTU and MSS clamping on day one, not after the first stalled upload
  • Decide the return path and test it from an outside network
  • If you bring your own prefix, publish the ROA before the first announcement
  • Monitor the far tunnel address: RFC 2784 defines no keepalive, so a dead tunnel can still look up
  • Remove old DNS records and banners that expose the real address

Questions

Frequently asked questions

No. GRE encapsulates but does not encrypt. If confidentiality between the endpoints matters, it is combined with IPsec — though for delivering public internet traffic to a public service, encryption usually adds nothing.

A little, from the extra network hop and the encapsulation itself, but it is generally small compared to the alternative of being offline during an attack.

The outer headers take 24 bytes from the usable packet size on an IPv4 path. If the tunnel MTU is left at the default, large packets get fragmented or dropped — which shows up as an oddly selective failure where small requests work and large ones hang.

Not reliably. GRE has no ports, so most NAT devices cannot track it, and the tunnel endpoint generally needs a public address. Where NAT cannot be avoided, a UDP-based tunnel is used instead.

Sources

Sources and verification

Tunnel checks run over a real GRE tunnel between two isolated network namespaces joined by a veth pair (iproute2 6.1.0, MTU 1476): a 1,448-byte ping with DF set passed, 1,449 bytes failed locally with "message too long, mtu=1476", and the tcpdump 4.99.3 filter captured GRE from the far endpoint. Debian 12, October 2026. MTU figures follow from the header sizes in RFC 2784 and RFC 2890.

  1. 01RFC 2784: Generic Routing Encapsulation (GRE) · IETF
  2. 02RFC 2890: Key and Sequence Number Extensions to GRE · IETF
  3. 03RFC 4459: MTU and Fragmentation Issues with In-the-Network Tunneling · IETF
  4. 04RFC 2827 (BCP 38): Network Ingress Filtering · IETF
  5. 05ip-link(8): GRE, IPIP and SIT tunnel options · man7.org

Last updated