code: def run_user_process(self, program, args, env):
          
          stdout_streams, stderr_streams = self._get_stdout_stderr_streams()
  
          if sys.platform == "win32":
              # PTYs don't work in windows so we use pipes.
              self._stdout_tee = io_wrap.Tee.pipe(*stdout_streams)
              self._stderr_tee = io_wrap.Tee.pipe(*stderr_streams)
              # Seems like the following actually isn't necessary on Windows
              # TODO(adrian): we may need to do the following if we use pipes instead of PTYs
              # because Python on Unix doesn't like writing UTF-8 to files
              # tell child python interpreters we accept utf-8
              # env['PYTHONIOENCODING'] = 'UTF-8'
          else:
              self._stdout_tee = io_wrap.Tee.pty(*stdout_streams)
              self._stderr_tee = io_wrap.Tee.pty(*stderr_streams)
  
          command = [program] + list(args)
          runner = util.find_runner(program)
          if runner:
              command = runner + command
          command = ' '.join(six.moves.shlex_quote(arg) for arg in command)
          self._stdout_stream.write_string(command + "\n\n")
  
          try:
              self.proc = subprocess.Popen(
                  command,
                  env=env,
                  stdout=self._stdout_tee.tee_file,
                  stderr=self._stderr_tee.tee_file,
                  shell=True,
              )
              self._run.pid = self.proc.pid
          except (OSError, IOError):
              raise Exception('Could not find program: %s' % command)
  
          self._sync_etc()
docs: Launch a user process, capture its output, and sync its files to the backend.
  
          This returns after the process has ended and syncing is done.
          Captures ctrl-c's, signals, etc.