Launch and write to terminal in Qt

时间秒杀一切 提交于 2019-12-08 07:58:23

问题


I am coding in linux using Qt. I understand that with popen or QProcess I can launch terminal from my program, but how do I write into to it? I google around people are suggesting fork() and pipe(). My purpose is to do an ICMP ping with the terminal, and stop when ping successfully. I made it with popen, but I couldn't stop the ping process thus my program won't run.


回答1:


You don't write anything to terminal because there's no terminal. You pass name of a program to run and its arguments as arguments of the QProcess::start method. If you only need to know if ping was successful or not it's enough to check the exit code of the process which you started earlier using QProcess::start; you don't have to read its output.

from ping(8) - Linux man page

If ping does not receive any reply packets at all it will exit with code 1. If a packet count and deadline are both specified, and fewer than count packets are received by the time the deadline has arrived, it will also exit with code 1. On other error it exits with code 2. Otherwise it exits with code 0. This makes it possible to use the exit code to see if a host is alive or not.

By default ping under Linux runs until you stop it. You can however use -c X option to send only X packets and -w X option to set timeout of the whole process to X seconds. This way you can limit the time ping will take to run.
Below is a working example of using QProcess to run ping program on Windows. For Linux you have to change ping options accordingly (for example -n to -c). In the example, ping is run up to X times, where X is the option you give to Ping class constructor. As soon as any of these executions returns with exit code 0 (meaning success) the result signal is emitted with value true. If no execution is successful the result signal is emitted with value false.

#include <QCoreApplication>
#include <QObject>
#include <QProcess>
#include <QTimer>
#include <QDebug>


class Ping : public QObject {

    Q_OBJECT

public:

    Ping(int count)
    : QObject(), count_(count) {

        arguments_ << "-n" << "1" << "example.com";

        QObject::connect(&process_,
                         SIGNAL(finished(int, QProcess::ExitStatus)),
                         this,
                         SLOT(handlePingOutput(int, QProcess::ExitStatus)));
    };

public slots:

    void handlePingOutput(int exitCode, QProcess::ExitStatus exitStatus) {
        qDebug() << exitCode;
        qDebug() << exitStatus;
        qDebug() << static_cast<QIODevice*>(QObject::sender())->readAll();
        if (!exitCode) {
            emit result(true);
        } else {
            if (--count_) {
                QTimer::singleShot(1000, this, SLOT(ping()));
            } else {
                emit result(false);
            }
        }
    }

    void ping() {
        process_.start("ping", arguments_);
    }

signals:

    void result(bool res);

private:

    QProcess process_;
    QStringList arguments_;
    int count_;
};


class Test : public QObject {

    Q_OBJECT

public:
    Test() : QObject() {};

public slots:
    void handle(bool result) {
        if (result)
            qDebug() << "Ping suceeded";
        else
            qDebug() << "Ping failed";
    }
};


int main(int argc, char *argv[])
{
    QCoreApplication app(argc, argv);

    Test test;
    Ping ping(3);
    QObject::connect(&ping,
                     SIGNAL(result(bool)),
                     &test,
                     SLOT(handle(bool)));

    ping.ping();
    app.exec();
}

#include "main.moc"


来源:https://stackoverflow.com/questions/4629185/launch-and-write-to-terminal-in-qt

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!