how to read QByteArray and run as Detached process in qt? - qt

I'm trying to run the hardcoded base64 .exe file in a Detached process.
What I'm trying now is:
void Read(QString file){
QProcess process;
process.startDetached(file);
}
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
QByteArray exe = QByteArray::fromBase64("TVqQAAMAAAAEAAAA...."); //base64 of .exe file
QString s = exe.data();
qDebug() << s ;
Read(s);
return a.exec();
}
not working, debug shows : "MZ?"

Related

Qt console application quit is problematic, stack variables is not being destructed

When you close console application in Windows 10, in the following code, Boo object is not being destructed even it is a local variable. I tried to catch interrupts but it didnt worked. I tried to connect to aboutToQuit signal , it didn't worked as well. Is there any way to destruct an object just before quit?
class Boo {
public:
~Boo() {
std::cout << "i'm dying" << std::endl;
}
};
void handle_quit() {
std::cout << "I quit" << std::endl;
}
int main(int argc, char *argv[])
{
Boo test;
QCoreApplication app(argc, argv);
QTimer::singleShot(0, &app, [&]() {
std::cout << "hello world qt";
});
QObject::connect(&app, &QCoreApplication::aboutToQuit, [&]() {
handle_quit();
});
return app.exec();
}
Here is the answer:
If you close the concole application by closing cmd window, the application gets SIGBREAK interrupt. In that case, you need to destruct everthing in 5 seconds. After 5 second application is being terminated forcefully by the system. Since my stack is not being destructed in that case, I moved it to heap and destructed it as soon as I got SIGBREAK.
class Boo {
~Boo () {
//do destruction job..
}
}
std::shared_ptr<Boo> test;
void SigInt_Handler(int) {
//destruct in 5 second...
test.reset();
}
int main(int argc, char *argv[])
{
test = make_shared<Boo>();
signal(SIGBREAK , &SigInt_Handler);
QCoreApplication app(argc, argv);
QTimer::singleShot(0, &app, [&]() {
std::cout << "hello world qt";
});
return app.exec();
}

How to continually run QProcess while running my QML program?

The problem I have in my code is, once the QML engine uplouded the QProcess stop!! Is it possible to let QProcess run while the QMLis already in operation!
the idea is: I want the user to be able to interact with only one specific mouse and one keyboard and to continually check this condition!
Can some one check what is the problem here?
int main(int argc, char *argv[])
{
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
QGuiApplication app(argc, argv);
QQmlApplicationEngine engine;
bool scanForDevices=0;
USBdeviceID *usbdeviceid =new USBdeviceID();
engine.rootContext()->setContextProperty("USBdeviceID", usbdeviceid);
QProcess OProcess;
QString Command; //Contains the command to be execute
Command = "lsusb";
while (1)
{
OProcess.start(Command,QIODevice::ReadOnly); //Starts execution of command
OProcess.waitForFinished(); //Waits for execution to complete
QString StdOut = OProcess.readAllStandardOutput(); //Reads standard output
QString StdError = OProcess.readAllStandardError(); //Reads standard error
cout<<"\n Printing the standard output..........\n";
cout<<endl<<StdOut.toStdString();
bool mouse1 = StdOut.contains("ID 046d:c03e");
bool keyBoard1 = StdOut.contains("ID 413c:1003");
if (mouse1 ==1 && keyBoard1==1)
{
// start main program
// revoke A signal to tell QML the correct devices are connected
usbdeviceid->setMouse1Detected(1);
usbdeviceid->setkeyBoard1Detected(1);
engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
if (engine.rootObjects().isEmpty())
return -1;
return app.exec();
}
}
}
}
It is not necessary to create infinite loops in Qt, instead the most elegant thing is to use the signals.
#include <QGuiApplication>
#include <QProcess>
#include <QQmlApplicationEngine>
class LSUSB: public QObject
{
Q_OBJECT
public:
LSUSB(const QStringList & ids, QObject *parent=nullptr): QObject(parent), status(false), ids(ids)
{
QString command = "lsusb";
connect(&process, &QProcess::readyReadStandardOutput, this, &LSUSB::onReadyReadStandardOutput);
connect(&process, QOverload<int, QProcess::ExitStatus>::of(&QProcess::finished), this, &LSUSB::onFinished);
process.setProgram(command);
process.start();
}
Q_SIGNALS:
void isLoaded();
private Q_SLOTS:
void onReadyReadStandardOutput(){
QString stdout = process.readAllStandardOutput();
status = true;
for(const QString & id: ids){
status &= stdout.contains(id);
}
if(status){
process.kill();
Q_EMIT isLoaded();
}
}
void onFinished(){
if(!status)
process.start();
}
private:
QProcess process;
bool status;
QStringList ids;
};
int main(int argc, char *argv[])
{
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
QGuiApplication app(argc, argv);
QQmlApplicationEngine engine;
LSUSB lsusb({"ID 046d:c03e", "ID 413c:1003"});
USBdeviceID usbdeviceid;
QObject::connect(&lsusb, &LSUSB::isLoaded, [&engine, &usbdeviceid](){
usbdeviceid.setMouse1Detected(1);
usbdeviceid.setkeyBoard1Detected(1);
engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
if (engine.rootObjects().isEmpty())
QCoreApplication::exit(-1);
});
return app.exec();
}
#include "main.moc"

