def __init__(self, process_obj):
     prep_data = spawn.get_preparation_data(process_obj._name)
     rhandle, whandle = _winapi.CreatePipe(None, 0)
     wfd = msvcrt.open_osfhandle(whandle, 0)
     cmd = spawn.get_command_line(parent_pid=os.getpid(), pipe_handle=
         rhandle)
     cmd = ' '.join('"%s"' % x for x in cmd)
     with open(wfd, 'wb', closefd=True) as to_child:
         try:
             hp, ht, pid, tid = _winapi.CreateProcess(spawn.
                 get_executable(), cmd, None, None, False, 0, None, None,
                 None)
             _winapi.CloseHandle(ht)
         except:
             _winapi.CloseHandle(rhandle)
             raise
         self.pid = pid
         self.returncode = None
         self._handle = hp
         self.sentinel = int(hp)
         util.Finalize(self, _winapi.CloseHandle, (self.sentinel,))
         set_spawning_popen(self)
         try:
             reduction.dump(prep_data, to_child)
             reduction.dump(process_obj, to_child)
         finally:
             set_spawning_popen(None)
Ejemplo n.º 2
0
        def __init__(self, process_obj):
            cmd = ' '.join('"%s"' % x for x in get_command_line())
            prep_data = get_preparation_data(process_obj._name)

            # create pipe for communication with child
            rfd, wfd = os.pipe()

            # get handle for read end of the pipe and make it inheritable
            rhandle = duplicate(msvcrt.get_osfhandle(rfd), inheritable=True)
            os.close(rfd)

            with open(wfd, 'wb', closefd=True) as to_child:
                # start process
                try:
                    hp, ht, pid, tid = _winapi.CreateProcess(
                        _python_exe, cmd + (' %s' % rhandle), None, None, 1, 0,
                        None, None, None)
                    _winapi.CloseHandle(ht)
                finally:
                    close(rhandle)

                # set attributes of self
                self.pid = pid
                self.returncode = None
                self._handle = hp
                self.sentinel = int(hp)

                # send information to child
                Popen._tls.process_handle = int(hp)
                try:
                    dump(prep_data, to_child, HIGHEST_PROTOCOL)
                    dump(process_obj, to_child, HIGHEST_PROTOCOL)
                finally:
                    del Popen._tls.process_handle
Ejemplo n.º 3
0
 def _execute_child(self, args, executable, preexec_fn, close_fds, pass_fds, cwd, env, startupinfo, creationflags, shell, p2cread, p2cwrite, c2pread, c2pwrite, errread, errwrite, unused_restore_signals, unused_start_new_session):
     if not isinstance(args, str):
         args = list2cmdline(args)
     if startupinfo is None:
         startupinfo = STARTUPINFO()
     if -1 not in (p2cread, c2pwrite, errwrite):
         startupinfo.hStdInput = p2cread
         startupinfo.hStdOutput = c2pwrite
         startupinfo.hStdError = errwrite
     if shell:
         startupinfo.wShowWindow = _winapi.SW_HIDE
         comspec = os.environ.get('COMSPEC', 'cmd.exe')
         args = '{} /c "{}"'.format(comspec, args)
         if _winapi.GetVersion() >= 2147483648 or os.path.basename(comspec).lower() == 'command.com':
             w9xpopen = self._find_w9xpopen()
             args = '"%s" %s' % (w9xpopen, args)
             creationflags |= _winapi.CREATE_NEW_CONSOLE
     try:
         (hp, ht, pid, tid) = _winapi.CreateProcess(executable, args, None, None, int(not close_fds), creationflags, env, cwd, startupinfo)
     except pywintypes.error as e:
         raise WindowsError(*e.args)
     finally:
         if p2cread != -1:
             p2cread.Close()
         if c2pwrite != -1:
             c2pwrite.Close()
         if errwrite != -1:
             errwrite.Close()
         if hasattr(self, '_devnull'):
             os.close(self._devnull)
     self._child_created = True
     self._handle = Handle(hp)
     self.pid = pid
     _winapi.CloseHandle(ht)
