75 lines
2.2 KiB
C
75 lines
2.2 KiB
C
#include <elf.h>
|
|
#include <merror.h>
|
|
#include <netinet/in.h>
|
|
#include <stddef.h>
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include <string.h>
|
|
|
|
#include "asm.h"
|
|
|
|
#define SYMTBL_INIT_LEN 24
|
|
|
|
int symtab_init(struct symbol_table *symtab)
|
|
{
|
|
symtab->size = SYMTBL_INIT_LEN;
|
|
symtab->len = 0;
|
|
symtab->symbols = malloc(sizeof(Elf32_Sym) * SYMTBL_INIT_LEN);
|
|
symtab->sections = malloc(sizeof(ssize_t) * SYMTBL_INIT_LEN);
|
|
|
|
if (symtab->symbols == NULL || symtab->sections == NULL) {
|
|
PERROR("cannot alloc");
|
|
return M_ERROR;
|
|
}
|
|
|
|
Elf32_Sym null = {0};
|
|
if (symtab_push(symtab, null, -1))
|
|
return M_ERROR;
|
|
|
|
return M_SUCCESS;
|
|
}
|
|
|
|
void symtab_free(struct symbol_table *symtab)
|
|
{
|
|
free(symtab->symbols);
|
|
free(symtab->sections);
|
|
}
|
|
|
|
int symtab_push(struct symbol_table *symtab, Elf32_Sym sym, ssize_t sec_idx)
|
|
{
|
|
if (symtab->len >= symtab->size) {
|
|
symtab->size *= 2;
|
|
symtab->symbols = realloc(symtab->symbols,
|
|
sizeof(Elf32_Sym) * symtab->size);
|
|
symtab->sections = realloc(symtab->sections,
|
|
sizeof(ssize_t) * symtab->size);
|
|
if (symtab->symbols == NULL || symtab->sections == NULL) {
|
|
PERROR("cannot realloc");
|
|
return M_ERROR;
|
|
}
|
|
}
|
|
|
|
symtab->symbols[symtab->len] = sym;
|
|
symtab->sections[symtab->len++] = sec_idx;
|
|
return M_SUCCESS;
|
|
}
|
|
|
|
int symtab_find(struct symbol_table *symtab, Elf32_Sym **ptr,
|
|
size_t *idx, const char name[MAX_LEX_LENGTH])
|
|
{
|
|
for (uint32_t i = 0; i < symtab->len; i++) {
|
|
Elf32_Sym *sym = &symtab->symbols[i];
|
|
const char *str = &symtab->strtab->ptr[ntohl(sym->st_name)];
|
|
if (strcmp(str, name) == 0) {
|
|
if (ptr != NULL)
|
|
*ptr = sym;
|
|
|
|
ptrdiff_t diff = sym - symtab->symbols;
|
|
if (idx != NULL)
|
|
*idx = diff;
|
|
|
|
return M_SUCCESS;
|
|
}
|
|
}
|
|
return M_ERROR;
|
|
}
|