int elf_checkFile(void *elfFile) { return ISELF32 (elfFile) ? elf32_checkFile(elfFile) : elf64_checkFile(elfFile); }
static void load_image(void** entry) { char* start = mod_dite_start; char* end = mod_dite_end; if(start == end) { printf("elf-loader: error, dite image is empty!\n"); abort(); } /* awiggins (2004-12-21): Should probably add an alignment check? */ /** awiggins (2005-05-29): Probably should add checks to see * the correct kind of elf file is being loaded for the platform, * or does the elf library do that somewhere?. */ if(!elf32_checkFile((struct Elf32_Header*)start)) { *entry = (void*)(uintptr_t)elf32_getEntryPoint((struct Elf32_Header*)start); } else if(!elf64_checkFile((struct Elf64_Header*)start)) { *entry = (void*)(uintptr_t)elf64_getEntryPoint((struct Elf64_Header*)start); } else { printf("elf-loader: error, dite image not a valid elf file!\n"); abort(); } #ifdef __PPC64__ if (arch_claim_memory((struct Elf32_Header*)start)) { printf("could not claim memory for elf file!\n"); abort(); } #endif if(!elf_loadFile(start, 1)) { printf("elf-loader: error, unable to load dite image!\n"); abort(); } }
/* * prints out some details of one elf file */ void elf32_fprintf(FILE *f, struct Elf32_Header *file, int size, const char *name, int flags) { struct Elf32_Phdr *segments; unsigned numSegments; struct Elf32_Shdr *sections; unsigned numSections; int i, r; char *str_table; fprintf(f, "Found an elf32 file called \"%s\" located " "at address 0x%p\n", name, file); if ((r = elf32_checkFile(file)) != 0) { char *magic = (char*) file; fprintf(f, "Invalid elf file (%d)\n", r); fprintf(f, "Magic is: %2.2hhx %2.2hhx %2.2hhx %2.2hhx\n", magic[0], magic[1], magic[2], magic[3]); return; } /* * get a pointer to the table of program segments */ segments = elf32_getProgramHeaderTable(file); numSegments = elf32_getNumProgramHeaders(file); sections = elf32_getSectionTable(file); numSections = elf32_getNumSections(file); if ((uintptr_t) sections > ((uintptr_t) file + size)) { fprintf(f, "Corrupted elfFile..\n"); return; } /* * print out info about each section */ if (flags & ELF_PRINT_PROGRAM_HEADERS) { /* * print out info about each program segment */ fprintf(f, "Program Headers:\n"); fprintf(f, " Type Offset VirtAddr PhysAddr " "FileSiz MemSiz Flg Align\n"); for (i = 0; i < numSegments; i++) { if (segments[i].p_type != 1) { fprintf(f, "segment %d is not loadable, " "skipping\n", i); } else { fprintf(f, " LOAD 0x%06" PRIx32 " 0x%08" PRIx32 " 0x%08" PRIx32 \ " 0x%05" PRIx32" 0x%05" PRIx32 " %c%c%c 0x%04" PRIx32 "\n", //fprintf(f, " LOAD 0x%" PRIxPTR " 0x%" PRIxPTR " 0x%" PRIxPTR // " 0x%" PRIxPTR" 0x%" PRIxPTR " %c%c%c 0x%" PRIxPTR "\n", segments[i].p_offset, segments[i].p_vaddr, segments[i].p_paddr, segments[i].p_filesz, segments[i].p_memsz, segments[i].p_flags & PF_R ? 'R' : ' ', segments[i].p_flags & PF_W ? 'W' : ' ', segments[i].p_flags & PF_X ? 'E' : ' ', segments[i].p_align); } } } if (flags & ELF_PRINT_SECTIONS) { str_table = elf32_getSegmentStringTable(file); printf("Section Headers:\n"); printf(" [Nr] Name Type Addr Off\n"); for (i = 0; i < numSections; i++) { //if (elf_checkSection(file, i) == 0) { fprintf(f, "[%2d] %s %lx %lx\n", i, elf32_getSectionName(file, i), //fprintf(f, "[%2d] %-17.17s %-15.15s %x %x\n", i, elf32_getSectionName(file, i), " ", ///fprintf(f, "%-17.17s %-15.15s %08x %06x\n", elf32_getSectionName(file, i), " " /* sections[i].sh_type // */ , sections[i].sh_addr, sections[i].sh_offset); //} } } }
BOOT_CODE static paddr_t load_boot_module(node_id_t node, multiboot_module_t* boot_module, paddr_t load_paddr) { Elf32_Header_t* elf_file = (Elf32_Header_t*)boot_module->start; v_region_t v_reg; if (!elf32_checkFile(elf_file)) { printf("Boot module does not contain a valid ELF32 image\n"); return 0; } v_reg = elf32_getMemoryBounds(elf_file); if (v_reg.end == 0) { printf("ELF32 image in boot module does not contain any segments\n"); return 0; } v_reg.end = ROUND_UP(v_reg.end, PAGE_BITS); printf("size=0x%x v_entry=0x%x v_start=0x%x v_end=0x%x ", v_reg.end - v_reg.start, elf_file->e_entry, v_reg.start, v_reg.end ); if (!IS_ALIGNED(v_reg.start, PAGE_BITS)) { printf("Userland image virtual start address must be 4KB-aligned\n"); return 0; } if (v_reg.end + 2 * BIT(PAGE_BITS) > PPTR_USER_TOP) { /* for IPC buffer frame and bootinfo frame, need 2*4K of additional userland virtual memory */ printf("Userland image virtual end address too high\n"); return 0; } if ((elf_file->e_entry < v_reg.start) || (elf_file->e_entry >= v_reg.end)) { printf("Userland image entry point does not lie within userland image\n"); return 0; } /* fill ui_info struct */ glks.ui_info_list[node].pv_offset = load_paddr - v_reg.start; glks.ui_info_list[node].p_reg.start = load_paddr; load_paddr += v_reg.end - v_reg.start; glks.ui_info_list[node].p_reg.end = load_paddr; glks.ui_info_list[node].v_entry = elf_file->e_entry; printf("p_start=0x%x p_end=0x%x\n", glks.ui_info_list[node].p_reg.start, glks.ui_info_list[node].p_reg.end ); if (load_paddr > glks.avail_p_reg.end) { printf("End of loaded userland image lies outside of usable physical memory\n"); return 0; } /* initialise all initial userland memory and load potentially sparse ELF image */ memzero( (void*)glks.ui_info_list[node].p_reg.start, glks.ui_info_list[node].p_reg.end - glks.ui_info_list[node].p_reg.start ); elf32_load(elf_file, glks.ui_info_list[node].pv_offset); return load_paddr; }