Ejemplo n.º 4
0
    def __init__(self, process_obj):
        prep_data = spawn.get_preparation_data(process_obj._name)

        # read end of pipe will be duplicated by the child process
        # -- see spawn_main() in spawn.py.
        #
        # bpo-33929: Previously, the read end of pipe was "stolen" by the child
        # process, but it leaked a handle if the child process had been
        # terminated before it could steal the handle from the parent process.
        rhandle, whandle = _winapi.CreatePipe(None, 0)
        wfd = msvcrt.open_osfhandle(whandle, 0)
        cmd = spawn.get_command_line(parent_pid=os.getpid(),
                                     pipe_handle=rhandle)
        cmd = ' '.join('"%s"' % x for x in cmd)

        python_exe = spawn.get_executable()

        # bpo-35797: When running in a venv, we bypass the redirect
        # executor and launch our base Python.
        if WINENV and _path_eq(python_exe, sys.executable):
            python_exe = sys._base_executable
            env = os.environ.copy()
            env["__PYVENV_LAUNCHER__"] = sys.executable
        else:
            env = os.environ.copy()
        env['Y_PYTHON_ENTRY_POINT'] = ':main'

        with open(wfd, 'wb', closefd=True) as to_child:
            # start process
            try:
                hp, ht, pid, tid = _winapi.CreateProcess(
                    python_exe, cmd,
                    None, None, False, 0, env, None, None)
                _winapi.CloseHandle(ht)
            except:
                _winapi.CloseHandle(rhandle)
                raise

            # set attributes of self
            self.pid = pid
            self.returncode = None
            self._handle = hp
            self.sentinel = int(hp)
            self.finalizer = util.Finalize(self, _close_handles,
                                           (self.sentinel, int(rhandle)))

            # send information to child
            set_spawning_popen(self)
            try:
                reduction.dump(prep_data, to_child)
                reduction.dump(process_obj, to_child)
            finally:
                set_spawning_popen(None)
Ejemplo n.º 5
0
    def __init__(self, process_obj):
        prep_data = spawn.get_preparation_data(process_obj._name)

        # read end of pipe will be duplicated by the child process
        # -- see spawn_main() in spawn.py.
        #
        # bpo-33929: Previously, the read end of pipe was "stolen" by the child
        # process, but it leaked a handle if the child process had been
        # terminated before it could steal the handle from the parent process.
        rhandle, whandle = _winapi.CreatePipe(None, 0)
        wfd = msvcrt.open_osfhandle(whandle, 0)
        cmd = spawn.get_command_line(parent_pid=os.getpid(),
                                     pipe_handle=rhandle)
        cmd = ' '.join('"%s"' % x for x in cmd)

        with open(wfd, 'wb', closefd=True) as to_child:
            # start process
            try:
                hp, ht, pid, tid = _winapi.CreateProcess(
                    spawn.get_executable(), cmd,
                    None, None, False, 0, None, None, None)
                _winapi.CloseHandle(ht)
            except:
                _winapi.CloseHandle(rhandle)
                raise

            # set attributes of self
            self.pid = pid
            self.returncode = None
            self._handle = hp
            self.sentinel = int(hp)
            self.finalizer = util.Finalize(self, _close_handles,
                                           (self.sentinel, int(rhandle)))

            # send information to child
            set_spawning_popen(self)
            try:
                reduction.dump(prep_data, to_child)
                reduction.dump(process_obj, to_child)
            finally:
                set_spawning_popen(None)
Ejemplo n.º 6
0
def spawnv_passfds(path, args, passfds):
    passfds = sorted(passfds)
    if sys.platform != "win32":
        errpipe_read, errpipe_write = os.pipe()
        try:
            from .reduction import _mk_inheritable
            from .fork_exec import fork_exec
            _pass = [_mk_inheritable(fd) for fd in passfds]
            return fork_exec(args, _pass)
        finally:
            os.close(errpipe_read)
            os.close(errpipe_write)
    else:
        cmd = ' '.join(f'"{x}"' for x in args)
        try:
            hp, ht, pid, tid = _winapi.CreateProcess(
                path, cmd, None, None, True, 0, None, None, None)
            _winapi.CloseHandle(ht)
        except BaseException:
            pass
        return pid
Ejemplo n.º 7
0
    def __init__(self, process_obj):
        prep_data = spawn.get_preparation_data(process_obj._name)

        # read end of pipe will be "stolen" by the child process
        # -- see spawn_main() in spawn.py.
        rhandle, whandle = _winapi.CreatePipe(None, 0)
        wfd = msvcrt.open_osfhandle(whandle, 0)
        cmd = spawn.get_command_line(parent_pid=os.getpid(),
                                     pipe_handle=rhandle)
        cmd = ' '.join('"%s"' % x for x in cmd)

        with open(wfd, 'wb', closefd=True) as to_child:
            # start process
            try:
                hp, ht, pid, tid = _winapi.CreateProcess(
                    spawn.get_executable(), cmd, None, None, False, 0, None,
                    None, None)
                _winapi.CloseHandle(ht)
            except:
                _winapi.CloseHandle(rhandle)
                raise

            # set attributes of self
            self.pid = pid
            self.returncode = None
            self._handle = hp
            self.sentinel = int(hp)
            util.Finalize(self, _winapi.CloseHandle, (self.sentinel, ))

            # send information to child
            popen.set_spawning_popen(self)
            try:
                reduction.dump(prep_data, to_child)
                reduction.dump(process_obj, to_child)
            finally:
                popen.set_spawning_popen(None)
