Osmocom kernel-level GTP implementation
=======================================
Andreas Schultz + Harald Welte
:copyright: Andreas Schultz + Harald Welte (Liense: CC-BY-SA)
:backend: slidy
:max-width: 45em

== What is GTP / GTP in GPRS

* GTP, the 'GPRS Tunneling Protocol' was first introduced with GPRS, the
  packet-switched add-on to GSM networks
* 'PDP contexts' are sessions with an external packet data network (IP)
  which provide a tunnel between the phone and that external network
* GTP is used betwen the SGSN and GGSN to tunnel the User-plane (IP)
  packet data of a PDP Context
* latest definition in (3GPP TS 29.281 version 12.1.0 Release 12)

[graphviz]
----
digraph G {
	label="GPRS Network"
	rankdir=LR;
	MS0 [label="MS"]
	MS0->BTS0 [label="Um", dir=both]
	BTS0 [label="BTS + CCU"]
	BTS0->PCU [dir=both]
	PCU->SGSN [label="Gb", dir=both]
	SGSN->GGSN [label="GTP", dir=both]
}
----


== GTP in UMTS

* In UMTS, PDP originally remained between SGSN and GGSN
[graphviz]
----
digraph G {
	label="UMTS Network"
	rankdir=LR;
	UE [label="UE"]
	NB [label="NodeB"]
	RNC [label="RNC"]

	UE->NB [label="Uu", dir=both]
	NB->RNC [label="Iub", dir=both]

	RNC->SGSN [label="IuPS", dir=both]
	SGSN->GGSN [label="GTP", dir=both]
}
----
* With HSPA in later releases (Rel7+), user plane is moved out of SGSN
  and NodeB generates GTP directly
* hNodeB (femtocell) architecture also originates GTP directly in hNodeB
[graphviz]
----
digraph G {
	label="UMTS Network / Later Release"
	rankdir=LR;
	UE [label="UE"]
	NB [label="NodeB"]
	RNC [label="RNC"]

	UE->NB [label="Uu", dir=both]
	NB->RNC [label="Iub", dir=both]

	RNC->SGSN [label="IuPS", dir=both]
	SGSN->GGSN [label="GTP-C", dir=both]
	NB->GGSN [label="GTP-U", dir=both]
}
----


== GTP in LTE

* LTE uses GTP at even more interfaces between network elements
* LTE introduces GTP-C Version 2 for control plane, but user plane
  remains GTP-U v1 like before.
* What used to be the GGSN is now called PDN-GW in LTE
[graphviz]
----
digraph G {
	label="LTE Network"
	rankdir=LR;
	UE [label="UE"]
	NB [label="eNodeB"]

	UE->NB [label="Uu", dir=both]
	NB -> MME [label="S1", dir=both]
	NB -> SGW [label="S1-U (GTP-U)", dir=both]
	MME -> SGW [label="S11", dir=both]
	SGW->PGW [label="S5 (GTP-U)", dir=both]
}
----



== GTP

* control (GTP-C) *and* user (GTP-U) plane protocol
* UDP based on well known ports (3386, 2152)
* per PDP context/tunnel identifiers (TID)
** one for each direction(!) in GTP v1
** is the only identifier for tunnel, not IP/Port tuples!
* support for packet sequnce numbers and reordering


== GTP-C

control protocol for:

* exchanging meta data
* assigning parameters to client:
  - IPv4 addresses
  - IPv6 prefixes
  - DNS servers
  - ...
* establishing and removing tunnels
* moving tunnel endpoints to other SGW's


== GTP-U

two main jobs:

* per client tunnelling of IP packets
* path maintenance
  - echo requests/replies
  - error reporting

[packetdiag]
----
{
  colwidth = 32
  node_height = 64

  0-7: Flags
  8-15: Type
  16-31: Length
  32-63: Tunnel ID
}
----

== Problems with Userspace GTP

* Userspace GTP was fine with GPRS speeds
** Packet rates / bandwidths small compared to routing
* With HSPA and particularly LTE, the world has changed
** Signalling / Control Plane traffic is very limited
** User Plane traffic is very high bandwidth


== Osmocom kernel-level GTP

* Move bandwidth-critical User Plane into Linux kernel
* Keep Control Plane stays in Userspace (OpenGGSN)
* Use netlink based API to control user plane in kernel

* Started by Harald Welte + Pablo Neira @ sysmocom in 2012
** unfortunately abandoned due to customer disappearing
* picked up by Andreas Schultz @ travelping in 2015
** fixed Harald + Pablo's bugs
** introduce network namespace support


== Design

* netlink API built on top of genl
* initialization:
** create GTP socket in userspace
** create tun like network interface
** bind GTP sockets to it
* for each PDP context, user space adds one record
** IP address assigned to MS for this PDP context
** TEIDs to identify mobile-originated packets
** SGSN IP for GTP header of mobile-terminated packets

== Design

* netlink API built on top of genl
* all PDP contexts share one tun device
** one tun device for all subscribers, not one per subscriber

[graphviz]
----
digraph G {
	rankdir=LR;
	MS0 [label="MS 10.0.0.1"];
	MS1 [label="MS 10.0.0.2"];
	MS2 [label="MS 10.0.0.3"];
	GGSN;
	tun0 [shape=box];

	MS0 -> SGSN [dir=both];
	MS1 -> SGSN [dir=both];
	MS2 -> SGSN [dir=both];

	SGSN -> GGSN [label="GTP-U", dir=both];
	GGSN -> tun0 [dir=none, minlen=0];
	tun0 -> SRV [label = "10.0.0.1 - 1.2.3.4", dir=both]
	tun0 -> SRV [label = "10.0.0.2 - 1.2.3.4", dir=both]
	tun0 -> SRV [label = "10.0.0.3 - 1.2.3.4", dir=both]
}
----

== STATUS

* working
** GTP-U v0 and v1 for IPv4 over IPv4
** multiple tunnels supported
** only single APN (multiple IP ranges not permited)

* Limitations
** no IPv6 support
** no offload support

* existing users (both GPLv2)
** OpenGGSN (http://cgit.osmocom.org/openggsn/)
** new 'ergw' Erlang GGSN / P-GW (https://github.com/travelping/ergw)


== TODO

* TODO:
** final round of clean-up, submission for mainline
** fix or remove IPv6 support
* discussion items:
** path MTU discovery
** implications by/for offloading faetures (csum / gso / ...)
* wishlist
** light-weight tunneling integration


== The End

Questions?
