From 50d28c050672da69162032114ac1f8f6a9e6c9e7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9ophile=20Bastian?= Date: Fri, 5 Jun 2020 17:30:35 +0200 Subject: [PATCH] Add VpnPacket class --- Makefile | 1 + VpnPacket.cpp | 21 +++++++++++++++++++++ VpnPacket.hpp | 42 ++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 64 insertions(+) create mode 100644 VpnPacket.cpp create mode 100644 VpnPacket.hpp diff --git a/Makefile b/Makefile index 1a831a5..86b51a0 100644 --- a/Makefile +++ b/Makefile @@ -5,6 +5,7 @@ CXXLIBS= OBJS= \ UdpVpn.o UdpVpnClient.o UdpVpnServer.o \ VpnPeer.o \ + VpnPacket.o \ TunDevice.o \ ip_header.o util.o main.o TARGET=congestvpn diff --git a/VpnPacket.cpp b/VpnPacket.cpp new file mode 100644 index 0000000..4b4f9d6 --- /dev/null +++ b/VpnPacket.cpp @@ -0,0 +1,21 @@ +#include "VpnPacket.hpp" + +const size_t VpnPacket::VPN_HEADER_SIZE = 0; + +static const size_t OUTER_HEADERS_SIZE = + 40 /* IPv6 header */ + 8 /* UDP header */; + // We use a TUN device, hence we don't have a layer 2 header. + +VpnPacket::VpnPacket(size_t mtu) + : _data_space(mtu-OUTER_HEADERS_SIZE), _data_size(0) +{ + _data = new char[mtu - OUTER_HEADERS_SIZE]; +} + +VpnPacket::~VpnPacket() { + delete[] _data; +} + +bool VpnPacket::parse_as_ipv6() { + return parse_ipv6_header(get_payload(), get_payload_size(), _ipv6_header); +} diff --git a/VpnPacket.hpp b/VpnPacket.hpp new file mode 100644 index 0000000..0a97567 --- /dev/null +++ b/VpnPacket.hpp @@ -0,0 +1,42 @@ +#pragma once + +/** A packet to be transmitted or received over the VPN socket */ + +#include + +#include "ip_header.hpp" + +class VpnPacket { + public: + static const size_t VPN_HEADER_SIZE; + + VpnPacket(size_t mtu); + ~VpnPacket(); + + /// Try to parse the packet as IPv6, return `false` upon failure. + bool parse_as_ipv6(); + bool ipv6_parsed() const { return _ipv6_parsed; } + const IPv6Header& get_ipv6_header() const { return _ipv6_header; } + + const char* get_payload() const { return _data + VPN_HEADER_SIZE; } + char* get_payload() { return _data + VPN_HEADER_SIZE; } + size_t get_payload_space() const { + return _data_space - VPN_HEADER_SIZE; } + size_t get_payload_size() const { + return _data_size - VPN_HEADER_SIZE; } + void set_payload_size(size_t payload_size) { + _data_size = payload_size + VPN_HEADER_SIZE; } + + const char* get_data() const { return _data; } + char* get_data() { return _data; } + size_t get_data_space() const { return _data_space; } + size_t get_data_size() const { return _data_size; } + void set_data_size(size_t data_size) { _data_size = data_size; } + + private: + char* _data; + size_t _data_space, _data_size; + + bool _ipv6_parsed; + IPv6Header _ipv6_header; +};