QProcess with powershell command still running
-
I have a big problem with QProcess ( I use Qt c++ ). I need to execute a command with admin permissions ( windows 7 ) - netsh - I have to add exception to my firewall.
proc->start("powershell",QStringList()<<"-Command"<<"Start-Process"<<"powershell.exe"<<"-Verb"<<"runas"<<"-ArgumentList"<<R"('here is netsh command')");
proc->waitForStarted();
qInfo()<<"before";
proc->waitForFinished(-1);
qInfo()<<"yeah!";
When I execute my program I see only "before". What can I do? I check my netsh command in powershell - it's good. Command is still running ( I waited 3 minutes ). -
@TomNow99 said in QProcess with powershell command still running:
I check my netsh command in powershell - it's good
Do you have to authenticate yourself as admin in this case?
My guess is that the command is simply waiting for admin credentials. -
@jsulm When I go to powershell ( no QT ) I can run this command ( netsh ). I work in my private pc, so I have only one account (main account ). When I execute this command in powershell I don't have to write password or something like that. I run this command and it's done. When I go to cmd and run this command I get message "execute as admin".
-
@TomNow99 You should connect slots to https://doc.qt.io/qt-5/qprocess.html#readyReadStandardOutput and https://doc.qt.io/qt-5/qprocess.html#readyReadStandardError and print nout what you get. But to do so you have to remove your blocking
proc->waitForFinished(-1);
call!
Also https://doc.qt.io/qt-5/qprocess.html#stateChanged and https://doc.qt.io/qt-5/qprocess.html#errorOccurred signals can provide more information. -
I delete line: "proc->waitForFinished(-1);"
and I add slots:
void MainWindow::finishedslot(int p)
{
qInfo()<<p;
}
void MainWindow::stateChangedslot(QProcess::ProcessState state)
{
qInfo()<<state;
}void MainWindow::readyReadStandardErrorslot()
{
QString stdOutput = proc->readAllStandardError();
qInfo()<<stdOutput;
}void MainWindow::readyReadStandardOutputslot()
{
QString stdOutput = proc->readAllStandardOutput();
qInfo()<<stdOutput;
}void MainWindow::errorOccurredslot(QProcess::ProcessError error)
{
qInfo()<<error;
}Now I see informations:
QProcess::Starting
QProcess::Running
before
yeah!And nothing more.
-
@TomNow99 said in QProcess with powershell command still running:
and I add slots
Just to be sure: you connected all of them to the related signals?
-
@jsulm Yes. When I bad connect signal and slot I see information below in QT. Here are my connects:
connect(proc, SIGNAL(finished(int)), this, SLOT(finishedslot(int)));
connect(proc, SIGNAL(stateChanged(QProcess::ProcessState)), this, SLOT(stateChangedslot(QProcess::ProcessState)));
connect(proc, SIGNAL(readyReadStandardError()), this, SLOT(readyReadStandardErrorslot()));
connect(proc, SIGNAL(readyReadStandardOutput()), this, SLOT(readyReadStandardOutputslot()));
connect(proc, SIGNAL(errorOccurred(QProcess::ProcessError)), this, SLOT(errorOccurredslot(QProcess::ProcessError)));I connect them before proc->start().
When I wrote script .bat, which have only 3 commands:
@echo off
powershell -Command "& {Start-Process powershell.exe -Verb runas -ArgumentList 'netsh command here'}"
exit 0And I run it in QT (proc->start(script.bat)) I have the same problem. But when I delete the line with powershell command:
@echo off
exit 0I get message in Qt that script is done.
-
@jsulm When I change powershell command in QT ( or in .bat script ) to:
( in QT ):
proc->start("powershell",QStringList()<<"-Command"<<"Start-Process"<<"powershell.exe"<<"-ArgumentList"<<R"('echo 4')");I still don't get information that proc is finished.
Can you run this code in your computer?
-
The problem might be that you have two nested calls to PowerShell without exiting them. A quick search shows people reporting the inner PowerShell call (with
-Verb runas
) keeps the console window open. So, instead of the netsh command you might want to provide a script that has the netsh command and an exit. Or maybe you can concatenate the two directly in the-ArgumentList
(I don't have much experience with PowerShell, but in Linux I could separate commands with a semicolon).