1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20: #include <dlfcn.h>
21: #include <link.h>
22: #include <ldsodefs.h>
23: #include <libintl.h>
24:
25: #if !defined SHARED && defined IS_IN_libdl
26:
27: int
28: dlinfo (void *handle, int request, void *arg)
29: {
30: return __dlinfo (handle, request, arg, RETURN_ADDRESS (0));
31: }
32:
33: #else
34:
35: # include <dl-tls.h>
36:
37: struct dlinfo_args
38: {
39: ElfW(Addr) caller;
40: void *handle;
41: int request;
42: void *arg;
43: };
44:
45: static void
46: dlinfo_doit (void *argsblock)
47: {
48: struct dlinfo_args *const args = argsblock;
49: struct link_map *l = args->handle;
50:
51: # if 0
52: if (args->handle == RTLD_SELF)
53: {
54: Lmid_t nsid;
55:
56:
57: for (nsid = 0; nsid < DL_NNS; ++nsid)
58: for (l = GL(dl_ns)[nsid]._ns_loaded; l != NULL; l = l->l_next)
59: if (caller >= l->l_map_start && caller < l->l_map_end
60: && (l->l_contiguous || _dl_addr_inside_object (l, caller)))
61: break;
62:
63: if (l == NULL)
64: GLRO(dl_signal_error) (0, NULL, NULL, N_("\
65: RTLD_SELF used in code not dynamically loaded"));
66: }
67: # endif
68:
69: switch (args->request)
70: {
71: case RTLD_DI_CONFIGADDR:
72: default:
73: GLRO(dl_signal_error) (0, NULL, NULL, N_("unsupported dlinfo request"));
74: break;
75:
76: case RTLD_DI_LMID:
77: *(Lmid_t *) args->arg = l->l_ns;
78: break;
79:
80: case RTLD_DI_LINKMAP:
81: *(struct link_map **) args->arg = l;
82: break;
83:
84: case RTLD_DI_SERINFO:
85: _dl_rtld_di_serinfo (l, args->arg, false);
86: break;
87: case RTLD_DI_SERINFOSIZE:
88: _dl_rtld_di_serinfo (l, args->arg, true);
89: break;
90:
91: case RTLD_DI_ORIGIN:
92: strcpy (args->arg, l->l_origin);
93: break;
94:
95: case RTLD_DI_TLS_MODID:
96: *(size_t *) args->arg = 0;
97: *(size_t *) args->arg = l->l_tls_modid;
98: break;
99:
100: case RTLD_DI_TLS_DATA:
101: {
102: void *data = NULL;
103: if (l->l_tls_modid != 0)
104: data = _dl_tls_get_addr_soft (l);
105: *(void **) args->arg = data;
106: break;
107: }
108: }
109: }
110:
111: int
112: __dlinfo (void *handle, int request, void *arg DL_CALLER_DECL)
113: {
114: # ifdef SHARED
115: if (__builtin_expect (_dlfcn_hook != NULL, 0))
116: return _dlfcn_hook->dlinfo (handle, request, arg,
117: DL_CALLER);
118: # endif
119:
120: struct dlinfo_args args = { (ElfW(Addr)) DL_CALLER,
121: handle, request, arg };
122: return _dlerror_run (&dlinfo_doit, &args) ? -1 : 0;
123: }
124: # ifdef SHARED
125: strong_alias (__dlinfo, dlinfo)
126: # endif
127: #endif