Ejemplo n.º 8
0
    def __init__(self, process_obj):
        prep_data = spawn.get_preparation_data(
            process_obj._name, getattr(process_obj, "init_main_module", True))

        # read end of pipe will be "stolen" by the child process
        # -- see spawn_main() in spawn.py.
        rfd, wfd = os.pipe()
        rhandle = duplicate(msvcrt.get_osfhandle(rfd), inheritable=True)
        os.close(rfd)

        cmd = get_command_line(parent_pid=os.getpid(), pipe_handle=rhandle)
        cmd = ' '.join(f'"{x}"' for x in cmd)

        python_exe = spawn.get_executable()

        # copy the environment variables to set in the child process
        child_env = os.environ.copy()
        child_env.update(process_obj.env)

        # bpo-35797: When running in a venv, we bypass the redirect
        # executor and launch our base Python.
        if WINENV and _path_eq(python_exe, sys.executable):
            python_exe = sys._base_executable
            child_env["__PYVENV_LAUNCHER__"] = sys.executable

        try:
            with open(wfd, 'wb') as to_child:
                # start process
                try:
                    # This flag allows to pass inheritable handles from the
                    # parent to the child process in a python2-3 compatible way
                    # (see
                    # https://github.com/tomMoral/loky/pull/204#discussion_r290719629
                    # for more detail). When support for Python 2 is dropped,
                    # the cleaner multiprocessing.reduction.steal_handle should
                    # be used instead.
                    inherit = True
                    hp, ht, pid, tid = _winapi.CreateProcess(
                        python_exe, cmd, None, None, inherit, 0, child_env,
                        None, None)
                    _winapi.CloseHandle(ht)
                except BaseException:
                    _winapi.CloseHandle(rhandle)
                    raise

                # set attributes of self
                self.pid = pid
                self.returncode = None
                self._handle = hp
                self.sentinel = int(hp)
                util.Finalize(self, _winapi.CloseHandle, (self.sentinel, ))

                # send information to child
                set_spawning_popen(self)
                try:
                    reduction.dump(prep_data, to_child)
                    reduction.dump(process_obj, to_child)
                finally:
                    set_spawning_popen(None)
        except IOError as exc:
            # IOError 22 happens when the launched subprocess terminated before
            # wfd.close is called. Thus we can safely ignore it.
            if exc.errno != 22:
                raise
            util.debug(
                f"While starting {process_obj._name}, ignored a IOError 22")
Ejemplo n.º 9
0
        def _execute_child_compat(self, args, executable, preexec_fn, close_fds,
                           cwd, env, universal_newlines, startupinfo,
                           creationflags, shell,
                           p2cread, p2cwrite,
                           c2pread, c2pwrite,
                           errread, errwrite):
            if not isinstance(args, str):
                args = subprocess.list2cmdline(args)

            # Always or in the create new process group
            creationflags |= winprocess.CREATE_NEW_PROCESS_GROUP

            if startupinfo is None:
                startupinfo = winprocess.STARTUPINFO()

            if None not in (p2cread, c2pwrite, errwrite):
                startupinfo.dwFlags |= winprocess.STARTF_USESTDHANDLES

                startupinfo.hStdInput = int(p2cread)
                startupinfo.hStdOutput = int(c2pwrite)
                startupinfo.hStdError = int(errwrite)
            if shell:
                startupinfo.dwFlags |= winprocess.STARTF_USESHOWWINDOW
                startupinfo.wShowWindow = winprocess.SW_HIDE
                comspec = os.environ.get("COMSPEC", "cmd.exe")
                args = comspec + " /c " + args

            # determine if we can create create a job
            canCreateJob = winprocess.CanCreateJobObject()

            # set process creation flags
            creationflags |= winprocess.CREATE_SUSPENDED
            creationflags |= winprocess.CREATE_UNICODE_ENVIRONMENT
            if canCreateJob:
                creationflags |= winprocess.CREATE_BREAKAWAY_FROM_JOB

            # create the process
            hp, ht, pid, tid = _winapi.CreateProcess(
                executable, args,
                None, None, # No special security
                1, # Must inherit handles!
                creationflags,
                env,
                cwd, startupinfo)
            self._child_created = True
            self._handle = int(hp)
            self._thread = ht
            self.pid = pid
            self.tid = tid

            if canCreateJob:
                # We create a new job for this process, so that we can kill
                # the process and any sub-processes
                self._job = winprocess.CreateJobObject()
                winprocess.AssignProcessToJobObject(self._job, int(hp))
            else:
                self._job = None

            winprocess.ResumeThread(int(ht))
            _winapi.CloseHandle(ht)

            if p2cread is not None and p2cread != -1:
                p2cread.Close()
            if c2pwrite is not None and c2pwrite != -1:
                c2pwrite.Close()
            if errwrite is not None and errwrite != -1:
                errwrite.Close()
            time.sleep(.1)