79 lines
1.9 KiB
C++
Executable File
79 lines
1.9 KiB
C++
Executable File
/**
|
|
* Loads and manages the libTmsIfAdapter module
|
|
* $Id$
|
|
* $HeadURL$
|
|
* $Author$
|
|
*
|
|
* Created by Mike Wille, ESZS, 2025-04-17
|
|
*/
|
|
|
|
#pragma once
|
|
|
|
#include "tms_if_adapter.h"
|
|
|
|
#include <stdexcept>
|
|
#include <string>
|
|
|
|
/* there's a massive problem with symbol collision between RTI DDS & Cyclone DDS (namely dds::core::Time::invalid())
|
|
* so we need the linux specific RTLD_DEEPBIND to force the use of the Cyclone DDS symbols inside the library */
|
|
#include <dlfcn.h>
|
|
|
|
|
|
namespace UAS
|
|
{
|
|
namespace ModuleLoader
|
|
{
|
|
using dlopen_handle = void *;
|
|
|
|
|
|
dlopen_handle load(std::string libPath) noexcept(false)
|
|
{
|
|
dlopen_handle handle = dlopen((libPath + "/libTmsIfAdapter.so").c_str(), RTLD_NOW | RTLD_LOCAL | RTLD_DEEPBIND);
|
|
|
|
if (handle == nullptr)
|
|
{
|
|
throw std::runtime_error((std::string("tms_if.h => ModuleLoader::load: unable to load libTmsIfAdapter.so: ") + dlerror()).c_str());
|
|
}
|
|
|
|
return handle;
|
|
}
|
|
|
|
|
|
TmsIfAdapter &get(dlopen_handle handle) noexcept(false)
|
|
{
|
|
auto get = reinterpret_cast<void *(*)()>(dlsym(handle, "get"));
|
|
if (get == nullptr)
|
|
{
|
|
throw std::runtime_error((std::string("tms_if.h => ModuleLoader::get: function symbol 'get' does not exist in libTmsIfAdapter.so: ") + dlerror()).c_str());
|
|
}
|
|
|
|
UAS::TmsIfAdapter &adapter = *reinterpret_cast<UAS::TmsIfAdapter *>(get());
|
|
return adapter;
|
|
}
|
|
|
|
|
|
void unload(dlopen_handle handle) noexcept(false)
|
|
{
|
|
if (handle == nullptr)
|
|
{
|
|
return;
|
|
}
|
|
|
|
auto stop = reinterpret_cast<void *(*)()>(dlsym(handle, "stop"));
|
|
if (stop == nullptr)
|
|
{
|
|
throw std::runtime_error((std::string("tms_if.h => ModuleLoader::unload: function symbol 'stop' does not exist in libTmsIfAdapter.so: ") + dlerror()).c_str());
|
|
}
|
|
|
|
stop();
|
|
|
|
const int ret = dlclose(handle);
|
|
|
|
if (ret != 0)
|
|
{
|
|
throw std::runtime_error((std::string("tms_if.h => ModuleLoader::unload: dlclose failed - ret != 0 (was "+std::to_string(ret)+"): ") + dlerror()).c_str());
|
|
}
|
|
}
|
|
} // ModuleLoader
|
|
} // namespace UAS
|