Package dpkt :: Module gre
[hide private]
[frames] | no frames]

Source Code for Module dpkt.gre

  1  # $Id: gre.py 30 2007-01-27 03:10:09Z dugsong $ 
  2   
  3  """Generic Routing Encapsulation.""" 
  4   
  5  import struct 
  6  import dpkt 
  7   
  8  GRE_CP = 0x8000  # Checksum Present 
  9  GRE_RP = 0x4000  # Routing Present 
 10  GRE_KP = 0x2000  # Key Present 
 11  GRE_SP = 0x1000  # Sequence Present 
 12  GRE_SS = 0x0800  # Strict Source Route 
 13  GRE_AP = 0x0080  # Acknowledgment Present 
 14   
 15  GRE_opt_fields = ( 
 16      (GRE_CP|GRE_RP, 'sum', 'H'), (GRE_CP|GRE_RP, 'off', 'H'), 
 17      (GRE_KP, 'key', 'I'), (GRE_SP, 'seq', 'I'), (GRE_AP, 'ack', 'I') 
 18      ) 
19 -class GRE(dpkt.Packet):
20 __hdr__ = ( 21 ('flags', 'H', 0), 22 ('p', 'H', 0x0800), # ETH_TYPE_IP 23 ) 24 _protosw = {} 25 sre = ()
26 - def get_v(self):
27 return self.flags & 0x7
28 - def set_v(self, v):
29 self.flags = (self.flags & ~0x7) | (v & 0x7)
30 v = property(get_v, set_v) 31
32 - def get_recur(self):
33 return (self.flags >> 5) & 0x7
34 - def set_recur(self, v):
35 self.flags = (self.flags & ~0xe0) | ((v & 0x7) << 5)
36 recur = property(get_recur, set_recur) 37
38 - class SRE(dpkt.Packet):
39 __hdr__ = [ 40 ('family', 'H', 0), 41 ('off', 'B', 0), 42 ('len', 'B', 0) 43 ]
44 - def unpack(self, buf):
45 dpkt.Packet.unpack(self, buf) 46 self.data = self.data[:self.len]
47
48 - def opt_fields_fmts(self):
49 if self.v == 0: 50 fields, fmts = [], [] 51 opt_fields = GRE_opt_fields 52 else: 53 fields, fmts = [ 'len', 'callid' ], [ 'H', 'H' ] 54 opt_fields = GRE_opt_fields[-2:] 55 for flags, field, fmt in opt_fields: 56 if self.flags & flags: 57 fields.append(field) 58 fmts.append(fmt) 59 return fields, fmts
60
61 - def unpack(self, buf):
62 dpkt.Packet.unpack(self, buf) 63 fields, fmts = self.opt_fields_fmts() 64 if fields: 65 fmt = ''.join(fmts) 66 fmtlen = struct.calcsize(fmt) 67 vals = struct.unpack(fmt, self.data[:fmtlen]) 68 self.data = self.data[fmtlen:] 69 self.__dict__.update(dict(zip(fields, vals))) 70 if self.flags & GRE_RP: 71 l = [] 72 while True: 73 sre = self.SRE(self.data) 74 l.append(sre) 75 if not sre.len: 76 break 77 self.sre = l 78 skip = sum(map(len, self.sre)) 79 self.data = self.data[skip:] 80 self.data = ethernet.Ethernet._typesw[self.p](self.data) 81 setattr(self, self.data.__class__.__name__.lower(), self.data)
82
83 - def __len__(self):
84 opt_fmtlen = struct.calcsize(''.join(self.opt_fields_fmts()[1])) 85 return self.__hdr_len__ + opt_fmtlen + \ 86 sum(map(len, self.sre)) + len(self.data)
87 88 # XXX - need to fix up repr to display optional fields... 89
90 - def __str__(self):
91 fields, fmts = self.opt_fields_fmts() 92 if fields: 93 vals = [] 94 for f in fields: 95 vals.append(getattr(self, f)) 96 opt_s = struct.pack(''.join(fmts), *vals) 97 else: 98 opt_s = '' 99 return self.pack_hdr() + opt_s + ''.join(map(str, self.sre)) + \ 100 str(self.data)
101 102 # XXX - auto-load GRE dispatch table from Ethernet dispatch table 103 import ethernet 104 GRE._protosw.update(ethernet.Ethernet._typesw) 105