Skip to content

Commit c8432a0

Browse files
committed
Implement dladdr() (partially)
Note that this always returns with dli_sname and dli_saddr set to NULL, indicating no symbol matching addr could be found. Signed-off-by: Jon Turney <[email protected]>
1 parent 51a993c commit c8432a0

File tree

6 files changed

+61
-1
lines changed

6 files changed

+61
-1
lines changed

winsup/cygwin/common.din

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -364,6 +364,7 @@ difftime NOSIGFE
364364
dirfd SIGFE
365365
dirname NOSIGFE
366366
div NOSIGFE
367+
dladdr SIGFE
367368
dlclose SIGFE
368369
dlerror NOSIGFE
369370
dlfork NOSIGFE

winsup/cygwin/dlfcn.cc

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -386,3 +386,37 @@ dlerror ()
386386
}
387387
return res;
388388
}
389+
390+
extern "C" int
391+
dladdr (const void *addr, Dl_info *info)
392+
{
393+
HMODULE hModule;
394+
BOOL ret = GetModuleHandleEx (GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS,
395+
(LPCSTR) addr,
396+
&hModule);
397+
if (!ret)
398+
return 0;
399+
400+
/* Module handle happens to be equal to it's base load address. */
401+
info->dli_fbase = hModule;
402+
403+
/* Get the module filename. This pathname may be in short-, long- or //?/
404+
format, depending on how it was specified when loaded, but we assume this
405+
is always an absolute pathname. */
406+
WCHAR fname[MAX_PATH];
407+
DWORD length = GetModuleFileNameW (hModule, fname, MAX_PATH);
408+
if ((length == 0) || (length == MAX_PATH))
409+
return 0;
410+
411+
/* Convert to a cygwin pathname */
412+
ssize_t conv = cygwin_conv_path (CCP_WIN_W_TO_POSIX | CCP_ABSOLUTE, fname,
413+
info->dli_fname, MAX_PATH);
414+
if (conv)
415+
return 0;
416+
417+
/* Always indicate no symbol matching addr could be found. */
418+
info->dli_sname = NULL;
419+
info->dli_saddr = NULL;
420+
421+
return 1;
422+
}

winsup/cygwin/include/cygwin/version.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -472,12 +472,13 @@ details. */
472472
305: [f]pathconf flag _PC_CASE_INSENSITIVE added.
473473
306: Export getentropy, getrandom.
474474
307: Export timingsafe_bcmp, timingsafe_memcmp.
475+
308: Export dladdr.
475476
476477
Note that we forgot to bump the api for ualarm, strtoll, strtoull,
477478
sigaltstack, sethostname. */
478479

479480
#define CYGWIN_VERSION_API_MAJOR 0
480-
#define CYGWIN_VERSION_API_MINOR 307
481+
#define CYGWIN_VERSION_API_MINOR 308
481482

482483
/* There is also a compatibity version number associated with the shared memory
483484
regions. It is incremented when incompatible changes are made to the shared

winsup/cygwin/include/dlfcn.h

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,9 @@ details. */
99
#ifndef _DLFCN_H
1010
#define _DLFCN_H
1111

12+
#include <sys/cdefs.h>
13+
#include <limits.h>
14+
1215
#ifdef __cplusplus
1316
extern "C" {
1417
#endif
@@ -42,6 +45,21 @@ extern void dlfork (int);
4245
#define RTLD_DEEPBIND 32 /* Place lookup scope so that this lib is */
4346
/* preferred over global scope. */
4447

48+
49+
#if __GNU_VISIBLE
50+
typedef struct Dl_info Dl_info;
51+
52+
struct Dl_info
53+
{
54+
char dli_fname[PATH_MAX]; /* Filename of defining object */
55+
void *dli_fbase; /* Load address of that object */
56+
const char *dli_sname; /* Name of nearest lower symbol */
57+
void *dli_saddr; /* Exact value of nearest symbol */
58+
};
59+
60+
extern int dladdr (const void *addr, Dl_info *info);
61+
#endif
62+
4563
#ifdef __cplusplus
4664
}
4765
#endif

winsup/cygwin/release/2.7.1

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,8 @@ What's new:
33

44
- New API: timingsafe_bcmp, timingsafe_memcmp
55

6+
- New API: dladdr
7+
68
What changed:
79
-------------
810

winsup/doc/posix.xml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1277,6 +1277,7 @@ also IEEE Std 1003.1-2008 (POSIX.1-2008).</para>
12771277
clog10
12781278
clog10f
12791279
clog10l
1280+
dladdr (see chapter "Implementation Notes")
12801281
dremf
12811282
dup3
12821283
envz_add
@@ -1665,6 +1666,9 @@ depending on whether _BSD_SOURCE or _GNU_SOURCE is defined when compiling.</para
16651666
<para><function>basename</function> is available in both POSIX and GNU flavors,
16661667
depending on whether libgen.h is included or not.</para>
16671668

1669+
<para><function>dladdr</function> always sets the Dl_info members dli_sname and
1670+
dli_saddr to NULL, indicating no symbol matching addr could be found.</para>
1671+
16681672
</sect1>
16691673

16701674
</chapter>

0 commit comments

Comments
 (0)