diff --git a/src/fs/luks.cpp b/src/fs/luks.cpp index 74b9dc1..3ffae65 100644 --- a/src/fs/luks.cpp +++ b/src/fs/luks.cpp @@ -113,31 +113,24 @@ bool luks::create(Report& report, const QString& deviceNode) const Q_ASSERT(m_innerFs); Q_ASSERT(!m_passphrase.isEmpty()); - std::vector commands; - commands.push_back(QStringLiteral("echo")); - commands.push_back(QStringLiteral("cryptsetup")); - std::vector args; - args.push_back({ m_passphrase }); - args.push_back({ QStringLiteral("-s"), - QStringLiteral("512"), - QStringLiteral("luksFormat"), - deviceNode }); - - ExternalCommand createCmd(commands, args); - if (!(createCmd.run(-1) && createCmd.exitCode() == 0)) + ExternalCommand createCmd(report, QStringLiteral("cryptsetup"), + { QStringLiteral("-s"), + QStringLiteral("512"), + QStringLiteral("luksFormat"), + deviceNode }); + if (!( createCmd.start(-1) && + createCmd.write(m_passphrase.toLatin1() + '\n' + m_passphrase.toLatin1() + '\n') == 2*(m_passphrase.toLatin1().length() + 1) && + createCmd.waitFor() && createCmd.exitCode() == 0)) + { return false; + } - commands.clear(); - commands.push_back(QStringLiteral("echo")); - commands.push_back(QStringLiteral("cryptsetup")); - args.clear(); - args.push_back({ m_passphrase }); - args.push_back({ QStringLiteral("open"), - deviceNode, - suggestedMapperName(deviceNode) }); + ExternalCommand openCmd(report, QStringLiteral("cryptsetup"), + { QStringLiteral("open"), + deviceNode, + suggestedMapperName(deviceNode) }); - ExternalCommand openCmd(commands, args); - if (!(openCmd.run(-1) && openCmd.exitCode() == 0)) + if (!( openCmd.start(-1) && openCmd.write(m_passphrase.toLatin1() + '\n') == m_passphrase.toLatin1().length() + 1 && openCmd.waitFor())) return false; QString mapperNode = mapperName(deviceNode); @@ -257,18 +250,17 @@ bool luks::cryptOpen(QWidget* parent, const QString& deviceNode) return false; QString passphrase = dlg.password(); - std::vector commands; - commands.push_back(QStringLiteral("echo")); - commands.push_back(QStringLiteral("cryptsetup")); - std::vector args; - args.push_back({ passphrase }); - args.push_back({ QStringLiteral("open"), - deviceNode, - suggestedMapperName(deviceNode) }); + ExternalCommand openCmd(QStringLiteral("cryptsetup"), + { QStringLiteral("open"), + deviceNode, + suggestedMapperName(deviceNode) }); - ExternalCommand cmd(commands, args); - if (!(cmd.run(-1) && cmd.exitCode() == 0)) + if (!( openCmd.start(-1) && + openCmd.write(passphrase.toLatin1() + '\n') == passphrase.toLatin1().length() + 1 && + openCmd.waitFor() && openCmd.exitCode() == 0) ) + { return false; + } if (m_innerFs) { diff --git a/src/util/externalcommand.cpp b/src/util/externalcommand.cpp index c1006b0..a9bb3a7 100644 --- a/src/util/externalcommand.cpp +++ b/src/util/externalcommand.cpp @@ -32,12 +32,13 @@ @param args the arguments to pass to the command */ ExternalCommand::ExternalCommand(const QString& cmd, const QStringList& args) : + QProcess(), m_Report(nullptr), + m_Command(cmd), + m_Args(args), m_ExitCode(-1), m_Output() { - m_Command.push_back(cmd); - m_Args.push_back(args); setup(); } @@ -47,35 +48,7 @@ ExternalCommand::ExternalCommand(const QString& cmd, const QStringList& args) : @param args the arguments to pass to the command */ ExternalCommand::ExternalCommand(Report& report, const QString& cmd, const QStringList& args) : - m_Report(report.newChild()), - m_ExitCode(-1), - m_Output() -{ - m_Command.push_back(cmd); - m_Args.push_back(args); - setup(); -} - -/** Creates a new ExternalCommand instance without Report. - @param cmd the vector of the piped commands to run - @param args the vector of the arguments to pass to the commands -*/ -ExternalCommand::ExternalCommand(const std::vector cmd, const std::vector args) : - m_Report(nullptr), - m_Command(cmd), - m_Args(args), - m_ExitCode(-1), - m_Output() -{ - setup(); -} - -/** Creates a new ExternalCommand instance with Report. - @param report the Report to write output to. - @param cmd the vector of the piped commands to run - @param args the vector of the arguments to pass to the commands - */ -ExternalCommand::ExternalCommand(Report& report, const std::vector cmd, const std::vector args) : + QProcess(), m_Report(report.newChild()), m_Command(cmd), m_Args(args), @@ -85,72 +58,52 @@ ExternalCommand::ExternalCommand(Report& report, const std::vector cmd, setup(); } -ExternalCommand::~ExternalCommand() -{ - delete[] processes; -} - void ExternalCommand::setup() { setEnvironment(QStringList() << QStringLiteral("LC_ALL=C") << QStringLiteral("PATH=") + QString::fromUtf8(getenv("PATH"))); setProcessChannelMode(MergedChannels); - processes = new QProcess[command().size()]; - connect(&processes[command().size() - 1], SIGNAL(readyReadStandardOutput()), SLOT(onReadOutput())); - connect(&processes[command().size() - 1], SIGNAL(finished(int, QProcess::ExitStatus)), SLOT(onFinished(int))); - - for (unsigned int i = 0; i < command().size() - 1; i++) { - processes[i].setStandardOutputProcess(&processes[i + 1]); - } + connect(this, SIGNAL(finished(int, QProcess::ExitStatus)), SLOT(onFinished(int))); + connect(this, SIGNAL(readyReadStandardOutput()), SLOT(onReadOutput())); } -/** Starts the external commands. +/** Starts the external command. @param timeout timeout to wait for the process to start @return true on success */ bool ExternalCommand::start(int timeout) { - for (unsigned int i = 0; i < command().size(); i++) - processes[i].start(command()[i], args()[i]); + QProcess::start(command(), args()); if (report()) { - QString s; - for (unsigned int i = 0; i < command().size(); i++) { - s += command()[i] + QStringLiteral(" ") + args()[i].join(QStringLiteral(" ")); - if (i < command().size() - 1) - s += QStringLiteral(" | "); - } - report()->setCommand(i18nc("@info/plain", "Command: %1", s)); + report()->setCommand(i18nc("@info/plain", "Command: %1 %2", command(), args().join(QStringLiteral(" ")))); } - for (unsigned int i = 0; i < command().size(); i++) { - if (!processes[i].waitForStarted(timeout)) { - if (report()) - report()->line() << i18nc("@info/plain", "(Command timeout while starting \"%1\")", command()[i] + QStringLiteral(" ") + args()[i].join(QStringLiteral(" "))); - - return false; - } + if (!waitForStarted(timeout)) + { + if (report()) + report()->line() << i18nc("@info/plain", "(Command timeout while starting)"); + return false; } return true; } -/** Waits for the external commands to finish. +/** Waits for the external command to finish. @param timeout timeout to wait until the process finishes. @return true on success */ bool ExternalCommand::waitFor(int timeout) { - for (unsigned int i = 0; i < command().size(); i++) { - processes[i].closeWriteChannel(); + closeWriteChannel(); - if (!processes[i].waitForFinished(timeout)) { - if (report()) - report()->line() << i18nc("@info/plain", "(Command timeout while running \"%1\")", command()[i] + QStringLiteral(" ") + args()[i].join(QStringLiteral(" "))); - return false; - } - onReadOutput(); + if (!waitForFinished(timeout)) { + if (report()) + report()->line() << i18nc("@info/plain", "(Command timeout while running)"); + return false; } + + onReadOutput(); return true; } @@ -165,7 +118,7 @@ bool ExternalCommand::run(int timeout) void ExternalCommand::onReadOutput() { - const QString s = QString::fromUtf8(processes[command().size() - 1].readAllStandardOutput()); + const QString s = QString::fromUtf8(readAllStandardOutput()); m_Output += s; diff --git a/src/util/externalcommand.h b/src/util/externalcommand.h index 8901f49..c9e4db1 100644 --- a/src/util/externalcommand.h +++ b/src/util/externalcommand.h @@ -45,30 +45,14 @@ class LIBKPMCORE_EXPORT ExternalCommand : public QProcess public: explicit ExternalCommand(const QString& cmd = QString(), const QStringList& args = QStringList()); explicit ExternalCommand(Report& report, const QString& cmd = QString(), const QStringList& args = QStringList()); - explicit ExternalCommand(const std::vector cmd, const std::vector args); - explicit ExternalCommand(Report& report, const std::vector cmd, const std::vector args); - ~ExternalCommand(); public: - void setCommand(const std::vector cmd) { - m_Command = cmd; /**< @param cmd the command to run */ - } - const std::vector command() const { - return m_Command; /**< @return the command to run */ - } + void setCommand(const QString& cmd) { m_Command = cmd; } /**< @param cmd the command to run */ + const QString& command() const { return m_Command; } /**< @return the command to run */ - /** @param s the argument to add - @param i the command to which the argument is added - */ - void addArg(const QString& s, const int i = 0) { - m_Args[i] << s; - } - const std::vector args() const { - return m_Args; /**< @return the arguments */ - } - void setArgs(const std::vector args) { - m_Args = args; /**< @param args the new arguments */ - } + void addArg(const QString& s) { m_Args << s; } /**< @param s the argument to add */ + const QStringList& args() const { return m_Args; } /**< @return the arguments */ + void setArgs(const QStringList& args) { m_Args = args; } /**< @param args the new arguments */ bool start(int timeout = 30000); bool waitFor(int timeout = 30000); @@ -97,10 +81,9 @@ protected Q_SLOTS: void onReadOutput(); private: - QProcess *processes; Report *m_Report; - std::vector m_Command; - std::vector m_Args; + QString m_Command; + QStringList m_Args; int m_ExitCode; QString m_Output; };