Commit 3fd6805f authored by Sam Ravnborg's avatar Sam Ravnborg Committed by Greg Kroah-Hartman

[PATCH] Clean up module.c symbol searching logic

Signed-off-by: default avatarSam Ravnborg <sam@ravnborg.org>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@suse.de>
parent 58383af6
...@@ -135,6 +135,18 @@ extern const unsigned long __start___kcrctab_gpl[]; ...@@ -135,6 +135,18 @@ extern const unsigned long __start___kcrctab_gpl[];
#define symversion(base, idx) ((base) ? ((base) + (idx)) : NULL) #define symversion(base, idx) ((base) ? ((base) + (idx)) : NULL)
#endif #endif
/* lookup symbol in given range of kernel_symbols */
static const struct kernel_symbol *lookup_symbol(const char *name,
const struct kernel_symbol *start,
const struct kernel_symbol *stop)
{
const struct kernel_symbol *ks = start;
for (; ks < stop; ks++)
if (strcmp(ks->name, name) == 0)
return ks;
return NULL;
}
/* Find a symbol, return value, crc and module which owns it */ /* Find a symbol, return value, crc and module which owns it */
static unsigned long __find_symbol(const char *name, static unsigned long __find_symbol(const char *name,
struct module **owner, struct module **owner,
...@@ -142,39 +154,41 @@ static unsigned long __find_symbol(const char *name, ...@@ -142,39 +154,41 @@ static unsigned long __find_symbol(const char *name,
int gplok) int gplok)
{ {
struct module *mod; struct module *mod;
unsigned int i; const struct kernel_symbol *ks;
/* Core kernel first. */ /* Core kernel first. */
*owner = NULL; *owner = NULL;
for (i = 0; __start___ksymtab+i < __stop___ksymtab; i++) { ks = lookup_symbol(name, __start___ksymtab, __stop___ksymtab);
if (strcmp(__start___ksymtab[i].name, name) == 0) { if (ks) {
*crc = symversion(__start___kcrctab, i); *crc = symversion(__start___kcrctab, (ks - __start___ksymtab));
return __start___ksymtab[i].value; return ks->value;
}
} }
if (gplok) { if (gplok) {
for (i = 0; __start___ksymtab_gpl+i<__stop___ksymtab_gpl; i++) ks = lookup_symbol(name, __start___ksymtab_gpl,
if (strcmp(__start___ksymtab_gpl[i].name, name) == 0) { __stop___ksymtab_gpl);
*crc = symversion(__start___kcrctab_gpl, i); if (ks) {
return __start___ksymtab_gpl[i].value; *crc = symversion(__start___kcrctab_gpl,
} (ks - __start___ksymtab_gpl));
return ks->value;
}
} }
/* Now try modules. */ /* Now try modules. */
list_for_each_entry(mod, &modules, list) { list_for_each_entry(mod, &modules, list) {
*owner = mod; *owner = mod;
for (i = 0; i < mod->num_syms; i++) ks = lookup_symbol(name, mod->syms, mod->syms + mod->num_syms);
if (strcmp(mod->syms[i].name, name) == 0) { if (ks) {
*crc = symversion(mod->crcs, i); *crc = symversion(mod->crcs, (ks - mod->syms));
return mod->syms[i].value; return ks->value;
} }
if (gplok) { if (gplok) {
for (i = 0; i < mod->num_gpl_syms; i++) { ks = lookup_symbol(name, mod->gpl_syms,
if (strcmp(mod->gpl_syms[i].name, name) == 0) { mod->gpl_syms + mod->num_gpl_syms);
*crc = symversion(mod->gpl_crcs, i); if (ks) {
return mod->gpl_syms[i].value; *crc = symversion(mod->gpl_crcs,
} (ks - mod->gpl_syms));
return ks->value;
} }
} }
} }
...@@ -1444,18 +1458,13 @@ static void setup_modinfo(struct module *mod, Elf_Shdr *sechdrs, ...@@ -1444,18 +1458,13 @@ static void setup_modinfo(struct module *mod, Elf_Shdr *sechdrs,
#ifdef CONFIG_KALLSYMS #ifdef CONFIG_KALLSYMS
int is_exported(const char *name, const struct module *mod) int is_exported(const char *name, const struct module *mod)
{ {
unsigned int i; if (!mod && lookup_symbol(name, __start___ksymtab, __stop___ksymtab))
return 1;
if (!mod) { else
for (i = 0; __start___ksymtab+i < __stop___ksymtab; i++) if (lookup_symbol(name, mod->syms, mod->syms + mod->num_syms))
if (strcmp(__start___ksymtab[i].name, name) == 0)
return 1;
return 0;
}
for (i = 0; i < mod->num_syms; i++)
if (strcmp(mod->syms[i].name, name) == 0)
return 1; return 1;
return 0; else
return 0;
} }
/* As per nm */ /* As per nm */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment