From a55177edfa4728a4871350c565ec4ef9a2dbb064 Mon Sep 17 00:00:00 2001 From: WerWolv Date: Mon, 19 Sep 2022 21:56:43 +0200 Subject: [PATCH] fix: Curl SSL context not being thread safe in the slightest --- lib/libimhex/include/hex/helpers/net.hpp | 2 ++ lib/libimhex/source/helpers/net.cpp | 11 +++++------ main/include/init/splash_window.hpp | 2 +- main/source/init/splash_window.cpp | 24 +++++++++++------------- main/source/init/tasks.cpp | 6 +++--- 5 files changed, 22 insertions(+), 23 deletions(-) diff --git a/lib/libimhex/include/hex/helpers/net.hpp b/lib/libimhex/include/hex/helpers/net.hpp index c0a2d860d..5ecf5feb3 100644 --- a/lib/libimhex/include/hex/helpers/net.hpp +++ b/lib/libimhex/include/hex/helpers/net.hpp @@ -11,6 +11,7 @@ #include #include +#include #include @@ -60,6 +61,7 @@ namespace hex { private: CURL *m_ctx; + mbedtls_x509_crt m_caCert; curl_slist *m_headers = nullptr; std::mutex m_transmissionActive; diff --git a/lib/libimhex/source/helpers/net.cpp b/lib/libimhex/source/helpers/net.cpp index a76008a63..6bc3c4e47 100644 --- a/lib/libimhex/source/helpers/net.cpp +++ b/lib/libimhex/source/helpers/net.cpp @@ -9,8 +9,6 @@ #include #include -#include - #include #include @@ -52,13 +50,13 @@ namespace hex { auto *cfg = static_cast(sslctx); - static mbedtls_x509_crt crt; - mbedtls_x509_crt_init(&crt); + auto crt = static_cast(userData); + mbedtls_x509_crt_init(crt); auto cacert = romfs::get("cacert.pem").string(); - mbedtls_x509_crt_parse(&crt, reinterpret_cast(cacert.data()), cacert.size()); + mbedtls_x509_crt_parse(crt, reinterpret_cast(cacert.data()), cacert.size()); - mbedtls_ssl_conf_ca_chain(cfg, &crt, nullptr); + mbedtls_ssl_conf_ca_chain(cfg, crt, nullptr); return CURLE_OK; } @@ -114,6 +112,7 @@ namespace hex { curl_easy_setopt(this->m_ctx, CURLOPT_CAPATH, nullptr); curl_easy_setopt(this->m_ctx, CURLOPT_SSLCERTTYPE, "PEM"); curl_easy_setopt(this->m_ctx, CURLOPT_SSL_CTX_FUNCTION, sslCtxFunction); + curl_easy_setopt(this->m_ctx, CURLOPT_SSL_CTX_DATA, &this->m_caCert); #endif curl_easy_setopt(this->m_ctx, CURLOPT_PROXY, Net::s_proxyUrl.c_str()); diff --git a/main/include/init/splash_window.hpp b/main/include/init/splash_window.hpp index ec03ed074..e1c2a2c93 100644 --- a/main/include/init/splash_window.hpp +++ b/main/include/init/splash_window.hpp @@ -26,7 +26,7 @@ namespace hex::init { private: GLFWwindow *m_window; std::mutex m_progressMutex; - float m_progress = 0; + std::atomic m_progress = 0; std::string m_currTaskName; void initGLFW(); diff --git a/main/source/init/splash_window.cpp b/main/source/init/splash_window.cpp index e92e0012d..7c389bc2e 100644 --- a/main/source/init/splash_window.cpp +++ b/main/source/init/splash_window.cpp @@ -43,18 +43,20 @@ namespace hex::init { return std::async(std::launch::async, [this] { bool status = true; - u32 tasksCompleted = 0; + std::atomic tasksCompleted = 0; for (const auto &[name, task, async] : this->m_tasks) { - if (!async) { - std::lock_guard guard(this->m_progressMutex); - this->m_currTaskName = name; - } + auto runTask = [&, task = task, name = name] { + { + std::lock_guard guard(this->m_progressMutex); + this->m_currTaskName = name; + } - auto runTask = [&, task = task] { if (!task()) status = false; tasksCompleted++; + + this->m_progress = float(tasksCompleted) / this->m_tasks.size(); }; try { @@ -68,18 +70,14 @@ namespace hex::init { log::error("Init task '{}' threw an exception: {}", name, e.what()); status = false; } - - { - std::lock_guard guard(this->m_progressMutex); - this->m_progress += 1.0F / this->m_tasks.size(); - } } - while (tasksCompleted < this->m_tasks.size()) + while (tasksCompleted < this->m_tasks.size()) { std::this_thread::sleep_for(100ms); + } // Small extra delay so the last progress step is visible - std::this_thread::sleep_for(200ms); + std::this_thread::sleep_for(100ms); return status; }); diff --git a/main/source/init/tasks.cpp b/main/source/init/tasks.cpp index 1603c20e3..acb5edd0a 100644 --- a/main/source/init/tasks.cpp +++ b/main/source/init/tasks.cpp @@ -324,9 +324,9 @@ namespace hex::init { std::vector getInitTasks() { return { - { "Checking for updates...", checkForUpdates, false }, - { "Downloading information...", downloadInformation, true }, - { "Loading fonts...", loadFonts, true }, + { "Checking for updates...", checkForUpdates, true }, + { "Downloading information...", downloadInformation, true }, + { "Loading fonts...", loadFonts, true }, { "Creating directories...", createDirectories, false }, { "Loading settings...", loadSettings, false }, { "Loading plugins...", loadPlugins, false },