SenseApis: New senseApiManager and X11XcbApi

Still fleshing these out but ultimately senseApiMgr will manage
sense apis, and the X11XcbApi is where we'll connect to Xcb and
read the screen.
This commit is contained in:
2025-01-08 06:26:36 -04:00
parent f594d29a2d
commit fe3f911db4
8 changed files with 248 additions and 2 deletions
+94
View File
@@ -0,0 +1,94 @@
#include <dlfcn.h>
#include <iostream>
#include <stdexcept>
#include <optional>
#include <senseApis/senseApiManager.h>
std::vector<std::unique_ptr<SenseApiLib>> senseApiLibs;
std::vector<std::unique_ptr<SenseApiInstance>> senseApiInstances;
SenseApiLib& SenseApiManager::loadSenseApiLib(const std::string& libraryPath)
{
auto lib = std::make_unique<SenseApiLib>(libraryPath);
// Clear any existing error
dlerror();
lib->handle.reset(dlopen(libraryPath.c_str(), RTLD_LAZY));
if (!lib->handle)
{
std::string error = dlerror()
? dlerror()
: "Unknown error while opening shlib";
throw std::runtime_error(
std::string(__func__) + " - Cannot load library '"
+ libraryPath + "': "
+ error);
}
senseApiLibs.push_back(std::move(lib));
return *senseApiLibs.back();
}
std::optional<std::reference_wrapper<SenseApiLib>> SenseApiManager::getSenseApiLib(
const std::string& libraryPath)
{
auto it = std::find_if(senseApiLibs.begin(), senseApiLibs.end(),
[&libPath = libraryPath](const std::unique_ptr<SenseApiLib>& lib) {
return lib->libraryPath == libPath;
}
);
if (it != senseApiLibs.end()) { return **it; }
return std::nullopt;
}
void SenseApiManager::unloadSenseApiLib(const std::string& libraryPath)
{
auto it = std::find_if(senseApiLibs.begin(), senseApiLibs.end(),
[&lpath = libraryPath](const std::unique_ptr<SenseApiLib>& lib) {
return lib->libraryPath == lpath;
}
);
if (it != senseApiLibs.end())
{
senseApiLibs.erase(it);
return;
}
std::cerr << std::string(__func__) + ": Library not found: "
<< libraryPath << '\n';
}
void SenseApiManager::registerSenseApi(const SenseApiInstance& apiInstance)
{
auto it = std::find_if(
senseApiInstances.begin(), senseApiInstances.end(),
[&apiInstance](const std::unique_ptr<SenseApiInstance>& instance) {
return static_cast<const SenseApiInstance&>(*instance) == apiInstance;
});
if (it != senseApiInstances.end())
{
std::cerr << std::string(__func__)
+ ": Sense API Instance already registered.\n";
return;
}
senseApiInstances.push_back(std::make_unique<SenseApiInstance>(apiInstance));
}
void SenseApiManager::unregisterSenseApi(const SenseApiInstance& apiInstance)
{
auto it = std::find_if(
senseApiInstances.begin(), senseApiInstances.end(),
[&apiInstance](const std::unique_ptr<SenseApiInstance>& instance) {
return const_cast<const SenseApiInstance&>(*instance) == apiInstance;
});
if (it != senseApiInstances.end()) {
senseApiInstances.erase(it);
} else {
std::cerr << std::string(__func__) + ": Sense API Instance not found.\n";
}
}