Sun, 18 Oct 2020 12:35:30 +0200
Merged with default branch.
# -*- coding: utf-8 -*- # Copyright (c) 2020 Detlev Offenbach <detlev@die-offenbachs.de> # """ Module implementing a function to patch multiprocessing.Process to support debugging of the process. """ import sys import traceback _debugClient = None _originalProcess = None _originalBootstrap = None def patchMultiprocessing(module, debugClient): """ Function to patch the multiprocessing module. @param module reference to the imported module to be patched @type module @param debugClient reference to the debug client object @type DebugClient """ # __IGNORE_WARNING_D234__ global _debugClient, _originalProcess, _originalBootstrap _debugClient = debugClient if sys.version_info >= (3, 4): _originalProcess = module.process.BaseProcess else: _originalProcess = module.Process _originalBootstrap = _originalProcess._bootstrap class ProcessWrapper(_originalProcess): """ Wrapper class for multiprocessing.Process. """ def _bootstrap(self, *args, **kwargs): """ Wrapper around _bootstrap to start debugger. @param args function arguments @type list @param kwargs keyword only arguments @type dict @return exit code of the process @rtype int """ if ( _debugClient.debugging and _debugClient.multiprocessSupport ): try: (wd, host, port, exceptions, tracePython, redirect, noencoding) = _debugClient.startOptions[:7] _debugClient.startDebugger( sys.argv[0], host=host, port=port, exceptions=exceptions, tracePython=tracePython, redirect=redirect, passive=False, multiprocessSupport=True ) except Exception: print("Exception during multiprocessing bootstrap init:") # __IGNORE_WARNING_M801__ traceback.print_exc(file=sys.stdout) sys.stdout.flush() raise return _originalBootstrap(self, *args, **kwargs) if sys.version_info >= (3, 4): _originalProcess._bootstrap = ProcessWrapper._bootstrap else: module.Process = ProcessWrapper ## if sys.version_info >= (3, 4): ## _originalProcess = module.Process #### _originalProcess = module.process.BaseProcess ## else: ## _originalProcess = module.Process ## class ProcessWrapper(_originalProcess): ## def __init__(self, *args, **kwargs): ## super(ProcessWrapper, self).__init__(*args, **kwargs) ## self._run = self.run ## self.run = self._bootstrap_eric6 ## # Class attributes are not transfered to new process. Therefore make a ## # copy as instance attribute ## self._options = _debugClient.startOptions ## ## def _bootstrap_eric6(self): ## """ ## Bootstrap for threading, which reports exceptions correctly. ## ## @param run the run method of threading.Thread ## @type method pointer ## """ ## from DebugClient import DebugClient ## self.debugClient = DebugClient() ## ## (_wd, host, port, exceptions, tracePython, redirect, ## noencoding) = self._options[:7] ## ## args = sys.argv ## self.debugClient.name = self.name ## ## self.debugClient.startDebugger(args[0], host, port, ## exceptions=exceptions, ## tracePython=tracePython, ## redirect=redirect) ## ## try: ## self._run() ## except Exception: ## excinfo = sys.exc_info() ## self.debugClient.user_exception(excinfo, True) ## finally: ## sys.settrace(None) ## ## if sys.version_info >= (3, 4): ## module.Process = ProcessWrapper #### module.process.BaseProcess = ProcessWrapper ## else: ## module.Process = ProcessWrapper