def response_cb(dialog, response, portNum=portNum, successFunc=successFunc, programName=programName): pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return if response == 0: System.kill_process(pid) startTime = time.time() while time.time() < startTime + 2: pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return time.sleep(0.1) def try_again(dialog, response, portNum=portNum, successFunc=successFunc): self.prompt_about_port(portNum, successFunc) self.show_msgbox( "Failed to kill program! Try killing process yourself. pid=%s, name=%s" % (pid, programName), cb=try_again) elif response == 1: self.prompt_about_port(portNum, successFunc)
def make_platform_status(): statusList = [] #add program state: for varName in ("IS_LIVE", "INSTALLED", "PY2EXE", "JUST_UPDATED", "DEBUG", "IS_ADMIN"): statusList.append([varName, getattr(ProgramState, varName, None)]) #check the state of each important directory: for varName in ("STARTING_DIR", "INSTALL_DIR", "USER_DIR"): dirName = getattr(ProgramState, varName, None) if dirName: #convert to a string if necessary: readAccess, writeAccess = System.check_folder_permissions(dirName) dirName = System.encode_for_filesystem(dirName) else: readAccess, writeAccess = (False, False) readStr = " " writeStr = " " if readAccess: readStr = "r" if writeAccess: writeStr = "w" permissionStr = readStr + writeStr dirStr = permissionStr + " " + str(dirName) statusList.append([varName, dirStr]) #what type of GUI are they using? guiType = "console" if ProgramState.USE_GTK: guiType = "gtk" elif ProgramState.USE_CURSES: guiType = "gtk" statusList.append(["GUI", guiType]) statusString = "\n".join([": \t".join([str(r) for r in line]) for line in statusList]) return statusString
def __init__(self, name, port, trafficType="TCP"): """ name = string describing this port (ie, the purpose) port = int port number to try forwarding """ #: string describing the purpose of this port self.name = name #: what type of traffic to forward (TCP or UDP) self.trafficType = trafficType #: port number to try forwarding self.port = port #: whether the UPNP program has been started yet self.startedUPNP = False #: whether UPNP succeeded self.usedUPNP = False if System.IS_WINDOWS: self.upnpcPath = os.path.join(Globals.WINDOWS_BIN, "upnp", "upnpc-static.exe") self.workingDir = os.path.join(Globals.WINDOWS_BIN, "upnp") else: self.upnpcPath = u"upnpc-static" self.workingDir = os.getcwd().decode('utf-8') #: the path to the upnp binary self.upnpcPath = System.encode_for_filesystem(self.upnpcPath) #: the path to the working directory for our binary self.workingDir = System.encode_for_filesystem(self.workingDir)
def prompt_about_port(self, portNum, successFunc): pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return programs = System.get_process_ids() programName = "None" for p in programs: if p[1] == pid: programName = p[0] break def response_cb(dialog, response, portNum=portNum, successFunc=successFunc, programName=programName): pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return if response == 0: System.kill_process(pid) startTime = time.time() while time.time() < startTime + 2: pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return time.sleep(0.1) def try_again(dialog, response, portNum=portNum, successFunc=successFunc): self.prompt_about_port(portNum, successFunc) self.show_msgbox("Failed to kill program! Try killing process yourself. pid=%s, name=%s" % (pid, programName), cb=try_again) elif response == 1: self.prompt_about_port(portNum, successFunc) self.show_msgbox("Port %s is in use by another program (%s). BitBlinder needs this port to run. \n\nWould you like to kill that program or retry the port?" % (portNum, programName), "Port Conflict!", response_cb, buttons=("Kill", 0, "Retry", 1))
def get_launch_command(): #if we're not running from py2exe, our executable is python, and it needs the main script name: encodedExe = System.encode_for_filesystem(ProgramState.EXECUTABLE) if not ProgramState.INSTALLED: encodedScript = System.encode_for_filesystem(ProgramState.MAIN_SCRIPT) command = "\"" + encodedExe + '" "' + encodedScript + "\"" else: command = "\"" + encodedExe + "\"" return command
def apply_update(): encodedInstallDir = System.encode_for_filesystem(ProgramState.INSTALL_DIR) encodedUpdateFile = System.encode_for_filesystem(Globals.UPDATE_FILE_NAME) cmd = "%s /S --LOCATION=\"%s\" --PID=%s" % (encodedUpdateFile, encodedInstallDir, os.getpid()) log_msg("Updater command: %s" % (cmd)) if ProgramState.INSTALLED: p = subprocess.Popen(cmd, cwd=os.getcwd()) else: log_msg("Go run the updater if you really feel like it.", 2)
def exit(self): shutdownDeferred = defer.Deferred() try: #for every process that did not yet exit, kill it for processObj in self.processes: #TODO: change to this once kill_recursive runs on linux: #kill_recursive(p.pid) System.kill_process(processObj.pid) except Exception, error: log_ex(error, "Failed to kill Application process:")
def prompt_about_port(self, portNum, successFunc): pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return programs = System.get_process_ids() programName = "None" for p in programs: if p[1] == pid: programName = p[0] break def response_cb(dialog, response, portNum=portNum, successFunc=successFunc, programName=programName): pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return if response == 0: System.kill_process(pid) startTime = time.time() while time.time() < startTime + 2: pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return time.sleep(0.1) def try_again(dialog, response, portNum=portNum, successFunc=successFunc): self.prompt_about_port(portNum, successFunc) self.show_msgbox( "Failed to kill program! Try killing process yourself. pid=%s, name=%s" % (pid, programName), cb=try_again) elif response == 1: self.prompt_about_port(portNum, successFunc) self.show_msgbox( "Port %s is in use by another program (%s). BitBlinder needs this port to run. \n\nWould you like to kill that program or retry the port?" % (portNum, programName), "Port Conflict!", response_cb, buttons=("Kill", 0, "Retry", 1))
def __init__(self, conn, args): MessageServer.MessageServerHandler.__init__(self, conn, args) self.clientConn.sendMessage("SUCCESS") args = args.split("\n") startingDir = args.pop(0) decodedStartingDir = System.decode_from_filesystem(startingDir) Startup.handle_args(decodedStartingDir, args)
def set_start_on_boot(self, newVal): """Change the registry key (if necessary) for auto launching BitBlinder at startup on windows, does nothing on *nix. Ends up calling a function made with NSIS that will get the necessary permissions to do the modification @param newVal: whether to start on boot or not @type newVal: bool""" if not System.IS_WINDOWS: return #No need to change if the value is already correct? if self.check_start_on_boot() == newVal: if self.startOnBootDeferred: log_msg("Failed to modify 'start at bootup' value, already editing the registry!", 0) return if self.startOnBootDeferred: return def uac_done(result): self.startOnBootDeferred = None if result != True: log_ex(result, "Bad result while running BitBlinderSettingsUpdate.exe") #launch the program: if newVal: args = " --add-startup=" + ClientUtil.get_launch_command() else: args = " --remove-startup" encodedExe = System.encode_for_filesystem(os.path.join(Globals.WINDOWS_BIN, "BitBlinderSettingsUpdate.exe")) self.startOnBootDeferred = SerialProcessLauncher.get().run_app(encodedExe + " /S" + args) self.startOnBootDeferred.addCallback(uac_done) self.startOnBootDeferred.addErrback(uac_done)
def send_startup_arguments(startingDir): #send arguments to any process that is already running: encodedStartingDir = System.encode_for_filesystem(startingDir) argsToSend = [encodedStartingDir] + sys.argv[1:] if StartupClient.send_args(argsToSend): #if we managed to send the args to the other instance, we're done: sys.exit(0)
def set_half_open_conns(self, app, halfOpenConnections): """uses tcpz to change the number of half open connections to 218""" try: #this is a windows specific fix: if not System.IS_WINDOWS: return #also, this is only necessary if we are acting as a Tor server: if not app.torApp.settings.beRelay: return winInfo = sys.getwindowsversion() #not sure if this exists, but just in case :) if winInfo[0] > 6: return #if this is win7, we're all set: if winInfo[0] == 6 and winInfo[1] >= 1: return #if this is vista, check the service pack level: if winInfo[0] == 6 and winInfo[1] == 0: #default and SP1 need fixing: if winInfo[4] not in ('', 'Service Pack 1'): return if halfOpenConnections: #if we already did this, also return: if self.appliedHalfOpenCorrection: return self.appliedHalfOpenCorrection = True #we should only ever run one tcp-z, no going back etiher ids = System.get_process_ids() for id in ids: if id[0] == 'tcpz.exe': return #create the vbs script file to do what we need: encodedScriptFile = System.encode_for_filesystem( os.path.join(Globals.USER_DATA_DIR, "tcpz.vbs")) encodedExe = System.encode_for_filesystem( os.path.join(Globals.WINDOWS_BIN, 'tcpz.exe')) cmd = """Set oShell = WScript.CreateObject("WSCript.shell")\r\ncall oShell.run("cmd /c ""%s"" -limit:220 -autoexit", 0, false)\r\n""" % ( encodedExe) f = open(encodedScriptFile, "wb") f.write(cmd) f.close() #and execute the script: SerialProcessLauncher.get().run_app( 'cscript.exe "%s" //B //Nologo' % (encodedScriptFile)) return except Exception, e: log_ex(e, "Failed to launch tcpz.exe")
def prompt_about_port(self, portNum, successFunc): pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return programs = System.get_process_ids() programName = "None" for p in programs: if p[1] == pid: programName = p[0] break #this has to go in the console as it isn't seen otherwise self.shutdown_func = "" msg = "Port %s is taken by program %s (pid=%s). Please kill the program or otherwise free the port and restart BitBlinder."% (portNum, programName, pid) log_msg(msg, 0) atexit.register(self.print_wrapper, msg) GlobalEvents.throw_event("quit_signal")
def cleanup_previous_processes(installDir): if System.IS_WINDOWS: #ensure that no processes from a previous run are left over: try: oldProcs = System.get_process_ids_by_exe_path( re.compile( "^%s.*(tor|firefox|firefoxportable|polipo|bitblinder|bitblindersettingsupdate)\\.exe$" % (installDir.replace("\\", "\\\\")), re.IGNORECASE)) for pid in oldProcs: #dont commit suicide... if pid == os.getpid(): continue log_msg( "Trying to shut down leftover process (%s) while booting BitBlinder..." % (pid), 1) System.kill_process(pid) except Exception, error: log_ex(error, "Failed while trying to shut down old processes")
def prompt_about_port(self, portNum, successFunc): pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return programs = System.get_process_ids() programName = "None" for p in programs: if p[1] == pid: programName = p[0] break #this has to go in the console as it isn't seen otherwise self.shutdown_func = "" msg = "Port %s is taken by program %s (pid=%s). Please kill the program or otherwise free the port and restart BitBlinder." % ( portNum, programName, pid) log_msg(msg, 0) atexit.register(self.print_wrapper, msg) GlobalEvents.throw_event("quit_signal")
def set_half_open_conns(self, app, halfOpenConnections): """uses tcpz to change the number of half open connections to 218""" try: #this is a windows specific fix: if not System.IS_WINDOWS: return #also, this is only necessary if we are acting as a Tor server: if not app.torApp.settings.beRelay: return winInfo = sys.getwindowsversion() #not sure if this exists, but just in case :) if winInfo [0] > 6: return #if this is win7, we're all set: if winInfo[0] == 6 and winInfo[1] >= 1: return #if this is vista, check the service pack level: if winInfo[0] == 6 and winInfo[1] == 0: #default and SP1 need fixing: if winInfo[4] not in ('', 'Service Pack 1'): return if halfOpenConnections: #if we already did this, also return: if self.appliedHalfOpenCorrection: return self.appliedHalfOpenCorrection = True #we should only ever run one tcp-z, no going back etiher ids = System.get_process_ids() for id in ids: if id[0] == 'tcpz.exe': return #create the vbs script file to do what we need: encodedScriptFile = System.encode_for_filesystem(os.path.join(Globals.USER_DATA_DIR, "tcpz.vbs")) encodedExe = System.encode_for_filesystem(os.path.join(Globals.WINDOWS_BIN,'tcpz.exe')) cmd = """Set oShell = WScript.CreateObject("WSCript.shell")\r\ncall oShell.run("cmd /c ""%s"" -limit:220 -autoexit", 0, false)\r\n""" % (encodedExe) f = open(encodedScriptFile, "wb") f.write(cmd) f.close() #and execute the script: SerialProcessLauncher.get().run_app('cscript.exe "%s" //B //Nologo' % (encodedScriptFile)) return except Exception, e: log_ex(e, "Failed to launch tcpz.exe")
def response_cb(dialog, response, portNum=portNum, successFunc=successFunc, programName=programName): pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return if response == 0: System.kill_process(pid) startTime = time.time() while time.time() < startTime + 2: pid = System.get_pid_from_port(portNum) if pid <= 0: successFunc() return time.sleep(0.1) def try_again(dialog, response, portNum=portNum, successFunc=successFunc): self.prompt_about_port(portNum, successFunc) self.show_msgbox("Failed to kill program! Try killing process yourself. pid=%s, name=%s" % (pid, programName), cb=try_again) elif response == 1: self.prompt_about_port(portNum, successFunc)
def _input_to_unicode(input): """Take some input and make sure it is unicode. If it's a string, decode it using the filesystem encoding. If it's unicode, just return it directly""" if type(input) == types.StringType: return System.decode_from_filesystem(input) elif type(input) == types.UnicodeType: return input else: raise AssertionError("Input must be a basestring")
def _check_for_firefoxes(self): self.checkFFEvent = None existingFFPIDs = System.get_process_ids_by_exe_path(re.compile("^.*apps\\\\firefoxportable.*\\\\firefox(portable)*.exe$", re.IGNORECASE)) #if it is NOT running if len(existingFFPIDs) <= 0: log_msg("Waited long enough. This is probably shutdown time.", 4) self.stop() return #if firefox is running now, lets just update our process list: for pid in existingFFPIDs: self.add_process(Process.Process(pid))
def check_port(portNum, successFunc): if portNum: pid = System.get_pid_from_port(portNum) if pid > 0: controller = GUIController.get() if controller: controller.prompt_about_port(portNum, successFunc) else: log_msg("no gui controller yet to prompt_about_port", 2) return successFunc()
def _launch_thread(self): processes = [] if len(self.liveCircuits) <= 0: #build some initial Circuits self.launch_initial_circuits() if System.IS_WINDOWS: #we determine which processes should live and die based on their exe path. FF_PROC_REGEX = re.compile("^.*\\\\apps\\\\firefoxportable.*\\\\(firefoxportable.exe|firefox.exe)$", re.IGNORECASE) #kill any leftover processes from last time: existingFFPIDs = System.get_process_ids_by_exe_path(FF_PROC_REGEX) for pid in existingFFPIDs: kill_process(pid) #launch polipo: path = "%s\\%s\\" % (self.appBasePath, self.name) p = LaunchProcess.LaunchProcess([path+"polipo.exe", "-c", path+"polipo.conf"], creationflags=win32process.CREATE_NO_WINDOW) self.polipoProc = Process.Process(p.pid) #launch firefox: p = LaunchProcess.LaunchProcess([path+"FirefoxPortable.exe", self.startPage]) #have to wait for both processes to launch properly: children = System.get_process_ids_by_exe_path(FF_PROC_REGEX) startTime = time.time() #dont wait any more than 15 seconds for everything to be started while len(children) < 2 and time.time() < startTime + 15: time.sleep(0.2) children = System.get_process_ids_by_exe_path(FF_PROC_REGEX) #if some of the processes are STILL missing: if len(children) < 2: #kill what we have: for child in children: kill_process(child) #and inform the user: raise DependencyError("Failed to launch Firefox. Try again?") #create entries for FirefoxPortable.exe, Firefox.exe and polipo.exe: for pid in children: processes.append(Process.Process(pid)) processes.append(self.polipoProc) elif System.IS_LINUX: raise DependencyError("Anonymous browsing is not yet supported for Linux. Support is coming soon!") else: raise Exception("This platform is not supported: %s" % (sys.platform)) return processes
def startup(): #dont print stuff if we are py2exed if ProgramState.PY2EXE: def silence(text): pass Logger.PRINT_FUNCTION = silence ProgramState.START_TIME = time.time() ProgramState.IS_ADMIN = System.is_admin() ProgramState.MAIN_SCRIPT = _input_to_unicode(os.path.realpath(sys.argv[0])) #store the starting directory for later, to alter the argument paths if necessary ProgramState.STARTING_DIR = os.getcwdu() if sys.platform not in ("win32", "linux2"): log_msg( "We dont have any idea what platform you're on: %s\nDefaulting to 'linux2'" % (sys.platform), 0) #read any arguments that were passed in options = read_args() #check that all dependencies are installed check_requirements() ProgramState.EXECUTABLE = _input_to_unicode(sys.executable) #figure out where bitblinder is running from (ProgramState.INSTALL_DIR, ProgramState.INSTALLED) = get_install_directory() #change directory to the install dir, because that's what all my code assumes right now: os.chdir(ProgramState.INSTALL_DIR) import_gtk() #set the global paths for user data files ProgramState.USER_DIR = get_user_directory() set_global_paths(ProgramState.INSTALL_DIR, ProgramState.USER_DIR) #try to send our startup arguments to any previously started BitBlinder instances send_startup_arguments(ProgramState.STARTING_DIR) #remove any leftover processes or data from previous runs cleanup_previous_processes(ProgramState.INSTALL_DIR) cleanup_previous_update(options) install_reactor() #do the rest of the imports: start_psyco()
def write(unicodeFileName, coins): fileName = System.encode_for_filesystem(unicodeFileName) #do not overwrite existing until we're sure the whole file has been output newFileName = fileName + ".new" f = open(newFileName, "wb") msg = "" for coin in coins: msg += coin.write_binary() #TODO: these should probably be stored encrypted? use username and password to generate an AES key for the file #TODO: should there actually be a different key? What about if there are multiple users? f.write(msg) f.close() #move the file to the real location: shutil.move(newFileName, fileName)
def make_platform_status(): statusList = [] #add program state: for varName in ("IS_LIVE", "INSTALLED", "PY2EXE", "JUST_UPDATED", "DEBUG", "IS_ADMIN"): statusList.append([varName, getattr(ProgramState, varName, None)]) #check the state of each important directory: for varName in ("STARTING_DIR", "INSTALL_DIR", "USER_DIR"): dirName = getattr(ProgramState, varName, None) if dirName: #convert to a string if necessary: readAccess, writeAccess = System.check_folder_permissions(dirName) dirName = System.encode_for_filesystem(dirName) else: readAccess, writeAccess = (False, False) readStr = " " writeStr = " " if readAccess: readStr = "r" if writeAccess: writeStr = "w" permissionStr = readStr + writeStr dirStr = permissionStr + " " + str(dirName) statusList.append([varName, dirStr]) #what type of GUI are they using? guiType = "console" if ProgramState.USE_GTK: guiType = "gtk" elif ProgramState.USE_CURSES: guiType = "gtk" statusList.append(["GUI", guiType]) statusString = "\n".join( [": \t".join([str(r) for r in line]) for line in statusList]) return statusString
def import_gtk(): #set the GTK path stuff specially on windows: if System.IS_WINDOWS: if ProgramState.INSTALLED: Globals.WINDOWS_BIN = ProgramState.INSTALL_DIR encodedInstallDir = System.encode_for_filesystem( ProgramState.INSTALL_DIR) os.environ['GTK2_RC_FILES'] = encodedInstallDir os.environ['GTK_PATH'] = encodedInstallDir os.environ['GTK_BASEPATH'] = encodedInstallDir os.environ['PATH'] = encodedInstallDir else: os.environ['PATH'] += ";" + Globals.WINDOWS_BIN Globals.WINDOWS_BIN = os.path.realpath(Globals.WINDOWS_BIN) #import gtk import pygtk pygtk.require('2.0') #NOTE: this crazy bit is to avoid a warning from GTK, which prints an error. #we want to submit error logs if any errors happen, but dont want this particular warning to count #because it always happens and is pointless # temp = sys.argv # sys.argv = [] #funny stuff with system args warnings.simplefilter("ignore") import gtk # sys.argv = temp #reinstate warnings warnings.resetwarnings() import gobject #find and parse the right rc file rc_file = os.getcwdu() if not ProgramState.INSTALLED: rc_file = os.path.join(rc_file, 'windows', 'build', 'dist') rc_file = os.path.join(rc_file, 'share', 'themes', 'Default', 'gtk-2.0', 'gtkrc') gtk.rc_parse(rc_file) else: #import GTK if possible: try: #funny stuff with system args warnings.simplefilter("ignore") import pygtk pygtk.require('2.0') import gtk, gobject #reinstate warnings warnings.resetwarnings() except ImportError: log_msg("Failed to import gtk.", 1) ProgramState.USE_GTK = False
def read(unicodeFileName, addFunc): fileName = System.encode_for_filesystem(unicodeFileName) if not Files.file_exists(fileName): log_msg( "Could not load coins, file=%s does not exist." % (fileName), 1) return #TODO: properly deal with various filesystem errors--permissions, etc :-/ #read in the original file: f = open(fileName, "rb") data = f.read() while len(data) > 0: acoin = ACoin.ACoin(self) data = acoin.read_binary(data) if acoin.is_fresh(self.currentACoinInterval): addFunc(acoin) else: log_msg("Dropped an expired acoin from %s interval because we are at %s." % \ (acoin.interval,self.currentACoinInterval), 1) f.close()
def setup(): insts = [] clk = Clk(50E6) insts.append(clk.gen()) if 1: rst = ResetSignal(0, active = 1, async = 0) insts.append(rstgen(rst, 100 * nsec, clk)) else: rst = None system = System(clk, rst) bus = WbBus(system, addr_depth = 10, data_width = 32) rename_interface(bus, None) shifter_bus = ShifterBus(num_cs = 4) return insts, gen, [ system, bus, shifter_bus ]
def get_install_directory(): #check if we're running as an installation or not: if System.IS_WINDOWS: encodedExeName = System.encode_for_filesystem( os.path.basename(ProgramState.EXECUTABLE)).lower() if encodedExeName in ("python", "python.exe", "pythonw.exe"): isInstalled = False installDir = _input_to_unicode( os.path.realpath(os.path.dirname(sys.argv[0]))) else: isInstalled = True installDir = os.path.dirname(ProgramState.EXECUTABLE) else: installDir = _input_to_unicode( os.path.realpath(os.path.dirname(sys.argv[0]))) if installDir == "/usr/share/python-support/python-bitblinder/bitblinder": isInstalled = True else: isInstalled = False return (installDir, isInstalled)
def _wait(self): """Runs in a Twisted thread, just waiting for the process to finish""" if System.IS_WINDOWS: self.returnCode = System.wait_for_pid(self.pid) return True else: done = False while not done: #this is necessary because defunct processes in linux never count as exiting with this method #which means that this thread never ends, which means that we hang while shutting down if System.SHUTDOWN: return False try: #debug if type(self.pid) is not int: log_msg('self.pid is not int: %s' % (self.pid), 0) os.kill(self.pid, 0) except OSError: done = True time.sleep(0.5) return True
def get_app_by_pid(self, originalPID): """Return the application that controls originalPID""" app = None #if this process is unknown: if not self.applicationMapping.has_key(originalPID): ids = System.get_process_ids() appName = "Unknown" for id in ids: if id[1] == originalPID: appName = id[0] break #make sure there is an app for it: if appName not in self.applications: app = BitBlinderApplication(appName, ApplicationSettings.ApplicationSettings, "", self.torApp, self.bankApp) self.add_application(app) else: app = self.applications[appName] #and finally, add the process to the app: p = Process.Process(originalPID) app.add_process(p) app = self.applicationMapping[originalPID] return app
def on_new_stream(self, event): #will automatically register itself with it's application stream = Stream.Stream(event) #figure out who should handle the stream next: if stream.isInternal and Stream.OBSERVE_INTERNAL: stream.app = self.torApp stream.app.on_new_stream(stream) else: try: #first check if this was launched internally, directly through Tor: #TODO: this is a little weird, multiple failure conditions: if self.waiting_for_stream(stream): self.handle_stream_creation(stream) return port = int(event.source_addr.split(":")[1]) #need to figure out the original application that started this: assert port, "port must be defined to map a Stream to an Application" pid = System.get_pid_from_port(port) assert pid != 0, "pid must be non-zero in order to map from a Stream to Application" originalApp = self.get_app_by_pid(pid) originalApp.on_new_stream(stream, None) except Exception, e: log_ex(e, "No app for stream=%d?" % (stream.id))
def set_start_on_boot(self, newVal): """Change the registry key (if necessary) for auto launching BitBlinder at startup on windows, does nothing on *nix. Ends up calling a function made with NSIS that will get the necessary permissions to do the modification @param newVal: whether to start on boot or not @type newVal: bool""" if not System.IS_WINDOWS: return #No need to change if the value is already correct? if self.check_start_on_boot() == newVal: if self.startOnBootDeferred: log_msg( "Failed to modify 'start at bootup' value, already editing the registry!", 0) return if self.startOnBootDeferred: return def uac_done(result): self.startOnBootDeferred = None if result != True: log_ex( result, "Bad result while running BitBlinderSettingsUpdate.exe") #launch the program: if newVal: args = " --add-startup=" + ClientUtil.get_launch_command() else: args = " --remove-startup" encodedExe = System.encode_for_filesystem( os.path.join(Globals.WINDOWS_BIN, "BitBlinderSettingsUpdate.exe")) self.startOnBootDeferred = SerialProcessLauncher.get().run_app( encodedExe + " /S" + args) self.startOnBootDeferred.addCallback(uac_done) self.startOnBootDeferred.addErrback(uac_done)
def get_app_by_pid(self, originalPID): """Return the application that controls originalPID""" app = None #if this process is unknown: if not self.applicationMapping.has_key(originalPID): ids = System.get_process_ids() appName = "Unknown" for id in ids: if id[1] == originalPID: appName = id[0] break #make sure there is an app for it: if appName not in self.applications: app = BitBlinderApplication( appName, ApplicationSettings.ApplicationSettings, "", self.torApp, self.bankApp) self.add_application(app) else: app = self.applications[appName] #and finally, add the process to the app: p = Process.Process(originalPID) app.add_process(p) app = self.applicationMapping[originalPID] return app
def cleanup_previous_update(options): #This option is defined to indicate that we just ran the updater script. We set #the appropriate global, and just try to delete the update exe ignoreUpdater = False if os.path.exists(Globals.UPDATE_FILE_NAME): #kill any leftover updater processes try: startTime = time.time() while True: updaterProcs = System.get_process_ids_by_exe_path( re.compile( "^%s$" % (Globals.UPDATE_FILE_NAME.replace("\\", "\\\\")), re.IGNORECASE)) if len(updaterProcs) <= 0: break for pid in updaterProcs: log_msg("Waiting for updater (%s) to shut down..." % (pid), 1) System.kill_process(pid) if time.time() > startTime + 10.0: raise Exception( "Waited 15 seconds and updater still had not shut down" ) else: time.sleep(1.0) except Exception, error: log_ex(error, "Failed while waiting for updater to finish") message = "The BitBlinderUpdate.exe is still running. You must wait for it to finish or forcefully close it before you can run BitBlinder again. Maybe try running BitBlinder as Administrator just once?" die(message, "Error", EXIT_CODES.BITBLINDER_ALREADY_RUNNING) #if this is the first run after an update: if options.FINISHED_UPDATE: #ok, NOW try moving the updater file startTime = time.time() while True: try: if os.path.exists(Globals.UPDATE_FILE_NAME): shutil.move(Globals.UPDATE_FILE_NAME, Globals.UPDATE_FILE_NAME + ".prev") break except Exception, error: time.sleep(0.5) if time.time() > startTime + 5.0: log_ex( error, "Failed to remove update .exe from the previous update" ) ignoreUpdater = True #ok, lets try making a file, just so I can see why this is failing for people: if issubclass(type(error), WindowsError): try: testFile = open( Globals.UPDATE_FILE_NAME + ".test", "wb") testFile.write("hello?") testFile.close() except Exception, error: log_ex(error, "And we could NOT write a file") else: log_msg( "But we successfully wrote to a file (%s) Weird." % (Globals.UPDATE_FILE_NAME + ".test")) break
if Files.file_exists("THIS_IS_LIVE"): from common.conf import Live as Conf else: from common.conf import Dev as Conf def syscall(cmd): return os.system(cmd) ADDRESS = "98.236.61.1" NUM_CLIENTS = 3 BB_CMD = "python Main.py --allow-multiple --no-gui --dev-network" TEST_PASSWORD = "******" TEST_USERNAME = "******" #make sure there are no leftover Tor or BitBlinder processes: torIds = System.get_process_ids_by_name(Globals.TOR_RE) for pid in torIds: System.kill_process(pid) bbIds = System.get_process_ids_by_name(re.compile("^%s.*$" % (BB_CMD))) for pid in bbIds: System.kill_process(pid) processes = [] def kill_all(): for p in processes: System.kill_process(p.pid) def handler(signum, frame): kill_all() signal.signal(signal.SIGTERM, handler) #for each checkout:
def kill_all(): for p in processes: System.kill_process(p.pid)
def on_response(dialog, response_id): if response_id == gtk.RESPONSE_OK: filename = System.decode_from_filesystem(dialog.get_filename()) callback(filename) dialog.destroy()
def destroy_marker_file(): fileName = os.path.join(Globals.LOG_FOLDER, 'closedcleanly.txt') encodedFileName = System.encode_for_filesystem(fileName) os.remove(encodedFileName)
if not os.path.exists(to_directory): os.makedirs(to_directory) shutil.copyfile(from_, to_) if __name__ == '__main__': #check if the script is already running: authFileName = "AUTH.PID" processes = [] if os.path.exists(authFileName): pidFile = open(authFileName, "rb") data = pidFile.read() pidFile.close() data = data.split("\n") data.pop() for pid in data: System.kill_process(int(pid)) pidFile = open(authFileName, "wb") #first generate the DirServer entries: dirServers = TorUtils.make_auth_lines(Conf.AUTH_SERVERS) #now make each of the torrc files and delete any leftover data: authConfs = [] for i in range(1, len(Conf.AUTH_SERVERS)+1): data = dirServers + AUTH_TORRC_DATA conf = Conf.AUTH_SERVERS[i-1] found = False for arg in args: if arg == conf["address"]: found = True break if not found: continue
def send_args(args): #if we dont care about other processes, just return immediately: if Globals.ALLOW_MULTIPLE_INSTANCES: return False #Check if any other InnomiNet process is already running: #if there is no "closedcleanly.txt", then it definitely is not running if os.path.exists(os.path.join(Globals.LOG_FOLDER, 'closedcleanly.txt')): #If we succeed, the pass the arguments and exit. s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) try: s.connect((Globals.NOMNET_STARTUP_HOST, Globals.NOMNET_STARTUP_PORT)) data = "STARTUP " + "\n".join(args) structFormat = "!I" prefixLength = struct.calcsize(structFormat) s.sendall(struct.pack(structFormat, len(data)) + data) timeout = 5 try: recvd = "" msg = "" startTime = time.time() try: while True: r, w, exceptions = select.select([s], [], [s], 1) #If there are exceptions, connection was probably closed... if exceptions: raise SocketClosed #if there is actually something to read (didnt just timeout): if r: #4096 seemed like a good number... chunk = s.recv(4096, 0) if chunk == '': raise SocketClosed, "socket connection broken" recvd = recvd + chunk while len(recvd) >= prefixLength: length ,= struct.unpack(structFormat, recvd[:prefixLength]) if len(recvd) < length + prefixLength: break msg = recvd[prefixLength:length + prefixLength] msg = msg.split(" ")[0] recvd = recvd[length + prefixLength:] if msg: break #check if we've waited too long: elapsed = time.time() - startTime if elapsed > timeout: raise SocketTimeout("Exceeded user requested timeout") #handle socket errors except socket.error: exception, value, traceback = sys.exc_info() if value[0] == ERR_CONNECTION_RESET_BY_PEER: raise SocketClosed("recv: ERR_CONNECTION_RESET_BY_PEER") raise if msg == "SUCCESS": log_msg("Finished passing arguments to running instance.", 2) else: log_msg("Previous process died!", 1) except Exception, e: if e.__class__.__name__ == "SocketTimeout": log_msg("Failed to read response message!", 0) raise e else: log_ex(e, "Unhandled exception while waiting for response from running instance") return True #If we FAIL to connect, then the program must not already be running, so start up and listen for later connections: #NOTE: sys.exit throws an exception, but it derives from BaseException, which is why we only catch Exceptions here... except Exception, e: if e.__class__.__name__ == "SocketTimeout": #see if Tor is running: IDs = System.get_process_ids_by_name(Globals.TOR_RE) for ID in IDs: log_msg("Trying to kill tor process %s" % (ID), 2) System.kill_process(ID) #just make sure that socket is closed: try: s.shutdown() except: pass try: s.close() except: pass
def read_args(): #Create the options parser, this will be used throughout the program's execution Globals.PARSER = optparse.OptionParser() #Some options that are initially important: Globals.PARSER.add_option("--WAIT_FOR_PROCESS", type="int", dest="WAIT_FOR_PROCESS", help="Dont use this", metavar="FILE") Globals.PARSER.add_option("--FINISHED_UPDATE", action="store_true", dest="FINISHED_UPDATE", default=False) Globals.PARSER.add_option("--use-existing-tor", action="store_true", dest="USE_EXISTING_TOR", default=False) Globals.PARSER.add_option("-m", "--minimize", action="store_true", dest="minimize", default=False) Globals.PARSER.add_option("--curses", action="store_true", dest="useCurses", default=False) Globals.PARSER.add_option("--no-gui", action="store_true", dest="no_gui", default=False) Globals.PARSER.add_option("--allow-multiple", action="store_true", dest="allow_multiple", default=False) Globals.PARSER.add_option("--dev-network", action="store_true", dest="dev_network", default=False) Globals.PARSER.add_option("--debug", action="store_true", dest="debug", default=False) #BitTorrent: Globals.PARSER.add_option("-t", "--torrent", dest="torrent", help="Download a torrent file", metavar="FILE") #for telling us which program to launch: Globals.PARSER.add_option("--launch-bt", action="store_true", dest="launch_bt", default=False) Globals.PARSER.add_option("--launch-bb", action="store_true", dest="launch_bb", default=False) Globals.PARSER.add_option("--launch-ff", action="store_true", dest="launch_ff", default=False) #actually parse the options: (options, args) = Globals.PARSER.parse_args() #make sure that SOMETHING is supposed to start up: if not options.launch_bb and not options.launch_bt and not options.launch_ff: sys.argv.append('--launch-bb') options.launch_bb = True #NOTE: weirdness: the WAIT_FOR_PROCESS option is ONLY here for convenience. #It takes a process id as an argument. All it does is wait for the process #with that pid and then exit. This is called by the updater batch file, #because we need to wait for the previous InnomiNet instance to exit before #updating. Because we use py2exe, I didnt want to make a separate script for that if options.WAIT_FOR_PROCESS: try: pid = options.WAIT_FOR_PROCESS log_msg( "Waiting on previous program (%s) to finish shutting down..." % (pid), 2) System.wait_for_pid(pid) log_msg("Finished waiting", 2) except Exception, error: log_ex(error, "WAIT_FOR_PROCESS failed") finally: