Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Qt console application leaves terminal open on termination
Forum Updated to NodeBB v4.3 + New Features

Qt console application leaves terminal open on termination

Scheduled Pinned Locked Moved Solved General and Desktop
25 Posts 3 Posters 3.9k Views 2 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • SPlattenS Offline
    SPlattenS Offline
    SPlatten
    wrote on last edited by SPlatten
    #21

    @jsulm , its a bit like a web-server, multiple clients, each client (module) does not monopolise the application by holding up communications, so to keep it as responsive as possible each client gets it's own thread.

    Kind Regards,
    Sy

    SPlattenS 1 Reply Last reply
    0
    • SPlattenS SPlatten

      @jsulm , its a bit like a web-server, multiple clients, each client (module) does not monopolise the application by holding up communications, so to keep it as responsive as possible each client gets it's own thread.

      SPlattenS Offline
      SPlattenS Offline
      SPlatten
      wrote on last edited by
      #22

      @SPlatten , I've re-written the launch function:

      QProcess* clsScriptHelper::pLaunch(QString strApp, QStringList& slstArgs) {
          QString strFullPath(clsDebugService::strGetUserFolder(strApp));
          qdbg() << "Checking for PID for: " << strFullPath;
          QProcess* pModule = nullptr;
          qint64 int64PID;
          if ( blnGetPID(strFullPath, int64PID) == true ) {
          //Process already running, no action required
          } else {
              int intLastSep = strFullPath.lastIndexOf(QDir::separator());
              qdbg() << "Process is NOT running, launching";
      
              if ( intLastSep > 0 ) {
                  QString strName = strFullPath.mid(intLastSep + 1)
                         ,strPath = strFullPath.mid(0, intLastSep + 1);
                  pModule = new QProcess(this);
                  pModule->setArguments(slstArgs);
                  pModule->setWorkingDirectory(strPath);
                  pModule->setProgram(strName);
                  pModule->start();
                  int64PID = pModule->processId();
      
                  if ( int64PID == 0 ) {
                      delete pModule;
                      pModule = nullptr;
                  }
              }
          }
          if ( int64PID > 0 ) {
              qdbg() << "Process: " << strFullPath << " started, PID: " << QString::number(int64PID);
          }
          return pModule;
      }
      

      This works a lot better and now the child process is terminated and the terminal window closes when the main application terminates, however I am still seeing in the Application Output:

      W00000000000000000014:QObject: Cannot create children for a parent that is in a different thread.
      W00000000000000000015:(Parent is clsScriptHelper(0x10320da10), parent's thread is QThread(0x10320aad0), current thread is clsThread(0x10325d1a0)
      

      Is there any way to avoid/prevent this?

      Kind Regards,
      Sy

      jsulmJ 1 Reply Last reply
      0
      • SPlattenS SPlatten

        @SPlatten , I've re-written the launch function:

        QProcess* clsScriptHelper::pLaunch(QString strApp, QStringList& slstArgs) {
            QString strFullPath(clsDebugService::strGetUserFolder(strApp));
            qdbg() << "Checking for PID for: " << strFullPath;
            QProcess* pModule = nullptr;
            qint64 int64PID;
            if ( blnGetPID(strFullPath, int64PID) == true ) {
            //Process already running, no action required
            } else {
                int intLastSep = strFullPath.lastIndexOf(QDir::separator());
                qdbg() << "Process is NOT running, launching";
        
                if ( intLastSep > 0 ) {
                    QString strName = strFullPath.mid(intLastSep + 1)
                           ,strPath = strFullPath.mid(0, intLastSep + 1);
                    pModule = new QProcess(this);
                    pModule->setArguments(slstArgs);
                    pModule->setWorkingDirectory(strPath);
                    pModule->setProgram(strName);
                    pModule->start();
                    int64PID = pModule->processId();
        
                    if ( int64PID == 0 ) {
                        delete pModule;
                        pModule = nullptr;
                    }
                }
            }
            if ( int64PID > 0 ) {
                qdbg() << "Process: " << strFullPath << " started, PID: " << QString::number(int64PID);
            }
            return pModule;
        }
        

        This works a lot better and now the child process is terminated and the terminal window closes when the main application terminates, however I am still seeing in the Application Output:

        W00000000000000000014:QObject: Cannot create children for a parent that is in a different thread.
        W00000000000000000015:(Parent is clsScriptHelper(0x10320da10), parent's thread is QThread(0x10320aad0), current thread is clsThread(0x10325d1a0)
        

        Is there any way to avoid/prevent this?

        jsulmJ Offline
        jsulmJ Offline
        jsulm
        Lifetime Qt Champion
        wrote on last edited by jsulm
        #23

        @SPlatten said in Qt console application leaves terminal open on termination:

        Is there any way to avoid/prevent this?

        Yes, doing multithreading in a proper way. As I wrote before: you are doing something wrongly somewhere in your code. And the warning even tells you what: you are using an objects as parent for another object which lives in another thread.
        You should read this: https://doc.qt.io/qt-5/qobject.html#thread-affinity

        https://forum.qt.io/topic/113070/qt-code-of-conduct

        SPlattenS 2 Replies Last reply
        1
        • jsulmJ jsulm

          @SPlatten said in Qt console application leaves terminal open on termination:

          Is there any way to avoid/prevent this?

          Yes, doing multithreading in a proper way. As I wrote before: you are doing something wrongly somewhere in your code. And the warning even tells you what: you are using an objects as parent for another object which lives in another thread.
          You should read this: https://doc.qt.io/qt-5/qobject.html#thread-affinity

          SPlattenS Offline
          SPlattenS Offline
          SPlatten
          wrote on last edited by
          #24

          @jsulm, the difficulty is that the method of calling the launch function is from an exported / exposed (not sure of correct terminology) API call from the C++ to JavaScript:

          Q_INVOKABLE QJsonObject use(QJsonValue strModule);
          

          In the JavaScript:

          xmleng.use("mdFileIO");
          

          Where xmleng is exposed to the JavaScript by the engine:

              const QString strXMLEngine("xmleng");
          
              if ( objGlobal.hasProperty(strXMLEngine) == false ) {
                  clsScriptHelper* pScriptHlpr = clsScriptHelper::pobjGetInstance();
          
                  if ( pScriptHlpr != nullptr ) {
                      QJSValue result = pobjScriptEng->newQObject(pScriptHlpr);
                      objGlobal.setProperty(strXMLEngine, result);
                  }
              }
          

          The use function in C++:

          /**
           * @brief clsScriptHelper::use
           * @param strModule : Name of the module to use
           * @return JSON object containing pass on when using the module
           */
          QJsonObject clsScriptHelper::use(QJsonValue strModule) {   
              clsXMLnode* pobjRoot = clsXMLnode::spobjGetRoot();
              Q_ASSERT_X(pobjRoot!=nullptr, "clsScriptHelper::use"
                                          , "pobjRoot is NULL!");
              QString strModulesPath = pobjRoot->strGetAttribute(clsXMLnode::mscszAttrModules)
                     ,strModuleName = strModule.toString();
          //Is module already loaded?
              mpModules::iterator itrModule;
              QJsonObject objModule;
              QStringList slstSlot;
          
              if ( clsScriptHelper::blnGetModule(strModuleName, &itrModule) == true ) {
          //Module already loaded, get the process id
                  objModule = itrModule->second;
              } else {
          //Module not loaded yet, attempt to start the module
                  QString strFullPath(strModulesPath + strModule.toString());
                  QStringList slstArgs;
                  slstArgs << QString::number(clsSocketServer::mscuint16port);
                  slstArgs << QString::number(clsSocketServer::uint16NextModulePort());
                  slstArgs << QString::number(QCoreApplication::applicationPid());
                  QProcess* pProcess;
                  if (  (pProcess = pLaunch(strFullPath, slstArgs)) != nullptr ) {
          //Module has been successfully started, save its PID
                      qint64 int64PID = pProcess->processId();
                      objModule.insert(clsJSON::mscszModule, strModule);
                      objModule.insert(clsScriptHelper::mscszPID, QJsonValue(int64PID));
                      msmpModules.insert(std::make_pair(strModuleName, objModule));
          //Register JSON decoders
                      QString strKey(strModule.toString() + clsJSON::msccColon + QString(clsJSON::mscszCmdHB));
                      clsJSON::registerDecoder(strKey, blnDecodeHeartbeat);
                  }
              }
              return objModule;
          }
          

          Kind Regards,
          Sy

          1 Reply Last reply
          0
          • jsulmJ jsulm

            @SPlatten said in Qt console application leaves terminal open on termination:

            Is there any way to avoid/prevent this?

            Yes, doing multithreading in a proper way. As I wrote before: you are doing something wrongly somewhere in your code. And the warning even tells you what: you are using an objects as parent for another object which lives in another thread.
            You should read this: https://doc.qt.io/qt-5/qobject.html#thread-affinity

            SPlattenS Offline
            SPlattenS Offline
            SPlatten
            wrote on last edited by SPlatten
            #25

            @jsulm, fixed now, the solution was to from "this" when creating the process.

            Kind Regards,
            Sy

            1 Reply Last reply
            2

            • Login

            • Login or register to search.
            • First post
              Last post
            0
            • Categories
            • Recent
            • Tags
            • Popular
            • Users
            • Groups
            • Search
            • Get Qt Extensions
            • Unsolved