forked from github_mirror/framelesshelper
sysapiloader: minor improvements of previous refactor
Signed-off-by: Yuhang Zhao <2546789017@qq.com>
This commit is contained in:
parent
fa8ca1ae2f
commit
a375bc6748
|
@ -40,6 +40,7 @@ public:
|
||||||
Q_NODISCARD static SysApiLoader *instance();
|
Q_NODISCARD static SysApiLoader *instance();
|
||||||
|
|
||||||
Q_NODISCARD static QString platformSharedLibrarySuffixName();
|
Q_NODISCARD static QString platformSharedLibrarySuffixName();
|
||||||
|
Q_NODISCARD static QString platformSystemLibraryDirectory();
|
||||||
Q_NODISCARD static QString generateUniqueKey(const QString &library, const QString &function);
|
Q_NODISCARD static QString generateUniqueKey(const QString &library, const QString &function);
|
||||||
|
|
||||||
Q_NODISCARD static QFunctionPointer resolve(const QString &library, const char *function);
|
Q_NODISCARD static QFunctionPointer resolve(const QString &library, const char *function);
|
||||||
|
|
|
@ -47,6 +47,8 @@
|
||||||
#include <QtCore/qhash.h>
|
#include <QtCore/qhash.h>
|
||||||
#include <QtCore/qmutex.h>
|
#include <QtCore/qmutex.h>
|
||||||
#include <QtCore/qloggingcategory.h>
|
#include <QtCore/qloggingcategory.h>
|
||||||
|
#include <QtCore/qdir.h>
|
||||||
|
#include <QtCore/qvarlengtharray.h>
|
||||||
#if SYSAPILOADER_QSYSTEMLIBRARY
|
#if SYSAPILOADER_QSYSTEMLIBRARY
|
||||||
# include <QtCore/private/qsystemlibrary_p.h>
|
# include <QtCore/private/qsystemlibrary_p.h>
|
||||||
#endif // SYSAPILOADER_QSYSTEMLIBRARY
|
#endif // SYSAPILOADER_QSYSTEMLIBRARY
|
||||||
|
@ -80,7 +82,7 @@ Q_GLOBAL_STATIC(SysApiLoaderData, g_loaderData)
|
||||||
|
|
||||||
Q_GLOBAL_STATIC(SysApiLoader, g_sysApiLoader)
|
Q_GLOBAL_STATIC(SysApiLoader, g_sysApiLoader)
|
||||||
|
|
||||||
static const bool LoaderDebug = qEnvironmentVariableIntValue("FRAMELESSHELPER_SYSAPILOADER_DEBUG");
|
static const bool LoaderDebugFlag = qEnvironmentVariableIntValue("FRAMELESSHELPER_SYSAPILOADER_DEBUG");
|
||||||
|
|
||||||
SysApiLoader::SysApiLoader(QObject *parent) : QObject(parent)
|
SysApiLoader::SysApiLoader(QObject *parent) : QObject(parent)
|
||||||
{
|
{
|
||||||
|
@ -103,7 +105,26 @@ QString SysApiLoader::platformSharedLibrarySuffixName()
|
||||||
#elif defined(Q_OS_MACOS)
|
#elif defined(Q_OS_MACOS)
|
||||||
return FRAMELESSHELPER_STRING_LITERAL(".dylib");
|
return FRAMELESSHELPER_STRING_LITERAL(".dylib");
|
||||||
#else
|
#else
|
||||||
#error Unsupported platform!
|
#error "Unsupported platform!"
|
||||||
|
#endif
|
||||||
|
}();
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
QString SysApiLoader::platformSystemLibraryDirectory()
|
||||||
|
{
|
||||||
|
static const auto result = []() -> QString {
|
||||||
|
#ifdef Q_OS_WINDOWS
|
||||||
|
QVarLengthArray<wchar_t, MAX_PATH> buf = {};
|
||||||
|
const UINT len = GetSystemDirectoryW(buf.data(), MAX_PATH);
|
||||||
|
if (len > MAX_PATH) {
|
||||||
|
// No need to +1 here, GetSystemDirectoryW() will always give us a null terminator.
|
||||||
|
buf.resize(len);
|
||||||
|
GetSystemDirectoryW(buf.data(), len);
|
||||||
|
}
|
||||||
|
return QString::fromWCharArray(buf.constData(), len);
|
||||||
|
#else
|
||||||
|
return FRAMELESSHELPER_STRING_LITERAL("/usr/lib");
|
||||||
#endif
|
#endif
|
||||||
}();
|
}();
|
||||||
return result;
|
return result;
|
||||||
|
@ -116,18 +137,9 @@ QString SysApiLoader::generateUniqueKey(const QString &library, const QString &f
|
||||||
if (library.isEmpty() || function.isEmpty()) {
|
if (library.isEmpty() || function.isEmpty()) {
|
||||||
return {};
|
return {};
|
||||||
}
|
}
|
||||||
QString key = library;
|
QString key = QDir::toNativeSeparators(library);
|
||||||
// Remove path, only keep the file name.
|
// Remove path, only keep the file name.
|
||||||
const auto lastSeparatorPos = [&key]() -> qsizetype {
|
if (const qsizetype lastSeparatorPos = key.lastIndexOf(QDir::separator()); lastSeparatorPos >= 0) {
|
||||||
if (const qsizetype pos1 = key.lastIndexOf(u'/'); pos1 >= 0) {
|
|
||||||
return pos1;
|
|
||||||
} else if (const qsizetype pos2 = key.lastIndexOf(u'\\'); pos2 >= 0) {
|
|
||||||
return pos2;
|
|
||||||
} else {
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
}();
|
|
||||||
if (lastSeparatorPos >= 0) {
|
|
||||||
key.remove(0, lastSeparatorPos);
|
key.remove(0, lastSeparatorPos);
|
||||||
}
|
}
|
||||||
#ifdef Q_OS_WINDOWS
|
#ifdef Q_OS_WINDOWS
|
||||||
|
@ -137,7 +149,7 @@ QString SysApiLoader::generateUniqueKey(const QString &library, const QString &f
|
||||||
if (!key.endsWith(suffix)) {
|
if (!key.endsWith(suffix)) {
|
||||||
key.append(suffix);
|
key.append(suffix);
|
||||||
}
|
}
|
||||||
key.append(u':');
|
key.append(u'@');
|
||||||
key.append(function);
|
key.append(function);
|
||||||
return key;
|
return key;
|
||||||
}
|
}
|
||||||
|
@ -187,15 +199,15 @@ bool SysApiLoader::isAvailable(const QString &library, const QString &function)
|
||||||
const QString key = generateUniqueKey(library, function);
|
const QString key = generateUniqueKey(library, function);
|
||||||
const QMutexLocker locker(&g_loaderData()->mutex);
|
const QMutexLocker locker(&g_loaderData()->mutex);
|
||||||
if (g_loaderData()->functionCache.contains(key)) {
|
if (g_loaderData()->functionCache.contains(key)) {
|
||||||
if (LoaderDebug) {
|
if (LoaderDebugFlag) {
|
||||||
DEBUG << "Function cache found:" << key;
|
DEBUG << Q_FUNC_INFO << "Function cache found:" << key;
|
||||||
}
|
}
|
||||||
return (g_loaderData()->functionCache.value(key) != nullptr);
|
return (g_loaderData()->functionCache.value(key) != nullptr);
|
||||||
} else {
|
} else {
|
||||||
const QFunctionPointer symbol = SysApiLoader::resolve(library, function);
|
const QFunctionPointer symbol = SysApiLoader::resolve(library, function);
|
||||||
g_loaderData()->functionCache.insert(key, symbol);
|
g_loaderData()->functionCache.insert(key, symbol);
|
||||||
if (LoaderDebug) {
|
if (LoaderDebugFlag) {
|
||||||
DEBUG << "New function cache:" << key << (symbol ? "[VALID]" : "[NULL]");
|
DEBUG << Q_FUNC_INFO << "New function cache:" << key << (symbol ? "[VALID]" : "[NULL]");
|
||||||
}
|
}
|
||||||
if (symbol) {
|
if (symbol) {
|
||||||
DEBUG << "Successfully loaded" << function << "from" << library;
|
DEBUG << "Successfully loaded" << function << "from" << library;
|
||||||
|
@ -217,13 +229,13 @@ QFunctionPointer SysApiLoader::get(const QString &library, const QString &functi
|
||||||
const QString key = generateUniqueKey(library, function);
|
const QString key = generateUniqueKey(library, function);
|
||||||
const QMutexLocker locker(&g_loaderData()->mutex);
|
const QMutexLocker locker(&g_loaderData()->mutex);
|
||||||
if (g_loaderData()->functionCache.contains(key)) {
|
if (g_loaderData()->functionCache.contains(key)) {
|
||||||
if (LoaderDebug) {
|
if (LoaderDebugFlag) {
|
||||||
DEBUG << "Function cache found:" << key;
|
DEBUG << Q_FUNC_INFO << "Function cache found:" << key;
|
||||||
}
|
}
|
||||||
return g_loaderData()->functionCache.value(key);
|
return g_loaderData()->functionCache.value(key);
|
||||||
} else {
|
} else {
|
||||||
if (LoaderDebug) {
|
if (LoaderDebugFlag) {
|
||||||
DEBUG << "Function cache not found:" << key;
|
DEBUG << Q_FUNC_INFO << "Function cache not found:" << key;
|
||||||
}
|
}
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue