package Net::OpenVPN::Manager::Plugin::FixMSS;

use namespace::autoclean;
use Moose;
use Net::OpenVPN::Manager::Plugin;
use IPTables::ChainMgr;

with 'Net::OpenVPN::Manager::Startable';

has 'ipv4' => (
    is => 'ro',
    isa => 'Int',
    default => 0,
);

has 'ipv6' => (
    is => 'ro',
    isa => 'Int',
    default => 0,
);

has 'chain' => (
    is => 'ro',
    isa => 'Str',
    default => "OPENVPN_FIXMSS",
);

sub _setup_iptables {
    my ($self, $mss, $ipv6) = @_;

    my $ipt = new IPTables::ChainMgr('use_ipv6' => $ipv6);
    $ipt->create_chain('mangle', $self->chain);
    $ipt->flush_chain('mangle', $self->chain);
    $ipt->add_jump_rule('mangle', 'FORWARD', -1, $self->chain);

    my @inrule = (
        $ipt->{'_cmd'},
        '-t', 'mangle',
        '-A', $self->chain,
        '-i', $self->manager->netdev,
        '-p', 'tcp',
        '--tcp-flags', 'SYN,RST', 'SYN',
        '-j', 'TCPMSS',
        '--set-mss', $mss
    );

    my @outrule = (
        $ipt->{'_cmd'},
        '-t', 'mangle',
        '-A', $self->chain,
        '-o', $self->manager->netdev,
        '-p', 'tcp',
        '--tcp-flags', 'SYN,RST', 'SYN',
        '-j', 'TCPMSS',
        '--set-mss', $mss
    );

    $ipt->run_ipt_cmd(join(" ", @inrule));
    $ipt->run_ipt_cmd(join(" ", @outrule));
}

sub start {
    my $self = shift;

    if ($self->ipv4 > 0) {
        $self->_setup_iptables($self->ipv4, 0);
    }

    if ($self->ipv6 > 0) {
        $self->_setup_iptables($self->ipv6, 1);
    }

    return PLUG_OK;
}

1;
