Home | History | Annotate | Download | only in layers
      1 ## This file is part of Scapy
      2 ## See http://www.secdev.org/projects/scapy for more informations
      3 ## Copyright (C) Philippe Biondi <phil (at] secdev.org>
      4 ## This program is published under a GPLv2 license
      5 
      6 """
      7 L2TP (Layer 2 Tunneling Protocol) for VPNs.
      8 
      9 [RFC 2661]
     10 """
     11 
     12 import struct
     13 
     14 from scapy.packet import *
     15 from scapy.fields import *
     16 from scapy.layers.inet import UDP
     17 from scapy.layers.ppp import PPP
     18 
     19 
     20 class L2TP(Packet):
     21     name = "L2TP"
     22     fields_desc = [ 
     23                     FlagsField("hdr", 0, 12, ['res00', 'res01', 'res02', 'res03', 'priority', 'offset',
     24                                               'res06', 'sequence', 'res08', 'res09', 'length', 'control']),
     25                     BitEnumField("version", 2, 4, {2: 'L2TPv2'}),
     26 
     27                     ConditionalField(ShortField("len", 0),
     28                         lambda pkt: pkt.hdr & 'control+length'),
     29                     ShortField("tunnel_id", 0),
     30                     ShortField("session_id", 0),
     31                     ConditionalField(ShortField("ns", 0),
     32                         lambda pkt: pkt.hdr & 'sequence+control'),
     33                     ConditionalField(ShortField("nr", 0),
     34                         lambda pkt: pkt.hdr & 'sequence+control'),
     35                     ConditionalField(
     36                         PadField(ShortField("offset", 0), 4, b"\x00"),
     37                         lambda pkt: not (pkt.hdr & 'control') and pkt.hdr & 'offset'
     38                         )
     39                     ]
     40 
     41     def post_build(self, pkt, pay):
     42         if self.len is None:
     43             l = len(pkt)+len(pay)
     44             pkt = pkt[:2]+struct.pack("!H", l)+pkt[4:]
     45         return pkt+pay
     46 
     47 
     48 bind_layers( UDP,           L2TP,          sport=1701, dport=1701)
     49 bind_layers( L2TP,          PPP,           )
     50