#include "plugin_launcher.h" #include "qt/qt_process_manager.h" #include #include #include #include namespace { QString resolveLogosHostPath(const QStringList& pluginsDirs) { QString logosHostPath; QByteArray envPathBytes = qgetenv("LOGOS_HOST_PATH"); if (!envPathBytes.isEmpty()) { logosHostPath = QString::fromUtf8(envPathBytes); } if (logosHostPath.isEmpty()) { logosHostPath = QDir::cleanPath(QCoreApplication::applicationDirPath() + "/logos_host"); } if (!QFile::exists(logosHostPath)) { if (!pluginsDirs.isEmpty()) { QDir pluginsDirCandidate(pluginsDirs.first()); QString candidate = QDir::cleanPath(pluginsDirCandidate.absoluteFilePath("../bin/logos_host")); if (QFile::exists(candidate)) { logosHostPath = candidate; } } } if (!QFile::exists(logosHostPath)) { qCritical() << "logos_host not found at:" << logosHostPath << "- set LOGOS_HOST_PATH or place it next to the executable"; return QString(); } return logosHostPath; } } namespace PluginLauncher { bool launch(const QString& name, const QString& pluginPath, const QStringList& pluginsDirs, OnTerminatedFn onTerminated) { QString logosHostPath = resolveLogosHostPath(pluginsDirs); if (logosHostPath.isEmpty()) return false; std::vector arguments = { "--name", name.toStdString(), "--path", pluginPath.toStdString() }; QtProcessManager::ProcessCallbacks callbacks; callbacks.onFinished = [onTerminated](const std::string& pName, int exitCode, bool crashed) { Q_UNUSED(exitCode); QString qName = QString::fromStdString(pName); if (crashed) { qCritical() << "Plugin process crashed:" << qName; exit(1); } if (onTerminated) onTerminated(qName); }; callbacks.onError = [](const std::string& pName, bool crashed) { if (crashed) { qCritical() << "Plugin process crashed:" << QString::fromStdString(pName); exit(1); } }; callbacks.onOutput = [](const std::string& pName, const std::string& line, bool isStderr) { QString qName = QString::fromStdString(pName); QString qLine = QString::fromStdString(line); if (isStderr) { qCritical() << "[" << qName << "]" << qLine; } else if (qLine.contains("Warning:") || qLine.contains("WARNING:")) { qWarning() << "[" << qName << "]" << qLine; } else if (qLine.contains("Critical:") || qLine.contains("FAILED:") || qLine.contains("ERROR:")) { qCritical() << "[" << qName << "]" << qLine; } }; return QtProcessManager::startProcess(name.toStdString(), logosHostPath.toStdString(), arguments, callbacks); } bool sendToken(const QString& name, const QString& token) { return QtProcessManager::sendToken(name.toStdString(), token.toStdString()); } void terminate(const QString& name) { QtProcessManager::terminateProcess(name.toStdString()); } void terminateAll() { QtProcessManager::terminateAll(); } bool hasProcess(const QString& name) { return QtProcessManager::hasProcess(name.toStdString()); } QHash getAllProcessIds() { auto stdMap = QtProcessManager::getAllProcessIds(); QHash result; for (const auto& [name, pid] : stdMap) { result.insert(QString::fromStdString(name), pid); } return result; } }