ecoff_object.cc revision 2420
15882Snate@binkert.org/* 25882Snate@binkert.org * Copyright (c) 2003-2005 The Regents of The University of Michigan 35882Snate@binkert.org * All rights reserved. 45882Snate@binkert.org * 55882Snate@binkert.org * Redistribution and use in source and binary forms, with or without 65882Snate@binkert.org * modification, are permitted provided that the following conditions are 75882Snate@binkert.org * met: redistributions of source code must retain the above copyright 85882Snate@binkert.org * notice, this list of conditions and the following disclaimer; 95882Snate@binkert.org * redistributions in binary form must reproduce the above copyright 105882Snate@binkert.org * notice, this list of conditions and the following disclaimer in the 115882Snate@binkert.org * documentation and/or other materials provided with the distribution; 125882Snate@binkert.org * neither the name of the copyright holders nor the names of its 135882Snate@binkert.org * contributors may be used to endorse or promote products derived from 145882Snate@binkert.org * this software without specific prior written permission. 155882Snate@binkert.org * 165882Snate@binkert.org * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 175882Snate@binkert.org * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 185882Snate@binkert.org * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 195882Snate@binkert.org * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 205882Snate@binkert.org * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 215882Snate@binkert.org * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 225882Snate@binkert.org * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 235882Snate@binkert.org * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 245882Snate@binkert.org * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 255882Snate@binkert.org * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 265882Snate@binkert.org * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 275882Snate@binkert.org */ 285882Snate@binkert.org 295882Snate@binkert.org#include <string> 305882Snate@binkert.org 315882Snate@binkert.org#include "base/loader/ecoff_object.hh" 325882Snate@binkert.org#include "base/loader/symtab.hh" 335882Snate@binkert.org 348232Snate@binkert.org#include "base/trace.hh" // for DPRINTF 358229Snate@binkert.org 368232Snate@binkert.org#include "base/loader/exec_ecoff.h" 378232Snate@binkert.org#include "base/loader/coff_sym.h" 388229Snate@binkert.org#include "base/loader/coff_symconst.h" 395882Snate@binkert.org 408232Snate@binkert.orgusing namespace std; 418232Snate@binkert.org 428232Snate@binkert.orgObjectFile * 438232Snate@binkert.orgEcoffObject::tryFile(const string &fname, int fd, size_t len, uint8_t *data) 445882Snate@binkert.org{ 458231Snate@binkert.org if (((ecoff_filehdr *)data)->f_magic == ECOFF_MAGIC_ALPHA) { 468231Snate@binkert.org // it's Alpha ECOFF 478232Snate@binkert.org return new EcoffObject(fname, fd, len, data, 488232Snate@binkert.org ObjectFile::Alpha, ObjectFile::Tru64); 498232Snate@binkert.org } 508232Snate@binkert.org else { 518232Snate@binkert.org return NULL; 525882Snate@binkert.org } 538231Snate@binkert.org} 545882Snate@binkert.org 555882Snate@binkert.org 565882Snate@binkert.orgEcoffObject::EcoffObject(const string &_filename, int _fd, 575882Snate@binkert.org size_t _len, uint8_t *_data, 588231Snate@binkert.org Arch _arch, OpSys _opSys) 595882Snate@binkert.org : ObjectFile(_filename, _fd, _len, _data, _arch, _opSys) 605882Snate@binkert.org{ 618231Snate@binkert.org execHdr = (ecoff_exechdr *)fileData; 628232Snate@binkert.org fileHdr = &(execHdr->f); 638232Snate@binkert.org aoutHdr = &(execHdr->a); 648232Snate@binkert.org 658232Snate@binkert.org entry = aoutHdr->entry; 668232Snate@binkert.org 678232Snate@binkert.org text.baseAddr = aoutHdr->text_start; 688232Snate@binkert.org text.size = aoutHdr->tsize; 698232Snate@binkert.org text.fileImage = fileData + ECOFF_TXTOFF(execHdr); 708232Snate@binkert.org 718232Snate@binkert.org data.baseAddr = aoutHdr->data_start; 728232Snate@binkert.org data.size = aoutHdr->dsize; 738232Snate@binkert.org data.fileImage = fileData + ECOFF_DATOFF(execHdr); 748232Snate@binkert.org 758232Snate@binkert.org bss.baseAddr = aoutHdr->bss_start; 768232Snate@binkert.org bss.size = aoutHdr->bsize; 778232Snate@binkert.org bss.fileImage = NULL; 788232Snate@binkert.org 798232Snate@binkert.org DPRINTFR(Loader, "text: 0x%x %d\ndata: 0x%x %d\nbss: 0x%x %d\n", 808232Snate@binkert.org text.baseAddr, text.size, data.baseAddr, data.size, 818232Snate@binkert.org bss.baseAddr, bss.size); 828232Snate@binkert.org} 838232Snate@binkert.org 848232Snate@binkert.org 858232Snate@binkert.orgbool 868232Snate@binkert.orgEcoffObject::loadGlobalSymbols(SymbolTable *symtab) 878232Snate@binkert.org{ 888232Snate@binkert.org if (!symtab) 898232Snate@binkert.org return false; 908232Snate@binkert.org 918232Snate@binkert.org if (fileHdr->f_magic != ECOFF_MAGIC_ALPHA) { 928232Snate@binkert.org warn("loadGlobalSymbols: wrong magic on %s\n", filename); 938232Snate@binkert.org return false; 948232Snate@binkert.org } 958232Snate@binkert.org 968232Snate@binkert.org ecoff_symhdr *syms = (ecoff_symhdr *)(fileData + fileHdr->f_symptr); 978232Snate@binkert.org if (syms->magic != magicSym2) { 988232Snate@binkert.org warn("loadGlobalSymbols: bad symbol header magic on %s\n", filename); 998232Snate@binkert.org return false; 1008232Snate@binkert.org } 1018232Snate@binkert.org 1028232Snate@binkert.org ecoff_extsym *ext_syms = (ecoff_extsym *)(fileData + syms->cbExtOffset); 1038232Snate@binkert.org 1048232Snate@binkert.org char *ext_strings = (char *)(fileData + syms->cbSsExtOffset); 1058232Snate@binkert.org for (int i = 0; i < syms->iextMax; i++) { 1068232Snate@binkert.org ecoff_sym *entry = &(ext_syms[i].asym); 1078232Snate@binkert.org if (entry->iss != -1) 1088232Snate@binkert.org symtab->insert(entry->value, ext_strings + entry->iss); 1098232Snate@binkert.org } 1108232Snate@binkert.org 1118232Snate@binkert.org return true; 1128232Snate@binkert.org} 1138232Snate@binkert.org 1148232Snate@binkert.orgbool 1158232Snate@binkert.orgEcoffObject::loadLocalSymbols(SymbolTable *symtab) 1168232Snate@binkert.org{ 1178232Snate@binkert.org if (!symtab) 1188232Snate@binkert.org return false; 1198232Snate@binkert.org 1208232Snate@binkert.org if (fileHdr->f_magic != ECOFF_MAGIC_ALPHA) { 1218232Snate@binkert.org warn("loadGlobalSymbols: wrong magic on %s\n", filename); 1228232Snate@binkert.org return false; 1238232Snate@binkert.org } 1248232Snate@binkert.org 1258232Snate@binkert.org ecoff_symhdr *syms = (ecoff_symhdr *)(fileData + fileHdr->f_symptr); 1268232Snate@binkert.org if (syms->magic != magicSym2) { 1278232Snate@binkert.org warn("loadGlobalSymbols: bad symbol header magic on %s\n", filename); 1288232Snate@binkert.org return false; 1298232Snate@binkert.org } 1308232Snate@binkert.org 1318232Snate@binkert.org ecoff_sym *local_syms = (ecoff_sym *)(fileData + syms->cbSymOffset); 1328232Snate@binkert.org char *local_strings = (char *)(fileData + syms->cbSsOffset); 1338232Snate@binkert.org ecoff_fdr *fdesc = (ecoff_fdr *)(fileData + syms->cbFdOffset); 1348232Snate@binkert.org 1358232Snate@binkert.org for (int i = 0; i < syms->ifdMax; i++) { 1368232Snate@binkert.org ecoff_sym *entry = (ecoff_sym *)(local_syms + fdesc[i].isymBase); 1378232Snate@binkert.org char *strings = (char *)(local_strings + fdesc[i].issBase); 1388232Snate@binkert.org for (int j = 0; j < fdesc[i].csym; j++) { 1398232Snate@binkert.org if (entry[j].st == stGlobal || entry[j].st == stProc) 1408232Snate@binkert.org if (entry[j].iss != -1) 1418232Snate@binkert.org symtab->insert(entry[j].value, strings + entry[j].iss); 1428232Snate@binkert.org } 1438232Snate@binkert.org } 1448232Snate@binkert.org 1458232Snate@binkert.org for (int i = 0; i < syms->isymMax; i++) { 1468232Snate@binkert.org ecoff_sym *entry = &(local_syms[i]); 1478232Snate@binkert.org if (entry->st == stProc) 1488232Snate@binkert.org symtab->insert(entry->value, local_strings + entry->iss); 1498232Snate@binkert.org } 1508232Snate@binkert.org 1518232Snate@binkert.org return true; 1528232Snate@binkert.org} 1538232Snate@binkert.org