Python Sniffer Implementation for Windows (#1147)

* Initial function loading of new listener interface.

* Additional changes for Node sniffer interface

* Use Interface Index instead of GUID

* Initialize Handle in sniffer

* Put Channel in the sniffer message
This commit is contained in:
Nick Banks
2017-01-18 09:10:07 -08:00
committed by Jonathan Hui
parent 419d251e2f
commit 71f47c105e
4 changed files with 359 additions and 2 deletions
+62 -2
View File
@@ -27,11 +27,11 @@
# POSSIBILITY OF SUCH DAMAGE.
#
import ctypes
import os
import socket
import sys
class SnifferTransport(object):
""" Interface for transport that allows eavesdrop other nodes. """
@@ -148,6 +148,66 @@ class SnifferSocketTransport(SnifferTransport):
return bytearray(data), nodeid
class MacFrame(ctypes.Structure):
_fields_ = [("buffer", ctypes.c_ubyte * 128),
("length", ctypes.c_ubyte),
("nodeid", ctypes.c_uint)]
class SnifferVirtualTransport(SnifferTransport):
""" Virtual interface based implementation of sniffer transport. """
def __init__(self, nodeid):
self.Handle = None
# Load the DLL
self.Api = ctypes.WinDLL("otnodeapi.dll")
if self.Api == None:
raise OSError("Failed to load otnodeapi.dll!")
# Define the functions
self.Api.otListenerInit.argtypes = [ctypes.c_uint]
self.Api.otListenerInit.restype = ctypes.c_void_p
self.Api.otListenerFinalize.argtypes = [ctypes.c_void_p]
self.Api.otListenerRead.argtypes = [ctypes.c_void_p, ctypes.POINTER(MacFrame)]
def __del__(self):
if not self.is_opened:
return
self.close()
def open(self):
if self.is_opened:
raise RuntimeError("Transport is already opened.")
# Initialize a listener
self.Handle = self.Api.otListenerInit(0)
if not self.is_opened:
raise RuntimeError("Transport opening failed.")
def close(self):
if not self.is_opened:
raise RuntimeError("Transport is closed.")
self.Api.otListenerFinalize(self.Handle);
self.Handle = None
@property
def is_opened(self):
return bool(self.Handle is not None)
def recv(self, bufsize):
frame = MacFrame()
pFrame = ctypes.pointer(frame);
self.Api.otListenerRead(self.Handle, pFrame)
return bytearray(frame.buffer)[:frame.length], frame.nodeid
class SnifferTransportFactory(object):
def create_transport(self, nodeid):
@@ -155,4 +215,4 @@ class SnifferTransportFactory(object):
return SnifferSocketTransport(nodeid)
else:
raise NotImplementedError
return SnifferVirtualTransport(nodeid)