Skip to content

Tooling and examples for retrieving the ECN bits of a network connection

License

Notifications You must be signed in to change notification settings

qvest-digital/ECN-Bits

Repository files navigation

┏━━━━━━━━━━┓
┃ ECN-Bits ┃
┗━━━━━━━━━━┛

┌──────────┐
│ Abstract │
└──────────┘

This repository contains tooling (libraries) and examples for
getting Explicit Congestion Notification (ECN) bits from IP
traffic, which is useful for L4S-aware applications. They are
available under liberal (Open Source) licences.

Development funded by Deutsche Telekom.

┌──────────────────────────────────────────┐
│ IMPORTANT note for git users on Windows® │
└──────────────────────────────────────────┘

This repository *must* be cloned with symbolic links *enabled*.
Use test-git.bat to verify that this is the case, and if not,
follow the instructions at…
‣ https://github.com/git-for-windows/git/wiki/Symbolic-Links
under “Allowing non-administrators to create symbolic links”
(basically, on Windows 10 version 1703 “Creators Update” and
newer, enable developer mode, otherwise set a group policy)
to enable symlink support if needed, then re-clone with e.g.
git clone -c core.symlinks=true https://github.com/qvest-digital/ECN-Bits.git

┌────────────────────────────────┐
│ Covered operating environments │
└────────────────────────────────┘

– Android/Linux: Java/JNI
  ‣ see android/README
  • library (AAR), with JNI component written in C,
    easily added into your own projects
    + java.net.ECNBitsDatagramSocket (extends DatagramSocket)
      to communicate and get the IP traffic class or the congestion factor
    + de.telekom.llcto.ecn_bits.android.lib.Bits
      to access the ECN bits contained in the traffic class byte
    + de.telekom.llcto.ecn_bits.android.lib.ECNBitsDatagramChannel
      (extends DatagramChannel) to communicate
    + de.telekom.llcto.ecn_bits.android.lib.ECNBitsDatagramSocket
      (extends DatagramSocket) to communicate
    + both support retrieveLastTrafficClass() to get the IP traffic class
      and startMeasurement() / getMeasurement() to get the congestion
      factor as an ECNStatistics object
    ! targetting Android 8 (Oreo, API 26/27) and up
    ! tested on Android 8/9/10
    : Status: working, minor nitpicking waiting on external projects’ bugfixes
      testing on Android 11 needed (including “strict mode”)
  • demo client GUI application
  ⚠ can be built with JDK 8 or 11 but no newer versions

– OpenJDK/Linux: Java/JNI/CLI
  ‣ see jdk-linux/README
  • library with Main class as example, with JNI component written in C;
    can easily be added as Maven dependency but requires to be locally
    compiled for the target CPU architecture (e.g. i386 or ARMv8)
  • reuses the Android/Linux library (see above)
    ⇒ offers the exact same API (functions)
    ⇒ uses the exact same JNI library ⇒ Linux-specific
  : Status: working (Netty example may be added later if demand exists)
  • PoC (Linux-specific and only for the buildhost architecture) first,
    possibly extended to other CPUs and OSes later, perhaps using JNA
  ⚠ Valid only for Java < 15 (due to JEP 373)

– BSD/Linux/MacOSX/WSL: C/CLI (libecn-bits.a/so)
  ‣ see c/README
  • library, manpages
  • CLI client and server examples (run for usage instructions)
  + known working on FreeBSD/MidnightBSD, Linux (including WSL 2), Mac OSX
  + also on the Linux variant Android runs on, e.g. built with musl libc
  + works on WSL 1, except setting the outgoing traffic class silently fails
  - cannot work on NetBSD, OpenBSD and derivatives: no API to get the TC
  ? might work on Solaris
  : Status: completed for those operating systems mentioned, dylib/.so built

– Windows: C/CLI (libecn-bitw.a/so; ecn-bitw.lib/dll)
  ‣ see ws2/README
  • library, CLI client/server examples, copied from BSD/Linux/Mac/WSL C/CLI
    but adapted for Winsock2 (supersetting: keeping BSD sockets support
    so all systems that the BSD/Linux/Mac/WSL runs on can be used modulo
    removed functionality (see below); applications needing to honour some
    Win32/Winsock2 specifics can remain portable)
  ! native Winsock2 can set (per-packet) outgoing ECN bits to NO/ECT(0)/ECT(1)
    but not CE and not the DSCP bits, nor a per-socket default
  • extra library exports for easier high-level language wrapping
  • manpages including preformatted plaintext form for GUI users
  • tested on Windows 10, versions 1909 (WSL 1, WinSock), 2004 (WSL 2)
  : Status: complete and builds a .dylib/.so/.DLL with HLL (.net) support code
    HLL support functions working, but not declared external API
  ! outgoing traffic class cannot at all be set on WSL 1
  ! WSL 2 in theory would work better than WSL 1 (as it uses the native
    Linux network stack) but the hypervisor side breaks networking in
    too many cases (no IPv6 support (up to that syscalls fail), lack of
    port forwarding for UDP, DNS resolver bugs), so users of networking
    are strongly encouraged to use WSL 1 instead.

– Windows, C++/UWP
  • implemented through linking the C/CLI library into the application

– Windows/Linux, C♯/.net including Mono (also VB.net and other CLR languages)
  ‣ see dotnet/README
  : Status: Extension Method API works but this needs more eyes, actual users

– iOS (Apple)
  • needs development

– Windows/Android, Unity (game engine)/C♯/Mono
  • needs development

┌────────────────┐
│ About ECN bits │
└────────────────┘

Both IP (IPv6) and Legacy IP (IPv4) have a Traffic Class
header field, eight bits in size. (This spans the second
and third nybble (half-octet) in IPv6; in IPv4 the whole
second octet is comprised of it.) The upper six bits are
used for DiffServ (DSCP) while the lower two are used by
ECN as follows:

• 00: NonECT — nōn-ECN-capable transport
• 10: ECT(0) — ECN-capable transport; L4S: legacy transport
• 01: ECT(1) — ECN-capable transport; L4S: L4S-aware transport
• 11: CE — congestion experienced

The Traffic Class header used to be known as IPToS.

┌────────────────────┐
│ Further directions │
└────────────────────┘

For writing L4S-aware applications, adaptively managing
bandwidth (and latency) are important. The scope of the
tooling included here is aids to get at the ECN bits of
the IP header; nothing more. SCReAM (Ericsson Research)
is a good example of how to actually adapt use of band‐
width based on network conditions:
‣ https://github.com/EricssonResearch/scream

DTAG and partners are currently researching integrating
SCReAM and writing other adaptive algorithms.

Another way to retrieve the IP traffic class (therefore
also the ECN bits) is packet sniffing — while this adds
latency and has concerns in production (security etc.),
it’s a viable path for testing. This is being worked on
by another team; it will be linked to later.

The directory CONFLUENCE/ contains extra documentation,
in both importable form (*.doc) and as PDF export, with
a plaintext version to improve legibility and grepping,
for this library and demo programs, with screenshots.
This extra documentation tends to get out of date though.

About

Tooling and examples for retrieving the ECN bits of a network connection

Resources

License

Stars

Watchers

Forks