diff options
Diffstat (limited to 'src/corelib/io/qprocess_unix.cpp')
-rw-r--r-- | src/corelib/io/qprocess_unix.cpp | 81 |
1 files changed, 70 insertions, 11 deletions
diff --git a/src/corelib/io/qprocess_unix.cpp b/src/corelib/io/qprocess_unix.cpp index e9957d2384..9868ea624a 100644 --- a/src/corelib/io/qprocess_unix.cpp +++ b/src/corelib/io/qprocess_unix.cpp @@ -807,19 +807,29 @@ pid_t QProcessPrivate::spawnChild(const char *workingDir, char **argv, char **en ? i : SPAWN_FDCLOSED; } + if (inputChannelMode == QProcess::ManagedInputChannel) + fd_map[0] = stdinChannel.pipe[0]; + else + fd_map[0] = QT_FILENO(stdin); + switch (processChannelMode) { case QProcess::ForwardedChannels: - fd_map[0] = stdinChannel.pipe[0]; fd_map[1] = QT_FILENO(stdout); fd_map[2] = QT_FILENO(stderr); break; + case QProcess::ForwardedOutputChannel: + fd_map[1] = QT_FILENO(stdout); + fd_map[2] = stderrChannel.pipe[1]; + break; + case QProcess::ForwardedErrorChannel: + fd_map[1] = stdoutChannel.pipe[1]; + fd_map[2] = QT_FILENO(stderr); + break; case QProcess::MergedChannels: - fd_map[0] = stdinChannel.pipe[0]; fd_map[1] = stdoutChannel.pipe[1]; fd_map[2] = stdoutChannel.pipe[1]; break; case QProcess::SeparateChannels: - fd_map[0] = stdinChannel.pipe[0]; fd_map[1] = stdoutChannel.pipe[1]; fd_map[2] = stderrChannel.pipe[1]; break; @@ -845,17 +855,19 @@ void QProcessPrivate::execChild(const char *workingDir, char **path, char **argv Q_Q(QProcess); - // copy the stdin socket (without closing on exec) - qt_safe_dup2(stdinChannel.pipe[0], fileno(stdin), 0); + // copy the stdin socket if asked to (without closing on exec) + if (inputChannelMode != QProcess::ForwardedInputChannel) + qt_safe_dup2(stdinChannel.pipe[0], fileno(stdin), 0); // copy the stdout and stderr if asked to if (processChannelMode != QProcess::ForwardedChannels) { - qt_safe_dup2(stdoutChannel.pipe[1], fileno(stdout), 0); + if (processChannelMode != QProcess::ForwardedOutputChannel) + qt_safe_dup2(stdoutChannel.pipe[1], fileno(stdout), 0); // merge stdout and stderr if asked to if (processChannelMode == QProcess::MergedChannels) { qt_safe_dup2(fileno(stdout), fileno(stderr), 0); - } else { + } else if (processChannelMode != QProcess::ForwardedErrorChannel) { qt_safe_dup2(stderrChannel.pipe[1], fileno(stderr), 0); } } @@ -1031,6 +1043,41 @@ static int qt_timeout_value(int msecs, int elapsed) return timeout < 0 ? 0 : timeout; } +#ifdef Q_OS_BLACKBERRY +// The BlackBerry event dispatcher uses bps_get_event. Unfortunately, already registered +// socket notifiers are disabled by a call to select. This is to rearm the standard streams. +static int bb_select(QProcessPrivate *process, int nfds, fd_set *fdread, fd_set *fdwrite, int timeout) +{ + bool stdoutEnabled = false; + bool stderrEnabled = false; + bool stdinEnabled = false; + + if (process->stdoutChannel.notifier && process->stdoutChannel.notifier->isEnabled()) { + stdoutEnabled = true; + process->stdoutChannel.notifier->setEnabled(false); + } + if (process->stderrChannel.notifier && process->stderrChannel.notifier->isEnabled()) { + stderrEnabled = true; + process->stderrChannel.notifier->setEnabled(false); + } + if (process->stdinChannel.notifier && process->stdinChannel.notifier->isEnabled()) { + stdinEnabled = true; + process->stdinChannel.notifier->setEnabled(false); + } + + const int ret = select_msecs(nfds, fdread, fdwrite, timeout); + + if (stdoutEnabled) + process->stdoutChannel.notifier->setEnabled(true); + if (stderrEnabled) + process->stderrChannel.notifier->setEnabled(true); + if (stdinEnabled) + process->stdinChannel.notifier->setEnabled(true); + + return ret; +} +#endif // Q_OS_BLACKBERRY + bool QProcessPrivate::waitForStarted(int msecs) { Q_Q(QProcess); @@ -1091,7 +1138,11 @@ bool QProcessPrivate::waitForReadyRead(int msecs) add_fd(nfds, stdinChannel.pipe[1], &fdwrite); int timeout = qt_timeout_value(msecs, stopWatch.elapsed()); +#ifdef Q_OS_BLACKBERRY + int ret = bb_select(this, nfds + 1, &fdread, &fdwrite, timeout); +#else int ret = select_msecs(nfds + 1, &fdread, &fdwrite, timeout); +#endif if (ret < 0) { break; } @@ -1163,8 +1214,12 @@ bool QProcessPrivate::waitForBytesWritten(int msecs) if (!writeBuffer.isEmpty() && stdinChannel.pipe[1] != -1) add_fd(nfds, stdinChannel.pipe[1], &fdwrite); - int timeout = qt_timeout_value(msecs, stopWatch.elapsed()); - int ret = select_msecs(nfds + 1, &fdread, &fdwrite, timeout); + int timeout = qt_timeout_value(msecs, stopWatch.elapsed()); +#ifdef Q_OS_BLACKBERRY + int ret = bb_select(this, nfds + 1, &fdread, &fdwrite, timeout); +#else + int ret = select_msecs(nfds + 1, &fdread, &fdwrite, timeout); +#endif if (ret < 0) { break; } @@ -1230,8 +1285,12 @@ bool QProcessPrivate::waitForFinished(int msecs) if (!writeBuffer.isEmpty() && stdinChannel.pipe[1] != -1) add_fd(nfds, stdinChannel.pipe[1], &fdwrite); - int timeout = qt_timeout_value(msecs, stopWatch.elapsed()); - int ret = select_msecs(nfds + 1, &fdread, &fdwrite, timeout); + int timeout = qt_timeout_value(msecs, stopWatch.elapsed()); +#ifdef Q_OS_BLACKBERRY + int ret = bb_select(this, nfds + 1, &fdread, &fdwrite, timeout); +#else + int ret = select_msecs(nfds + 1, &fdread, &fdwrite, timeout); +#endif if (ret < 0) { break; } |