How to restart a qt application after crashing?

Is it possible to restart a qt application after its crashing? Just like those windows service which will restart on its own. If so, how could I do it? I have tried code like this:
#define RESTART_CODE 1000
int main(int argc, char *argv[])
{
int return_from_event_loop_code;
QPointer<QApplication> app;
QPointer<MainWindow> main_window;
do
{
if(app) delete app;
if(main_window) delete main_window;
app = new QApplication(argc, argv);
main_window = new MainWindow(app);
return_from_event_loop_code = app->exec();
}
while(return_from_event_loop_code==RESTART_CODE)
return return_from_event_loop_code;
}
But it is not working...
What should I do now?
create another qt application that runs your application.
#include <QApplication>
#include "QProcess"
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
QProcess aProcess;
QString exe = "Your process name with exact path";
QByteArray myOut;
while(1)
{
aProcess.start(exe);
//aProcess.waitForStarted();
//myOut = aProcess.readAllStandardOutput();
//printf("%s",myOut.constData());
aProcess.waitForFinished(-1);
//QString output(aProcess.readAllStandardOutput());
myOut = aProcess.readAllStandardOutput();
printf("%s",myOut.constData());
}
return a.exec();
}
this program will restart your app when it crashed or closed
You can use my open source library:
https://marketplace.qt.io/products/main-loop-wdt-for-qt-qml
It is a watchdog timer for the main loop and only works if the main loop freezes (double mutex lock, infinite loop, etc.), but it would not work in an application crash.

Memory corruption with libtorrent-rasterbar and QGuiApplication

I'm trying to use libtorrent in my Qt5 application but keep getting segfaults
with messages like malloc(): memory corruption. After hours of debbuging I come up with this small piece of code which triggers this problem:
int main(int argc, char *argv[])
{
QGuiApplication app(argc, argv);
std::string filename = "fedora.torrent";
libtorrent::error_code ec;
libtorrent::add_torrent_params parameters;
std::cerr << "111\n";
parameters.ti = new libtorrent::torrent_info(filename, ec);;
std::cerr << "222\n";
return app.exec()
}
In this case constructor of torrent_info produce segfault. But if I move libtorrent related code before creation of QGuiApplication like this:
int main(int argc, char *argv[])
{
std::string filename = "fedora.torrent";
libtorrent::error_code ec;
libtorrent::add_torrent_params parameters;
std::cerr << "111\n";
parameters.ti = new libtorrent::torrent_info(filename, ec);;
std::cerr << "222\n";
QGuiApplication app(argc, argv);
return app.exec()
}
then it works just fine. Also this problem exist only in 32-bit build, in 64-bit build both variants work the same.
This is most likely caused by building libtorrent with one set of TORRENT_* defines and linking against it with a different set. Some of those defines affect layouts of some structs used in the public API and when differing between the calling application and the library introduce ABI incompatibility issues.

QX11EmbedWidget and QX11EmbedContainer

Can one place an arbitrary program (firefox, openoffice, etc...) in a QX11EmbedContainer? The fllowing seems, to work
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
QX11EmbedContainer container;
container.show();
QProcess * process = new QProcess(&container);
QString executable("xterm");
QStringList arguments;
arguments << "-into";
arguments << QString::number(container.winId());
process->start(executable, arguments);
int status = app.exec();
process->close();
return status;
}
but the next snippet launches a new window, not what I want
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
QX11EmbedContainer container;
container.show();
QProcess * process = new QProcess(&container);
QString executable("konsole");
process->start(executable);
int status = app.exec();
process->close();
return status;
}
The first example work because xterm is able to reparent its top level widget (an X11 window). You tell it to do so with the argument -into <WinId>.
I don't know if Konsole can do that, i don't use it and the man page doesn't seem to talk about this.
But that doesn't mean it is not doable, the X Window system is very flexible and anyone can reparent another window (that's how windows managers add decorations to windows).
Take a look at man 3 XReparentWindow ;-)

Resources