mirror of
https://github.com/RGBCube/serenity
synced 2025-07-27 10:07:44 +00:00
LibDl: Move the dlfcn
implementation to LibC
This commit is contained in:
parent
27bfb81702
commit
226608a48f
9 changed files with 77 additions and 81 deletions
|
@ -4,10 +4,82 @@
|
|||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#include <AK/String.h>
|
||||
#include <AK/Types.h>
|
||||
#include <dlfcn.h>
|
||||
#include <dlfcn_integration.h>
|
||||
#include <string.h>
|
||||
|
||||
// These are used by libdl and are filled in by the dynamic loader.
|
||||
// These are filled in by the dynamic loader.
|
||||
DlCloseFunction __dlclose;
|
||||
DlOpenFunction __dlopen;
|
||||
DlSymFunction __dlsym;
|
||||
DlAddrFunction __dladdr;
|
||||
|
||||
// FIXME: use thread_local and a String once TLS works
|
||||
#ifdef NO_TLS
|
||||
char* s_dlerror_text = NULL;
|
||||
bool s_dlerror_retrieved = false;
|
||||
#else
|
||||
__thread char* s_dlerror_text = NULL;
|
||||
__thread bool s_dlerror_retrieved = false;
|
||||
#endif
|
||||
|
||||
static void store_error(String const& error)
|
||||
{
|
||||
free(s_dlerror_text);
|
||||
s_dlerror_text = strdup(error.characters());
|
||||
s_dlerror_retrieved = false;
|
||||
}
|
||||
|
||||
int dlclose(void* handle)
|
||||
{
|
||||
auto result = __dlclose(handle);
|
||||
if (result.is_error()) {
|
||||
store_error(result.error().text);
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
char* dlerror()
|
||||
{
|
||||
if (s_dlerror_retrieved) {
|
||||
free(s_dlerror_text);
|
||||
s_dlerror_text = nullptr;
|
||||
}
|
||||
s_dlerror_retrieved = true;
|
||||
return const_cast<char*>(s_dlerror_text);
|
||||
}
|
||||
|
||||
void* dlopen(char const* filename, int flags)
|
||||
{
|
||||
auto result = __dlopen(filename, flags);
|
||||
if (result.is_error()) {
|
||||
store_error(result.error().text);
|
||||
return nullptr;
|
||||
}
|
||||
return result.value();
|
||||
}
|
||||
|
||||
void* dlsym(void* handle, char const* symbol_name)
|
||||
{
|
||||
auto result = __dlsym(handle, symbol_name);
|
||||
if (result.is_error()) {
|
||||
store_error(result.error().text);
|
||||
return nullptr;
|
||||
}
|
||||
return result.value();
|
||||
}
|
||||
|
||||
int dladdr(void* addr, Dl_info* info)
|
||||
{
|
||||
auto result = __dladdr(addr, info);
|
||||
if (result.is_error()) {
|
||||
// FIXME: According to the man page glibc does _not_ make the error
|
||||
// available via dlerror(), however we do. Does this break anything?
|
||||
store_error(result.error().text);
|
||||
return 0;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue