[gnome-builder] rustup: take_*_fd takes ownership of fd, so use os.dup



commit de88bdead9b3287773a7b5f285d464c9a3c3f7bb
Author: Christian Hergert <chergert redhat com>
Date:   Fri Feb 24 12:49:35 2017 -0800

    rustup: take_*_fd takes ownership of fd, so use os.dup
    
    We need to dup the FD so that the callee can take ownership. Otherwise we
    can run into a state where the FD is closed before they can be applied to
    the stdout/stderr assignments.

 plugins/rustup/rustup_plugin/__init__.py |   15 +++++++++++----
 1 files changed, 11 insertions(+), 4 deletions(-)
---
diff --git a/plugins/rustup/rustup_plugin/__init__.py b/plugins/rustup/rustup_plugin/__init__.py
index 8ee81dd..eaa8182 100644
--- a/plugins/rustup/rustup_plugin/__init__.py
+++ b/plugins/rustup/rustup_plugin/__init__.py
@@ -279,6 +279,7 @@ class RustupInstaller(Ide.Transfer):
             self.props.title = _('Updating rustup')
         elif self.mode == _MODE_INSTALL_TOOLCHAIN:
             self.props.title = _('Installing rust ') + self.toolchain
+
         self.props.status = _('Checking system')
         self.props.icon_name = 'emblem-system-symbolic'
         self.state = _STATE_INIT
@@ -286,9 +287,11 @@ class RustupInstaller(Ide.Transfer):
         self.installed_components = 0
 
         task = Gio.Task.new(self, cancellable, callback)
+
         launcher = Ide.SubprocessLauncher()
         launcher.set_run_on_host(True)
         launcher.set_clear_env(False)
+
         if self.mode == _MODE_INSTALL:
             rustup_sh_path = get_module_data_path('resources/rustup.sh')
             # XXX: ensure that the script is executable
@@ -307,18 +310,22 @@ class RustupInstaller(Ide.Transfer):
             launcher.push_argv('toolchain')
             launcher.push_argv('install')
             launcher.push_argv(self.toolchain)
+
         # rustup needs a tty to give us a progress bar
         (master_fd, slave_fd) = pty.openpty()
-        launcher.take_stdin_fd (slave_fd)
-        launcher.take_stdout_fd (slave_fd)
-        launcher.take_stderr_fd (slave_fd)
+        launcher.take_stdin_fd(os.dup(slave_fd))
+        launcher.take_stdout_fd(os.dup(slave_fd))
+        launcher.take_stderr_fd(slave_fd)
 
         data_stream = Gio.DataInputStream.new(Gio.UnixInputStream.new(master_fd, False))
         # set it to ANY so the progress bars can be parsed
         data_stream.set_newline_type(Gio.DataStreamNewlineType.ANY)
         data_stream.read_line_async(GLib.PRIORITY_DEFAULT, cancellable, self._read_line_cb, cancellable)
 
-        sub_process = launcher.spawn()
+        try:
+            sub_process = launcher.spawn()
+        except Exception as ex:
+            task.return_error(GLib.Error(ex))
 
         sub_process.wait_async(cancellable, self._wait_cb, task)
 


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]