geode/loader/src/platform/mac/Mod.cpp

78 lines
2.6 KiB
C++
Raw Normal View History

2022-07-30 12:24:03 -04:00
#include <Geode/DefaultInclude.hpp>
#ifdef GEODE_IS_MACOS
2022-10-30 14:56:36 -04:00
#include <Geode/loader/Mod.hpp>
#include <dlfcn.h>
2022-07-30 12:24:03 -04:00
USE_GEODE_NAMESPACE();
2022-10-30 14:56:36 -04:00
template <typename T>
T findSymbolOrMangled(void* dylib, char const* name, char const* mangled) {
auto res = reinterpret_cast<T>(dlsym(dylib, name));
if (!res) {
res = reinterpret_cast<T>(dlsym(dylib, mangled));
}
return res;
2022-07-30 12:24:03 -04:00
}
Result<> Mod::loadPlatformBinary() {
2022-10-30 14:56:36 -04:00
auto dylib =
dlopen((this->m_tempDirName / this->m_info.m_binaryName).string().c_str(), RTLD_LAZY);
if (dylib) {
this->m_implicitLoadFunc =
findSymbolOrMangled<geode_load>(dylib, "geode_implicit_load", "_geode_implicit_load");
this->m_loadFunc = findSymbolOrMangled<geode_load>(dylib, "geode_load", "_geode_load");
this->m_unloadFunc =
findSymbolOrMangled<geode_unload>(dylib, "geode_unload", "_geode_unload");
this->m_enableFunc =
findSymbolOrMangled<geode_enable>(dylib, "geode_enable", "_geode_enable");
this->m_disableFunc =
findSymbolOrMangled<geode_disable>(dylib, "geode_disable", "_geode_disable");
this->m_saveDataFunc =
findSymbolOrMangled<geode_save_data>(dylib, "geode_save_data", "_geode_save_data");
this->m_loadDataFunc =
findSymbolOrMangled<geode_load_data>(dylib, "geode_load_data", "_geode_load_data");
this->m_settingUpdatedFunc = findSymbolOrMangled<geode_setting_updated>(
dylib, "geode_setting_updated", "_geode_setting_updated"
);
2022-07-30 12:24:03 -04:00
2022-10-30 14:56:36 -04:00
if (!this->m_implicitLoadFunc && !this->m_loadFunc) {
return Err(
2022-10-30 14:56:36 -04:00
"Unable to find mod entry point (lacking both implicit & explicit definition)"
);
}
2022-07-30 12:24:03 -04:00
2022-10-30 14:56:36 -04:00
if (this->m_platformInfo) {
delete this->m_platformInfo;
}
this->m_platformInfo = new PlatformInfo { dylib };
2022-07-30 12:24:03 -04:00
return Ok();
2022-10-30 14:56:36 -04:00
}
std::string err = (char const*)dlerror();
return Err("Unable to load the DYLIB: dlerror returned (" + err + ")");
2022-07-30 12:24:03 -04:00
}
Result<> Mod::unloadPlatformBinary() {
2022-10-30 14:56:36 -04:00
auto dylib = this->m_platformInfo->m_dylib;
delete this->m_platformInfo;
this->m_platformInfo = nullptr;
if (dlclose(dylib) == 0) {
this->m_unloadFunc = nullptr;
this->m_loadFunc = nullptr;
this->m_implicitLoadFunc = nullptr;
this->m_enableFunc = nullptr;
this->m_disableFunc = nullptr;
this->m_saveDataFunc = nullptr;
this->m_loadDataFunc = nullptr;
this->m_settingUpdatedFunc = nullptr;
return Ok();
2022-10-30 14:56:36 -04:00
}
else {
return Err("Unable to free library");
2022-10-30 14:56:36 -04:00
}
2022-07-30 12:24:03 -04:00
}
#endif