From 489d35a65bc8eaa44d5176e7fe1dbb38265ce72f Mon Sep 17 00:00:00 2001 From: xamidev Date: Sat, 6 Sep 2025 19:32:19 +0200 Subject: [PATCH] clean switches + 64-common --- main.c | 182 +++++++++++++++++++++++++++++++++++-------------------- makefile | 2 +- 2 files changed, 118 insertions(+), 66 deletions(-) diff --git a/main.c b/main.c index 56ac267..3e5eab2 100644 --- a/main.c +++ b/main.c @@ -80,15 +80,9 @@ void display_elf_common(unsigned char e_ident[EI_NIDENT]) // EI_DATA switch(e_ident[5]) { - case 0x01: - printf("(little-endian) "); - break; - case 0x02: - printf("(big-endian) "); - break; - default: - printf("\nInvalid data encoding!\n"); - exit(-EINVAL); + case 0x01: printf("(little-endian) "); break; + case 0x02: printf("(big-endian) "); break; + default: printf("\nInvalid data encoding!\n"); exit(-EINVAL); } if (verbose) @@ -153,6 +147,61 @@ void check_dynamic32(Elf32_Ehdr* header, FILE* fp) free((char*)interpstr); } +void check_dynamic64(Elf64_Ehdr* header, FILE* fp) +{ + // Is dynamically linked? (has PT_INTERP program header?) + // read program headers + fseek(fp, header->e_phoff, SEEK_SET); + Elf64_Phdr *p_headers = malloc(header->e_phnum * sizeof(Elf64_Phdr)); + if (!p_headers) + { + puts("Memory allocation error."); + exit(-ENOMEM); + } + if (!fread(p_headers, sizeof(Elf64_Phdr), header->e_phnum, fp)) + { + puts("Read error."); + exit(-EIO); + } + + const char* interpstr = NULL; + + for (int i=0; ie_phnum; i++) + { + if (p_headers[i].p_type == PT_INTERP) + { + interp = true; + + // Get interpreter path + interpstr = malloc(p_headers[i].p_filesz); + if (!interpstr) + { + puts("Memory allocation error."); + exit(-ENOMEM); + } + fseek(fp, p_headers[i].p_offset, SEEK_SET); + if (!fread((char*)interpstr, 1, p_headers[i].p_filesz, fp)) + { + puts("Read error."); + exit(-EIO); + } + break; + } + } + + if (interp) + { + printf("dynamically linked (interpreter: %s), ", interpstr); + } + else + { + printf("statically linked, "); + } + + free(p_headers); + free((char*)interpstr); +} + void display_elf32(Elf32_Ehdr* header, FILE* fp) { printf("32-bit ELF "); @@ -162,25 +211,13 @@ void display_elf32(Elf32_Ehdr* header, FILE* fp) { switch (header->e_type) { - case 0x00: - printf("(no file type),"); - break; - case 0x01: - printf("(relocatable file),"); - break; - case 0x02: - printf("(executable file),"); - break; - case 0x03: // (ET_DYN, prob means PIE) - printf("(shared object file),"); - pie = true; - break; - case 0x04: - printf("(core file),"); - break; - default: - printf("(unknown),"); - break; + case 0x00: printf("(no file type),"); break; + case 0x01: printf("(relocatable file),"); break; + case 0x02: printf("(executable file),"); break; + // (ET_DYN, prob means PIE) + case 0x03: printf("(shared object file),"); pie = true; break; + case 0x04: printf("(core file),"); break; + default: printf("(unknown),"); break; } printf(" "); } else if (header->e_type == 0x03) @@ -190,36 +227,16 @@ void display_elf32(Elf32_Ehdr* header, FILE* fp) switch (header->e_machine) { - case 0x00: - printf("No architecture, "); - break; - case 0x01: - printf("AT&T WE 32100, "); - break; - case 0x02: - printf("SPARC, "); - break; - case 0x03: - printf("i386, "); - break; - case 0x04: - printf("Motorola 68000, "); - break; - case 0x05: - printf("Motorola 88000, "); - break; - case 0x07: - printf("Intel 80860, "); - break; - case 0x08: - printf("MIPS RS3000, "); - break; - case 0x09: - printf("MIPS RS4000, "); - break; - default: - printf("Unknown architecture, "); - break; + case 0x00: printf("No architecture, "); break; + case 0x01: printf("AT&T WE 32100, "); break; + case 0x02: printf("SPARC, "); break; + case 0x03: printf("i386, "); break; + case 0x04: printf("Motorola 68000, "); break; + case 0x05: printf("Motorola 88000, "); break; + case 0x07: printf("Intel 80860, "); break; + case 0x08: printf("MIPS RS3000, "); break; + case 0x09: printf("MIPS RS4000, "); break; + default: printf("Unknown architecture, "); break; } if (verbose) @@ -228,6 +245,47 @@ void display_elf32(Elf32_Ehdr* header, FILE* fp) } } +// Duplicate code.. gotta find a solution to this +// (properly differentiate 32/64b) +void display_elf64(Elf64_Ehdr* header, FILE* fp) +{ + printf("64-bit ELF "); + display_elf_common(header->e_ident); + + if (verbose) + { + switch (header->e_type) + { + case 0x00: printf("(no file type),"); break; + case 0x01: printf("(relocatable file),"); break; + case 0x02: printf("(executable file),"); break; + // (ET_DYN, prob means PIE) + case 0x03: printf("(shared object file),"); pie = true; break; + case 0x04: printf("(core file),"); break; + default: printf("(unknown),"); break; + } + printf(" "); + } else if (header->e_type == 0x03) + { + pie = true; + } + + switch (header->e_machine) + { + // A few only.. full list here (many exotic stuff, might implement it one day) + // https://gist.github.com/x0nu11byt3/bcb35c3de461e5fb66173071a2379779 + case 40: printf("ARM, "); break; + case 21: printf("PowerPC, "); break; + case 62: printf("amd64, "); break; + default: printf("Unknown architecture, "); break; + } + + if (verbose) + { + check_dynamic64(header, fp); + } +} + void check_sec32(Elf32_Ehdr* header, FILE* fp) { /* NX: @@ -410,12 +468,6 @@ void check_sec32(Elf32_Ehdr* header, FILE* fp) free(p_headers); } -void display_elf64(Elf64_Ehdr* header) -{ - printf("64-bit ELF "); - display_elf_common(header->e_ident); -} - unsigned char read_elf_obj_size(FILE* fp) { unsigned char local_elf_obj_size = 0; @@ -497,7 +549,7 @@ int main(int argc, char* argv[]) puts("Failed to parse 64-bit ELF header"); return -EINVAL; } - display_elf64(&elf64_header); + display_elf64(&elf64_header, elf_file); break; default: puts("Invalid ELF object size"); diff --git a/makefile b/makefile index e2b6756..278bd68 100644 --- a/makefile +++ b/makefile @@ -6,7 +6,7 @@ install: test: make - gcc -m32 -fstack-protector -static -Wl,-z,relro,-z,now main.c + gcc -fstack-protector -static -Wl,-z,relro,-z,now main.c ./helpelf a.out clean: