<s> """<STR_LIT>""" <EOL> import os <EOL> import json <EOL> import gevent <EOL> import logging <EOL> from gevent import subprocess <EOL> from buttplug . core import heartbeat <EOL> from buttplug . core import greenlet <EOL> from buttplug . core import event <EOL> from buttplug . core import queue <EOL> from buttplug . core import config <EOL> class Plugin ( object ) : <EOL> """<STR_LIT>""" <EOL> PLUGIN_INFO_FILE = "<STR_LIT>" <EOL> PLUGIN_REQUIRED_KEYS = [ u"<STR_LIT:name>" , u"<STR_LIT:version>" , u"<STR_LIT>" , u"<STR_LIT>" ] <EOL> def __init__ ( self , info , plugin_dir ) : <EOL> self . plugin_path = os . path . join ( config . get_dir ( "<STR_LIT>" ) , plugin_dir ) <EOL> self . executable_path = os . path . join ( config . get_dir ( "<STR_LIT>" ) , <EOL> plugin_dir , info [ "<STR_LIT>" ] ) <EOL> if not os . path . exists ( self . executable_path ) : <EOL> raise PluginException ( "<STR_LIT>" + <EOL> self . executable_path ) <EOL> self . name = info [ "<STR_LIT:name>" ] <EOL> self . version = info [ "<STR_LIT:version>" ] <EOL> self . messages = info [ "<STR_LIT>" ] <EOL> _plugins = { } <EOL> _devices = { } <EOL> class PluginException ( Exception ) : <EOL> """<STR_LIT>""" <EOL> pass <EOL> def scan_for_plugins ( ) : <EOL> """<STR_LIT>""" <EOL> for i in os . listdir ( config . get_dir ( "<STR_LIT>" ) ) : <EOL> plugin_file = os . path . join ( config . get_dir ( "<STR_LIT>" ) , i , <EOL> Plugin . PLUGIN_INFO_FILE ) <EOL> if not os . path . exists ( plugin_file ) : <EOL> continue <EOL> info = None <EOL> try : <EOL> with open ( plugin_file ) as pfile : <EOL> info = json . load ( pfile ) <EOL> except ValueError : <EOL> logging . warning ( "<STR_LIT>" , i ) <EOL> continue <EOL> if not set ( Plugin . PLUGIN_REQUIRED_KEYS ) . issubset ( set ( info . keys ( ) ) ) : <EOL> raise PluginException ( "<STR_LIT>" ) <EOL> if info [ "<STR_LIT:name>" ] in _plugins . keys ( ) : <EOL> raise PluginException ( "<STR_LIT>" + <EOL> info [ "<STR_LIT:name>" ] ) <EOL> greenlet . spawn_gevent_func ( "<STR_LIT>" % info [ "<STR_LIT:name>" ] , <EOL> "<STR_LIT>" , _run_count_plugin , Plugin ( info , i ) ) <EOL> def _start_process ( cmd , identity ) : <EOL> """<STR_LIT>""" <EOL> cmd += [ "<STR_LIT>" % identity ] <EOL> logging . info ( "<STR_LIT>" , cmd ) <EOL> try : <EOL> proc = subprocess . Popen ( cmd , stdout = subprocess . PIPE , <EOL> stderr = subprocess . PIPE ) <EOL> except OSError , e : <EOL> logging . warning ( "<STR_LIT>" , <EOL> e . strerror ) <EOL> return None <EOL> return proc <EOL> def _run_count_plugin ( plugin ) : <EOL> """<STR_LIT>""" <EOL> count_identity = greenlet . random_ident ( ) <EOL> e = event . add ( count_identity , "<STR_LIT>" ) <EOL> count_process_cmd = [ plugin . executable_path , "<STR_LIT>" % <EOL> config . get_value ( "<STR_LIT>" ) , "<STR_LIT>" ] <EOL> count_process = _start_process ( count_process_cmd , count_identity ) <EOL> if not count_process : <EOL> logging . warning ( "<STR_LIT>" , <EOL> plugin . name ) <EOL> return <EOL> try : <EOL> e . get ( block = True , timeout = <NUM_LIT:1> ) <EOL> except gevent . Timeout : <EOL> logging . info ( "<STR_LIT>" , <EOL> plugin . name ) <EOL> return <EOL> except greenlet . BPGreenletExit : <EOL> logging . debug ( "<STR_LIT>" , plugin . name ) <EOL> return <EOL> logging . info ( "<STR_LIT>" , plugin . name , <EOL> count_identity ) <EOL> greenlet . add_identity_greenlet ( count_identity , gevent . getcurrent ( ) ) <EOL> hb = heartbeat . spawn_heartbeat ( count_identity , gevent . getcurrent ( ) ) <EOL> _plugins [ plugin . name ] = plugin <EOL> while True : <EOL> queue . add ( count_identity , [ "<STR_LIT:s>" , "<STR_LIT>" ] ) <EOL> e = event . add ( count_identity , "<STR_LIT>" ) <EOL> try : <EOL> ( i , msg ) = e . get ( block = True , timeout = <NUM_LIT:1> ) <EOL> except gevent . Timeout : <EOL> logging . info ( "<STR_LIT>" , plugin . name ) <EOL> break <EOL> except greenlet . BPGreenletExit : <EOL> logging . debug ( "<STR_LIT>" , plugin . name ) <EOL> break <EOL> _devices [ plugin . name ] = msg [ <NUM_LIT:2> ] <EOL> try : <EOL> gevent . sleep ( <NUM_LIT:1> ) <EOL> except greenlet . BPGreenletExit : <EOL> logging . debug ( "<STR_LIT>" , plugin . name ) <EOL> break <EOL> if not hb . ready ( ) : <EOL> hb . kill ( exception = greenlet . BPGreenletExit , block = True , timeout = <NUM_LIT:1> ) <EOL> greenlet . remove_identity_greenlet ( count_identity , kill_greenlet = False ) <EOL> del _plugins [ plugin . name ] <EOL> queue . add ( count_identity , [ "<STR_LIT:s>" , "<STR_LIT>" ] ) <EOL> logging . debug ( "<STR_LIT>" , count_identity , <EOL> plugin . name ) <EOL> def plugins_available ( ) : <EOL> """<STR_LIT>""" <EOL> return _plugins . values ( ) <EOL> _ctd = { } <EOL> _dtc = { } <EOL> def forward_device_msg ( identity , msg ) : <EOL> """<STR_LIT>""" <EOL> to_alias = msg [ <NUM_LIT:0> ] <EOL> print _ctd <EOL> print _dtc <EOL> to_addr = None <EOL> new_msg = None <EOL> if to_alias == "<STR_LIT:c>" : <EOL> new_msg = [ identity ] + list ( msg [ <NUM_LIT:1> : ] ) <EOL> to_addr = _dtc [ identity ] [ <NUM_LIT:0> ] <EOL> elif to_alias in _dtc . keys ( ) : <EOL> new_msg = [ "<STR_LIT:s>" ] + list ( msg [ <NUM_LIT:1> : ] ) <EOL> to_addr = _ctd [ identity ] [ <NUM_LIT:0> ] <EOL> else : <EOL> logging . warning ( "<STR_LIT>" , identity , to_addr ) <EOL> return <EOL> logging . debug ( "<STR_LIT>" , new_msg , to_addr ) <EOL> queue . add ( to_addr , new_msg ) <EOL> def kill_claims ( identity ) : <EOL> """<STR_LIT>""" <EOL> if identity not in _ctd : <EOL> logging . warning ( "<STR_LIT>" , identity ) <EOL> return <EOL> for dev_id in _ctd [ identity ] : <EOL> g = greenlet . get_identity_greenlet ( dev_id ) <EOL> if g is None : <EOL> logging . warning ( "<STR_LIT>" , dev_id , <EOL> identity ) <EOL> continue <EOL> g . kill ( exception = greenlet . BPGreenletExit , timeout = <NUM_LIT:1> , block = True ) <EOL> def run_device_plugin ( identity , msg ) : <EOL> """<STR_LIT>""" <EOL> p = None <EOL> dev_id = msg [ <NUM_LIT:2> ] <EOL> for ( plugin_name , device_list ) in _devices . items ( ) : <EOL> if dev_id in device_list : <EOL> p = _plugins [ plugin_name ] <EOL> if p is None : <EOL> logging . warning ( "<STR_LIT>" , dev_id ) <EOL> queue . add ( identity , [ "<STR_LIT:s>" , "<STR_LIT>" , dev_id , False ] ) <EOL> return <EOL> if dev_id in _dtc . keys ( ) : <EOL> logging . warning ( "<STR_LIT>" , dev_id ) <EOL> queue . add ( identity , [ "<STR_LIT:s>" , "<STR_LIT>" , dev_id , False ] ) <EOL> return <EOL> device_process = _start_process ( [ p . executable_path , "<STR_LIT>" % <EOL> config . get_value ( "<STR_LIT>" ) ] , <EOL> dev_id ) <EOL> if not device_process : <EOL> logging . warning ( "<STR_LIT>" , <EOL> p . name ) <EOL> return <EOL> e = event . add ( dev_id , "<STR_LIT>" ) <EOL> try : <EOL> ( i , m ) = e . get ( timeout = <NUM_LIT:5> ) <EOL> except greenlet . BPGreenletExit : <EOL> return <EOL> except gevent . Timeout : <EOL> logging . info ( "<STR_LIT>" , dev_id ) <EOL> queue . add ( dev_id , [ "<STR_LIT:s>" , "<STR_LIT>" ] ) <EOL> queue . add ( identity , [ "<STR_LIT:s>" , "<STR_LIT>" , dev_id , False ] ) <EOL> return <EOL> greenlet . add_identity_greenlet ( dev_id , gevent . getcurrent ( ) ) <EOL> hb = heartbeat . spawn_heartbeat ( dev_id , gevent . getcurrent ( ) ) <EOL> queue . add ( dev_id , [ "<STR_LIT:s>" , "<STR_LIT>" , dev_id ] ) <EOL> e = event . add ( dev_id , "<STR_LIT>" ) <EOL> try : <EOL> ( i , m ) = e . get ( ) <EOL> except greenlet . BPGreenletExit : <EOL> queue . add ( dev_id , [ "<STR_LIT:s>" , "<STR_LIT>" ] ) <EOL> return <EOL> if m [ <NUM_LIT:3> ] is False : <EOL> logging . info ( "<STR_LIT>" , dev_id ) <EOL> queue . add ( dev_id , [ "<STR_LIT:s>" , "<STR_LIT>" ] ) <EOL> queue . add ( identity , [ "<STR_LIT:s>" , "<STR_LIT>" , dev_id , False ] ) <EOL> return <EOL> queue . add ( identity , [ "<STR_LIT:s>" , "<STR_LIT>" , dev_id , True ] ) <EOL> if identity not in _ctd . keys ( ) : <EOL> _ctd [ identity ] = [ ] <EOL> _ctd [ identity ] . append ( dev_id ) <EOL> if dev_id not in _dtc . keys ( ) : <EOL> _dtc [ dev_id ] = [ ] <EOL> _dtc [ dev_id ] . append ( identity ) <EOL> while True : <EOL> try : <EOL> gevent . sleep ( <NUM_LIT:1> ) <EOL> except greenlet . BPGreenletExit : <EOL> break <EOL> if not hb . ready ( ) : <EOL> hb . kill ( exception = greenlet . BPGreenletExit , block = True , timeout = <NUM_LIT:1> ) <EOL> _ctd [ identity ] . remove ( dev_id ) <EOL> del _dtc [ dev_id ] <EOL> greenlet . remove_identity_greenlet ( dev_id , kill_greenlet = False ) <EOL> queue . add ( dev_id , [ "<STR_LIT:s>" , "<STR_LIT>" ] ) <EOL> logging . debug ( "<STR_LIT>" , dev_id ) </s>
