2017-12-21 07:45:38 +08:00
|
|
|
/*
|
2025-02-19 17:29:27 +08:00
|
|
|
* Copyright (C) 2019-2025 Intel Corporation
|
2017-12-21 07:45:38 +08:00
|
|
|
*
|
2018-09-18 15:11:08 +08:00
|
|
|
* SPDX-License-Identifier: MIT
|
2017-12-21 07:45:38 +08:00
|
|
|
*
|
|
|
|
*/
|
|
|
|
|
2020-02-24 05:44:01 +08:00
|
|
|
#include "shared/source/os_interface/linux/os_library_linux.h"
|
2019-02-27 18:39:32 +08:00
|
|
|
|
2020-02-24 05:44:01 +08:00
|
|
|
#include "shared/source/helpers/debug_helpers.h"
|
2021-02-23 21:03:54 +08:00
|
|
|
#include "shared/source/os_interface/linux/sys_calls.h"
|
2019-02-27 18:39:32 +08:00
|
|
|
|
2025-02-19 17:29:27 +08:00
|
|
|
#include <cstring>
|
2017-12-21 07:45:38 +08:00
|
|
|
#include <dlfcn.h>
|
2023-08-21 20:00:06 +08:00
|
|
|
#include <link.h>
|
2017-12-21 07:45:38 +08:00
|
|
|
|
2019-03-26 18:59:46 +08:00
|
|
|
namespace NEO {
|
2021-03-12 09:01:51 +08:00
|
|
|
|
2024-10-17 03:53:07 +08:00
|
|
|
OsLibrary *OsLibrary::load(const OsLibraryCreateProperties &properties) {
|
|
|
|
auto ptr = new (std::nothrow) Linux::OsLibrary(properties);
|
2017-12-21 07:45:38 +08:00
|
|
|
if (ptr == nullptr)
|
|
|
|
return nullptr;
|
|
|
|
|
|
|
|
if (!ptr->isLoaded()) {
|
|
|
|
delete ptr;
|
|
|
|
return nullptr;
|
|
|
|
}
|
|
|
|
return ptr;
|
|
|
|
}
|
2020-10-30 20:42:13 +08:00
|
|
|
|
|
|
|
const std::string OsLibrary::createFullSystemPath(const std::string &name) {
|
|
|
|
return name;
|
|
|
|
}
|
|
|
|
|
2024-12-20 00:56:46 +08:00
|
|
|
bool getLoadedLibVersion(const std::string &libName, const std::string ®exVersionPattern, std::string &outVersion, std::string &errReason) {
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2017-12-21 07:45:38 +08:00
|
|
|
namespace Linux {
|
|
|
|
|
2024-10-17 03:53:07 +08:00
|
|
|
OsLibrary::OsLibrary(const OsLibraryCreateProperties &properties) {
|
|
|
|
if (properties.libraryName.empty() || properties.performSelfLoad) {
|
2021-02-23 21:03:54 +08:00
|
|
|
this->handle = SysCalls::dlopen(0, RTLD_LAZY);
|
2017-12-21 07:45:38 +08:00
|
|
|
} else {
|
2019-03-01 01:13:29 +08:00
|
|
|
#ifdef SANITIZER_BUILD
|
2021-02-23 21:03:54 +08:00
|
|
|
auto dlopenFlag = RTLD_LAZY;
|
2019-03-01 01:13:29 +08:00
|
|
|
#else
|
2021-02-23 21:03:54 +08:00
|
|
|
auto dlopenFlag = RTLD_LAZY | RTLD_DEEPBIND;
|
2020-08-06 23:58:01 +08:00
|
|
|
/* Background: https://github.com/intel/compute-runtime/issues/122 */
|
2019-03-01 01:13:29 +08:00
|
|
|
#endif
|
2024-10-17 03:53:07 +08:00
|
|
|
dlopenFlag = properties.customLoadFlags ? *properties.customLoadFlags : dlopenFlag;
|
2021-02-23 21:03:54 +08:00
|
|
|
adjustLibraryFlags(dlopenFlag);
|
2024-10-17 03:53:07 +08:00
|
|
|
this->handle = SysCalls::dlopen(properties.libraryName.c_str(), dlopenFlag);
|
|
|
|
if (!this->handle && (properties.errorValue != nullptr)) {
|
|
|
|
properties.errorValue->assign(dlerror());
|
2021-03-12 09:01:51 +08:00
|
|
|
}
|
2017-12-21 07:45:38 +08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
OsLibrary::~OsLibrary() {
|
|
|
|
if (this->handle != nullptr) {
|
|
|
|
dlclose(this->handle);
|
|
|
|
this->handle = nullptr;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
bool OsLibrary::isLoaded() {
|
|
|
|
return this->handle != nullptr;
|
|
|
|
}
|
|
|
|
|
|
|
|
void *OsLibrary::getProcAddress(const std::string &procName) {
|
|
|
|
DEBUG_BREAK_IF(this->handle == nullptr);
|
|
|
|
|
|
|
|
return dlsym(this->handle, procName.c_str());
|
|
|
|
}
|
2023-08-21 20:00:06 +08:00
|
|
|
|
|
|
|
std::string OsLibrary::getFullPath() {
|
|
|
|
struct link_map *map = nullptr;
|
|
|
|
int retVal = NEO::SysCalls::dlinfo(this->handle, RTLD_DI_LINKMAP, &map);
|
|
|
|
if (retVal == 0 && map != nullptr) {
|
|
|
|
return std::string(map->l_name);
|
|
|
|
}
|
|
|
|
return std::string();
|
|
|
|
}
|
2025-02-19 17:29:27 +08:00
|
|
|
|
|
|
|
bool isLibraryLoaded(const std::string &libraryName) {
|
|
|
|
auto handle = SysCalls::dlopen(0, RTLD_LAZY);
|
2025-02-19 21:34:15 +08:00
|
|
|
if (!handle) {
|
|
|
|
return false;
|
|
|
|
}
|
2025-02-19 17:29:27 +08:00
|
|
|
struct link_map *map = nullptr;
|
|
|
|
int retVal = NEO::SysCalls::dlinfo(handle, RTLD_DI_LINKMAP, &map);
|
|
|
|
if (retVal == 0 && map != nullptr) {
|
|
|
|
while (map) {
|
|
|
|
if (strstr(map->l_name, libraryName.c_str())) {
|
|
|
|
dlclose(handle);
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
map = map->l_next;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
dlclose(handle);
|
|
|
|
return false;
|
|
|
|
}
|
2018-06-13 03:54:39 +08:00
|
|
|
} // namespace Linux
|
2019-03-26 18:59:46 +08:00
|
|
|
} // namespace NEO
|