From 25f68b08ab8c1fc35aab2d060b0f38ebf7856785 Mon Sep 17 00:00:00 2001 From: Marcus Comstedt Date: Fri, 30 Jun 2006 20:21:42 +0000 Subject: Moved backends/dc into new platform directory. svn-id: r23357 --- backends/dc/dcloader.cpp | 441 ----------------------------------------------- 1 file changed, 441 deletions(-) delete mode 100644 backends/dc/dcloader.cpp (limited to 'backends/dc/dcloader.cpp') diff --git a/backends/dc/dcloader.cpp b/backends/dc/dcloader.cpp deleted file mode 100644 index 2ce853c061..0000000000 --- a/backends/dc/dcloader.cpp +++ /dev/null @@ -1,441 +0,0 @@ -/* ScummVM - Scumm Interpreter - * Dreamcast port - * Copyright (C) 2002-2004 Marcus Comstedt - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License - * as published by the Free Software Foundation; either version 2 - * of the License, or (at your option) any later version. - - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. - * - * $URL$ - * $Id$ - * - */ - -#include -#include -#include -#include - -#include "dcloader.h" - -#ifdef DL_DEBUG -#define DBG(...) reportf(__VA_ARGS__) -#else -#define DBG(...) 0 -#endif - - -/* ELF stuff */ - -typedef unsigned short Elf32_Half, Elf32_Section; -typedef unsigned long Elf32_Word, Elf32_Addr, Elf32_Off; -typedef signed long Elf32_Sword; -typedef Elf32_Half Elf32_Versym; - -#define EI_NIDENT (16) -#define ELFMAG "\177ELF\1\1" -#define SELFMAG 6 - -typedef struct -{ - unsigned char e_ident[EI_NIDENT]; /* Magic number and other info */ - Elf32_Half e_type; /* Object file type */ - Elf32_Half e_machine; /* Architecture */ - Elf32_Word e_version; /* Object file version */ - Elf32_Addr e_entry; /* Entry point virtual address */ - Elf32_Off e_phoff; /* Program header table file offset */ - Elf32_Off e_shoff; /* Section header table file offset */ - Elf32_Word e_flags; /* Processor-specific flags */ - Elf32_Half e_ehsize; /* ELF header size in bytes */ - Elf32_Half e_phentsize; /* Program header table entry size */ - Elf32_Half e_phnum; /* Program header table entry count */ - Elf32_Half e_shentsize; /* Section header table entry size */ - Elf32_Half e_shnum; /* Section header table entry count */ - Elf32_Half e_shstrndx; /* Section header string table index */ -} Elf32_Ehdr; - -typedef struct -{ - Elf32_Word p_type; /* Segment type */ - Elf32_Off p_offset; /* Segment file offset */ - Elf32_Addr p_vaddr; /* Segment virtual address */ - Elf32_Addr p_paddr; /* Segment physical address */ - Elf32_Word p_filesz; /* Segment size in file */ - Elf32_Word p_memsz; /* Segment size in memory */ - Elf32_Word p_flags; /* Segment flags */ - Elf32_Word p_align; /* Segment alignment */ -} Elf32_Phdr; - -typedef struct -{ - Elf32_Word sh_name; /* Section name (string tbl index) */ - Elf32_Word sh_type; /* Section type */ - Elf32_Word sh_flags; /* Section flags */ - Elf32_Addr sh_addr; /* Section virtual addr at execution */ - Elf32_Off sh_offset; /* Section file offset */ - Elf32_Word sh_size; /* Section size in bytes */ - Elf32_Word sh_link; /* Link to another section */ - Elf32_Word sh_info; /* Additional section information */ - Elf32_Word sh_addralign; /* Section alignment */ - Elf32_Word sh_entsize; /* Entry size if section holds table */ -} Elf32_Shdr; - -typedef struct -{ - Elf32_Word st_name; /* Symbol name (string tbl index) */ - Elf32_Addr st_value; /* Symbol value */ - Elf32_Word st_size; /* Symbol size */ - unsigned char st_info; /* Symbol type and binding */ - unsigned char st_other; /* Symbol visibility */ - Elf32_Section st_shndx; /* Section index */ -} Elf32_Sym; - -typedef struct -{ - Elf32_Addr r_offset; /* Address */ - Elf32_Word r_info; /* Relocation type and symbol index */ - Elf32_Sword r_addend; /* Addend */ -} Elf32_Rela; - - - -extern "C" void flush_instruction_cache(); - -static void purge_copyback() -{ - int i; - for(i=0; i!=(1<<14); i+=(1<<5)) - *(volatile unsigned int *)(0xf4000000+i) &= ~3; -} - - -void DLObject::seterror(const char *fmt, ...) -{ - if(errbuf) { - va_list va; - va_start(va, fmt); - vsnprintf(errbuf, MAXDLERRLEN, fmt, va); - va_end(va); - } -} - -void DLObject::discard_symtab() -{ - free(symtab); - free(strtab); - symtab = NULL; - strtab = NULL; - symbol_cnt = 0; -} - -void DLObject::unload() -{ - discard_symtab(); - free(segment); - segment = NULL; -} - -bool DLObject::relocate(int fd, unsigned long offset, unsigned long size) -{ - Elf32_Rela *rela; - - if(!(rela = (Elf32_Rela *)malloc(size))) { - seterror("Out of memory."); - return false; - } - - if(lseek(fd, offset, SEEK_SET)<0 || - read(fd, rela, size) != size) { - seterror("Relocation table load failed."); - free(rela); - return false; - } - - int cnt = size / sizeof(*rela); - for(int i=0; i>4)); - - void *target = ((char *)segment)+rela[i].r_offset; - - switch(rela[i].r_info & 0xf) { - case 1: /* DIR32 */ - if(sym->st_shndx < 0xff00) - *(unsigned long *)target += (unsigned long)segment; - break; - default: - seterror("Unknown relocation type %d.", rela[i].r_info & 0xf); - free(rela); - return false; - } - - } - - free(rela); - return true; -} - - -bool DLObject::load(int fd) -{ - Elf32_Ehdr ehdr; - Elf32_Phdr phdr; - Elf32_Shdr *shdr; - int symtab_sect = -1; - - if(read(fd, &ehdr, sizeof(ehdr)) != sizeof(ehdr) || - memcmp(ehdr.e_ident, ELFMAG, SELFMAG) || - ehdr.e_type != 2 || ehdr.e_machine != 42 || - ehdr.e_phentsize < sizeof(phdr) || ehdr.e_shentsize != sizeof(*shdr) || - ehdr.e_phnum != 1) { - seterror("Invalid file type."); - return false; - } - - DBG("phoff = %d, phentsz = %d, phnum = %d\n", - ehdr.e_phoff, ehdr.e_phentsize, ehdr.e_phnum); - - if(lseek(fd, ehdr.e_phoff, SEEK_SET)<0 || - read(fd, &phdr, sizeof(phdr)) != sizeof(phdr)) { - seterror("Program header load failed."); - return false; - } - - if(phdr.p_type != 1 || phdr.p_vaddr != 0 || phdr.p_paddr != 0 || - phdr.p_filesz > phdr.p_memsz) { - seterror("Invalid program header."); - return false; - } - - DBG("offs = %d, filesz = %d, memsz = %d, align = %d\n", - phdr.p_offset, phdr.p_filesz, phdr.p_memsz, phdr.p_align); - - if(!(segment = memalign(phdr.p_align, phdr.p_memsz))) { - seterror("Out of memory."); - return false; - } - - DBG("segment @ %p\n", segment); - - if(phdr.p_memsz > phdr.p_filesz) - memset(((char *)segment) + phdr.p_filesz, 0, phdr.p_memsz - phdr.p_filesz); - - if(lseek(fd, phdr.p_offset, SEEK_SET)<0 || - read(fd, segment, phdr.p_filesz) != phdr.p_filesz) { - seterror("Segment load failed."); - return false; - } - - DBG("shoff = %d, shentsz = %d, shnum = %d\n", - ehdr.e_shoff, ehdr.e_shentsize, ehdr.e_shnum); - - if(!(shdr = (Elf32_Shdr *)malloc(ehdr.e_shnum * sizeof(*shdr)))) { - seterror("Out of memory."); - return false; - } - - if(lseek(fd, ehdr.e_shoff, SEEK_SET)<0 || - read(fd, shdr, ehdr.e_shnum * sizeof(*shdr)) != - ehdr.e_shnum * sizeof(*shdr)) { - seterror("Section headers load failed."); - free(shdr); - return false; - } - - for(int i=0; ist_shndx < 0xff00) - s->st_value += (Elf32_Addr)segment; - - for(int i=0; ist_info>>4 == 1 || s->st_info>>4 == 2) && - strtab[s->st_name] == '_' && !strcmp(name, strtab+s->st_name+1)) { - DBG("=> %p\n", (void*)s->st_value); - return (void*)s->st_value; - } - - seterror("Symbol \"%s\" not found.", name); - return NULL; -} - - -static char dlerr[MAXDLERRLEN]; - -void *dlopen(const char *filename, int flags) -{ - DLObject *obj = new DLObject(dlerr); - if(obj->open(filename)) - return (void *)obj; - delete obj; - return NULL; -} - -int dlclose(void *handle) -{ - DLObject *obj = (DLObject *)handle; - if(obj == NULL) { - strcpy(dlerr, "Handle is NULL."); - return -1; - } - if(obj->close()) { - delete obj; - return 0; - } - return -1; -} - -void *dlsym(void *handle, const char *symbol) -{ - if(handle == NULL) { - strcpy(dlerr, "Handle is NULL."); - return NULL; - } - return ((DLObject *)handle)->symbol(symbol); -} - -const char *dlerror() -{ - return dlerr; -} - -void dlforgetsyms(void *handle) -{ - if(handle != NULL) - ((DLObject *)handle)->discard_symtab(); -} -- cgit v1.2.3