diff --git a/app/gui/mainwindow.cpp b/app/gui/mainwindow.cpp index 095eb3bc..93716d3f 100644 --- a/app/gui/mainwindow.cpp +++ b/app/gui/mainwindow.cpp @@ -35,11 +35,9 @@ void MainWindow::on_newHostBtn_clicked() QString hostname = popupmanager::getHostnameDialog(this); if (!hostname.isEmpty()) { - IdentityManager im = IdentityManager(); - NvPairingManager pm(hostname, im); + NvPairingManager pm(hostname); QString pin = pm.generatePinString(); - NvHTTP http(hostname, im); pm.pair(http.getServerInfo(), pin); } } diff --git a/app/http/computermanager.cpp b/app/http/computermanager.cpp index 843c43b5..5dc772db 100644 --- a/app/http/computermanager.cpp +++ b/app/http/computermanager.cpp @@ -23,9 +23,8 @@ class PcMonitorThread : public QThread #define TRIES_BEFORE_OFFLINING 2 #define POLLS_PER_APPLIST_FETCH 10 - PcMonitorThread(NvComputer* computer, IdentityManager im) - : m_Im(im), - m_Computer(computer) + PcMonitorThread(NvComputer* computer) + : m_Computer(computer) { } @@ -49,7 +48,7 @@ class PcMonitorThread : public QThread bool TryPollComputer(QString& address, bool& changed) { - NvHTTP http(address, m_Im); + NvHTTP http(address); QString serverInfo; try { @@ -174,6 +173,5 @@ signals: void computerStateChanged(NvComputer* computer); private: - IdentityManager m_Im; NvComputer* m_Computer; }; diff --git a/app/http/identitymanager.cpp b/app/http/identitymanager.cpp index cd8f5d3e..68ef9e59 100644 --- a/app/http/identitymanager.cpp +++ b/app/http/identitymanager.cpp @@ -13,6 +13,20 @@ #include #include +IdentityManager* IdentityManager::s_Im = nullptr; + +IdentityManager* +IdentityManager::get() +{ + // This will always be called first on the main thread, + // so it's safe to initialize without locks. + if (s_Im == nullptr) { + s_Im = new IdentityManager(); + } + + return s_Im; +} + IdentityManager::IdentityManager() { m_RootDirectory = QDir(QStandardPaths::writableLocation(QStandardPaths::AppConfigLocation)); diff --git a/app/http/identitymanager.h b/app/http/identitymanager.h index 267c1825..602f0330 100644 --- a/app/http/identitymanager.h +++ b/app/http/identitymanager.h @@ -6,8 +6,6 @@ class IdentityManager { public: - IdentityManager(); - QString getUniqueId(); @@ -20,10 +18,18 @@ public: QSslConfiguration getSslConfig(); + static + IdentityManager* + get(); + private: + IdentityManager(); + QDir m_RootDirectory; QByteArray m_CachedPrivateKey; QByteArray m_CachedPemCert; QString m_CachedUniqueId; + + static IdentityManager* s_Im; }; diff --git a/app/http/nvhttp.cpp b/app/http/nvhttp.cpp index 91aac65f..c581c180 100644 --- a/app/http/nvhttp.cpp +++ b/app/http/nvhttp.cpp @@ -11,9 +11,8 @@ #define REQUEST_TIMEOUT_MS 5000 -NvHTTP::NvHTTP(QString address, IdentityManager im) : - m_Address(address), - m_Im(im) +NvHTTP::NvHTTP(QString address) : + m_Address(address) { m_BaseUrlHttp.setScheme("http"); m_BaseUrlHttps.setScheme("https"); @@ -266,14 +265,14 @@ NvHTTP::openConnection(QUrl baseUrl, // Build a URL for the request QUrl url(baseUrl); url.setPath("/" + command); - url.setQuery("uniqueid=" + m_Im.getUniqueId() + + url.setQuery("uniqueid=" + IdentityManager::get()->getUniqueId() + "&uuid=" + QUuid::createUuid().toRfc4122().toHex() + ((arguments != nullptr) ? ("&" + arguments) : "")); QNetworkRequest request = QNetworkRequest(url); // Add our client certificate - request.setSslConfiguration(m_Im.getSslConfig()); + request.setSslConfiguration(IdentityManager::get()->getSslConfig()); QNetworkReply* reply = m_Nam.get(request); diff --git a/app/http/nvhttp.h b/app/http/nvhttp.h index cbf8adb9..7f50ee8b 100644 --- a/app/http/nvhttp.h +++ b/app/http/nvhttp.h @@ -40,7 +40,7 @@ private: class NvHTTP { public: - NvHTTP(QString address, IdentityManager im); + NvHTTP(QString address); int getCurrentGame(QString serverInfo); @@ -92,5 +92,4 @@ private: QString m_Address; QNetworkAccessManager m_Nam; - IdentityManager m_Im; }; diff --git a/app/http/nvpairingmanager.cpp b/app/http/nvpairingmanager.cpp index fef66b4c..4ab5c1c5 100644 --- a/app/http/nvpairingmanager.cpp +++ b/app/http/nvpairingmanager.cpp @@ -10,11 +10,10 @@ #include #include -NvPairingManager::NvPairingManager(QString address, IdentityManager im) : - m_Http(address, im), - m_Im(im) +NvPairingManager::NvPairingManager(QString address) : + m_Http(address) { - QByteArray cert = m_Im.getCertificate(); + QByteArray cert = IdentityManager::get()->getCertificate(); BIO *bio = BIO_new_mem_buf(cert.data(), -1); THROW_BAD_ALLOC_IF_NULL(bio); @@ -25,7 +24,7 @@ NvPairingManager::NvPairingManager(QString address, IdentityManager im) : throw new std::runtime_error("Unable to load certificate"); } - QByteArray pk = m_Im.getPrivateKey(); + QByteArray pk = IdentityManager::get()->getPrivateKey(); bio = BIO_new_mem_buf(pk.data(), -1); THROW_BAD_ALLOC_IF_NULL(bio); @@ -198,7 +197,7 @@ NvPairingManager::pair(QString serverInfo, QString pin) QString getCert = m_Http.openConnectionToString(m_Http.m_BaseUrlHttp, "pair", "devicename=roth&updateState=1&phrase=getservercert&salt=" + - salt.toHex() + "&clientcert=" + m_Im.getCertificate().toHex(), + salt.toHex() + "&clientcert=" + IdentityManager::get()->getCertificate().toHex(), false); m_Http.verifyResponseStatus(getCert); if (m_Http.getXmlString(getCert, "paired") != "1") diff --git a/app/http/nvpairingmanager.h b/app/http/nvpairingmanager.h index dbf8bba9..7ea281c3 100644 --- a/app/http/nvpairingmanager.h +++ b/app/http/nvpairingmanager.h @@ -19,7 +19,7 @@ public: ALREADY_IN_PROGRESS }; - NvPairingManager(QString address, IdentityManager im); + NvPairingManager(QString address); ~NvPairingManager(); @@ -52,7 +52,6 @@ private: signMessage(QByteArray message); NvHTTP m_Http; - IdentityManager m_Im; X509* m_Cert; EVP_PKEY* m_PrivateKey; };