Module loading
Posted: Thu Nov 03, 2022 7:27 am
Hello! I have problem with the kernel module loading.
So after the module loaded, i got #UD and the problem is: the kernel symbols not resolving(address of functions didn't setted)
What i am doing wrong?
There are function for module symbols resolving:
So after the module loaded, i got #UD and the problem is: the kernel symbols not resolving(address of functions didn't setted)
What i am doing wrong?
There are function for module symbols resolving:
Code: Select all
bool module_resolve_symbols(module_t *mod,Elf32_Ehdr *e) {
unsigned i;
Elf32_Shdr *s;
Elf32_Sym *sym;
const char *str;
Elf32_Word size,entsize;
for (i = 0, s = (Elf32_Shdr *)((char *)e + e->e_shoff); i < e->e_shnum;
i++,s = (Elf32_Shdr *)((char *)s + e->e_shentsize)) {
if (s->sh_type == SHT_SYMTAB) break;
}
if (i == e->e_shnum) {
printf("%s: failed to find symbol table in module!\n");
return false;
}
mod->symtab = (Elf32_Sym *)((char *)e + s->sh_offset);
sym = mod->symtab;
size = s->sh_size;
entsize = s->sh_entsize;
s = (Elf32_Shdr *)((char *)e + e->e_shoff + e->e_shentsize * s->sh_link);
str = (char *)e+ s->sh_offset;
for (i = 0; i < size/entsize; i++,sym = (Elf32_Sym *)((char *)sym + entsize)) {
uint8_t type = ELF32_ST_TYPE(sym->st_info);
uint8_t bind = ELF32_ST_BIND(sym->st_info);
const char *name = str + sym->st_name;
switch (type) {
case STT_NOTYPE:
case STT_OBJECT:
if (sym->st_name != 0 && sym->st_shndx == 0) {
sym->st_value = (Elf32_Addr)symbols_findValue(name);
printf("Symbol %s founded in kernel: %x\n",name,sym->st_value);
if (!sym->st_value) {
printf("Cannot find symbol %s in kernel, abort\n",name);
return false;
}
} else {
sym->st_value += (Elf32_Addr) module_get_section_addr(mod,sym->st_shndx);
if (bind != STB_LOCAL) {
printf("TODO: add this to global symbol table: %s\n",name);
}
} break;
case STT_FUNC:
sym->st_value += (Elf32_Addr) module_get_section_addr(mod,sym->st_shndx);
if (bind != STB_LOCAL) {
printf("TODO: This function %s also need to be added to global symbols table\n",name);
}
if (strcmp(name,"module_main")) {
printf("Module init found\n");
mod->init = (void (*)(module_t *))sym->st_value;
}
break;
case STT_SECTION:
sym->st_value += (Elf32_Addr) module_get_section_addr(mod,sym->st_shndx);
break;
case STT_FILE:
sym->st_value = 0;
break;
default:
printf("Unknown symbol type: %d,%s\n",type,name);
return false;
break;
}
}
return true;
}