Skip to content

Commit

Permalink
win32: revisit how and when modules are enumerated
Browse files Browse the repository at this point in the history
  • Loading branch information
Jarhmander committed Nov 14, 2023
1 parent 4c9f140 commit f6c2f4f
Show file tree
Hide file tree
Showing 2 changed files with 32 additions and 13 deletions.
18 changes: 9 additions & 9 deletions c/foreign.c
Original file line number Diff line number Diff line change
Expand Up @@ -66,9 +66,6 @@ static ptr bvstring(const char *s);

#ifdef LOAD_SHARED_OBJECT
static void load_shared_object(const char *path);
#ifdef WIN32
HMODULE *base_modules;
#endif /* WIN32 */
#endif /* LOAD_SHARED_OBJECT */

#ifdef HPUX
Expand Down Expand Up @@ -135,9 +132,15 @@ static ptr lookup_dynamic(const char *s, ptr tbl) {

#ifdef WIN32
if (!handle) {
for (HMODULE *m = base_modules; *m; ++m) {
value = dlsym(*m, s);
if (value != NULL) return addr_to_ptr(value);
HMODULE *modules = S_enum_process_modules();
if (modules) {
for (HMODULE *m = modules; *m; ++m) {
value = dlsym(*m, s);
if (value != NULL) break;
}
free(modules);
if (value != NULL)
return addr_to_ptr(value);
}
} else
#endif /* WIN32 */
Expand Down Expand Up @@ -349,9 +352,6 @@ void S_foreign_init(void) {
S_protect(&S_foreign_dynamic);
S_foreign_dynamic = Snil;
Sforeign_symbol("(cs)load_shared_object", (void *)load_shared_object);
#ifdef WIN32
base_modules = S_enum_process_modules();
#endif /* WIN32 */
#endif /* LOAD_SHARED_OBJECT */

Sforeign_symbol("(cs)lookup_foreign_entry", (void *)lookup_foreign_entry);
Expand Down
27 changes: 23 additions & 4 deletions c/windows.c
Original file line number Diff line number Diff line change
Expand Up @@ -51,12 +51,31 @@ void *S_ntdlopen(const char *path) {
}

HMODULE *S_enum_process_modules(void) {
DWORD cur_num_bytes = 1024;
DWORD req_num_bytes;
HMODULE *modules = malloc(cur_num_bytes);

enum { MAX_MODULES = 256 };
if (!modules)
return NULL;

static HMODULE modules[MAX_MODULES + 1] = { NULL };
DWORD req_num_bytes;
EnumProcessModules(GetCurrentProcess(), modules, MAX_MODULES*sizeof(HMODULE), &req_num_bytes);
for (;;) {
if (!EnumProcessModules(GetCurrentProcess(), modules, cur_num_bytes, &req_num_bytes))
return NULL;
req_num_bytes += sizeof *modules; // for sentinel NULL value
if (req_num_bytes <= cur_num_bytes)
break;
HMODULE *new_mod = realloc(modules, req_num_bytes);
if (!new_mod) {
free(modules);
return NULL;
}

modules = new_mod;
cur_num_bytes = req_num_bytes;
}

const size_t numel = req_num_bytes/sizeof *modules;
modules[numel - 1] = NULL;

return modules;
}
Expand Down

0 comments on commit f6c2f4f

Please sign in to comment.