2011-09-28 60 views
1

我目前有一个Python 2.6的代码段,它同时运行两个循环。该代码使用gps(gpsd)模块和scapy模块。基本上,第一个功能(gpsInfo)包含一个连续的while循环,从GPS设备获取GPS数据并将位置写入控制台。第二个功能(ClientDetect)运行在一个连续的循环中,同时嗅探wifi数据的空气并在发现特定数据包时打印这些数据。我将这两个循环与GPS作为后台线程运行。我想要做的事情(并且一直在努力5天来研究如何)是,当ClientDetect函数找到匹配并打印相应的信息时,我想要打印到相应的GPS坐标时打印到安慰。目前我的代码似乎不工作。两个同时发生的Python循环有一个结果

observedclients = [] p = "" # Relate to wifi packet session = 
gps.gps(mode=gps.WATCH_NEWSTYLE) 

def gpsInfo(): 

    while True: 
     session.poll() 
     time.sleep(5) 
     if gps.PACKET_SET: 
      session.stream 
      print session.fix.latitude + session.fix.longitude 
      time.sleep(0.1) 

def WifiDetect(p): 
    if p.haslayer(Dot11): 
     if p.type == 0 and p.subtype in stamgmtstypes: 
      if p.addr2 not in observedclients: 
       print p.addr2 
       observedclients.append(p.addr2) 

def ActivateWifiDetect(): 
    sniff(iface="mon0", prn=WifiDetect) 

if __name__ == '__main__': 
    t = threading.Thread(target=gpsInfo) 
    t.start() 
    WifiDetect() 

任何人都可以看看我的代码来看看如何最好地同时获取数据的时候有一个WiFi命中,为GPS坐标太打印?有人提到实施排队,但我已经研究过这一点,但对于如何实施它却无济于事。

如上所述,此代码的目的是扫描GPS和特定的WiFi数据包,并在检测到时打印与数据包有关的细节以及检测到的位置。

回答

2

一个简单的方法是将gps位置存储在全局变量中,并且在需要打印某些数据时让wifi嗅探线程读取全局数据;这个问题是因为两个线程可以同时访问全局变量,所以你需要用一个互斥体来包装它;

last_location = (None, None) 
location_mutex = threading.Lock() 

def gpsInfo(): 
    global last_location 
    while True: 
     session.poll() 
     time.sleep(5) 
     if gps.PACKET_SET: 
      session.stream 
      with location_mutex: 
       # DON'T Print from inside thread! 
       last_location = session.fix.latitude, session.fix.longitude 
      time.sleep(0.1) 

def WifiDetect(p): 
    if p.haslayer(Dot11): 
     if p.type == 0 and p.subtype in stamgmtstypes: 
      if p.addr2 not in observedclients: 
       with location_mutex: 
        print p.addr2, last_location 
        observedclients.append((p.addr2, last_location)) 
+0

虽然互斥锁/锁虽然,我会不会停止GPS循环等待检测到一个WiFi数据包?通过这个我的意思是,它可能是5分钟之前,特定的WiFi数据包被嗅探,如果是这样的话,GPS位置不会过期,因为检测到的第一个GPS位置被锁定,等待wifi结果? – thefragileomen

+0

不,该锁仅保留足够长的时间来读取或写入该变量,两个线程都不会在它们持有锁的同时等待IO。真正阻止该锁的可能性非常低。唯一一次你可能会看到实际等待锁定的时间是'print'实际上将新行刷新到控制台所需的时间,这段时间并不长。 – SingleNegationElimination

+0

感谢TokenMacGuy的工作。我实际上修改了我的代码,以便从GPS设备获取Unix时间,以便与检测到数据包的时间进行比较,并将它们精确同步到第二个时间,这反映报告的位置确实是数据包发生时的位置嗅了嗅。 – thefragileomen

1

你需要告诉python你正在使用一个外部变量,当你在一个函数中使用gps。代码应该是这样的:

def gpsInfo(): 
    global gps # new line 

    while True: 
     session.poll() 
     time.sleep(5) 
     if gps.PACKET_SET: 
      session.stream 
      print session.fix.latitude + session.fix.longitude 
      time.sleep(0.1) 


def WifiDetect(p): 
    global p, observedclients # new line 

    if p.haslayer(Dot11): 
     if p.type == 0 and p.subtype in stamgmtstypes: 
      if p.addr2 not in observedclients: 
       print p.addr2 
       observedclients.append(p.addr2) 
+0

通常不需要指定全局。只有当你想重新绑定它。 –

+0

嗯我一直有很多问题没有指定全球。 – Serdalis

1

我认为你应该对你的目标更具体。

如果你想要做的就是GPS COORDS当Wi-Fi网络的嗅探,只是做(伪代码):

while True: 
    if networkSniffed(): 
     async_GetGPSCoords() 

如果你想有一个日志中的所有GPS COORDS的,想匹配随着Wifi网络数据,只需打印所有的数据与时间戳,做后处理通过时间戳与GPS坐标相匹配的Wifi网络。