diff options
author | Lisa Hsu <hsul@eecs.umich.edu> | 2008-12-05 12:11:46 -0500 |
---|---|---|
committer | Lisa Hsu <hsul@eecs.umich.edu> | 2008-12-05 12:11:46 -0500 |
commit | 854aa60fdcec2a95d2c08844d62681b498281ca3 (patch) | |
tree | 773ef7b3acb7d6b1da8628217a0441fab9c45af2 /src | |
parent | d6b229ea0f46de3a622ebb1ef86cb526625ebc2e (diff) | |
parent | f1430941cf17fc15a8b86eba41f9c856ad9347d8 (diff) | |
download | gem5-854aa60fdcec2a95d2c08844d62681b498281ca3.tar.xz |
Automated merge with ssh://m5sim.org//repo/m5
Diffstat (limited to 'src')
-rw-r--r-- | src/arch/alpha/linux/process.cc | 2 | ||||
-rw-r--r-- | src/arch/alpha/process.cc | 118 | ||||
-rw-r--r-- | src/arch/alpha/process.hh | 5 | ||||
-rw-r--r-- | src/arch/sparc/process.hh | 20 | ||||
-rw-r--r-- | src/arch/x86/process.cc | 9 | ||||
-rw-r--r-- | src/arch/x86/process.hh | 16 | ||||
-rw-r--r-- | src/base/loader/elf_object.cc | 2 | ||||
-rw-r--r-- | src/sim/process.cc | 15 | ||||
-rw-r--r-- | src/sim/process.hh | 16 |
9 files changed, 152 insertions, 51 deletions
diff --git a/src/arch/alpha/linux/process.cc b/src/arch/alpha/linux/process.cc index efcd6623e..6684051af 100644 --- a/src/arch/alpha/linux/process.cc +++ b/src/arch/alpha/linux/process.cc @@ -52,7 +52,7 @@ unameFunc(SyscallDesc *desc, int callnum, LiveProcess *process, strcpy(name->sysname, "Linux"); strcpy(name->nodename, "m5.eecs.umich.edu"); - strcpy(name->release, "2.4.20"); + strcpy(name->release, "2.6.26"); strcpy(name->version, "#1 Mon Aug 18 11:32:15 EDT 2003"); strcpy(name->machine, "alpha"); diff --git a/src/arch/alpha/process.cc b/src/arch/alpha/process.cc index 28e8df308..3e5851e74 100644 --- a/src/arch/alpha/process.cc +++ b/src/arch/alpha/process.cc @@ -32,8 +32,11 @@ #include "arch/alpha/isa_traits.hh" #include "arch/alpha/process.hh" #include "base/loader/object_file.hh" +#include "base/loader/elf_object.hh" #include "base/misc.hh" #include "cpu/thread_context.hh" +#include "mem/page_table.hh" +#include "sim/process_impl.hh" #include "sim/system.hh" using namespace AlphaISA; @@ -60,11 +63,126 @@ AlphaLiveProcess::AlphaLiveProcess(LiveProcessParams *params, } void +AlphaLiveProcess::argsInit(int intSize, int pageSize) +{ + objFile->loadSections(initVirtMem); + + typedef M5_auxv_t<uint64_t> auxv_t; + std::vector<auxv_t> auxv; + + ElfObject * elfObject = dynamic_cast<ElfObject *>(objFile); + if(elfObject) + { + // modern glibc uses a bunch of auxiliary vectors to set up + // TLS as well as do a bunch of other stuff + // these vectors go on the bottom of the stack, below argc/argv/envp + // pointers but above actual arg strings + // I don't have all the ones glibc looks at here, but so far it doesn't + // seem to be a problem. + // check out _dl_aux_init() in glibc/elf/dl-support.c for details + // --Lisa + auxv.push_back(auxv_t(M5_AT_PAGESZ, AlphaISA::VMPageSize)); + auxv.push_back(auxv_t(M5_AT_CLKTCK, 100)); + auxv.push_back(auxv_t(M5_AT_PHDR, elfObject->programHeaderTable())); + DPRINTF(Loader, "auxv at PHDR %08p\n", elfObject->programHeaderTable()); + auxv.push_back(auxv_t(M5_AT_PHNUM, elfObject->programHeaderCount())); + auxv.push_back(auxv_t(M5_AT_ENTRY, objFile->entryPoint())); + auxv.push_back(auxv_t(M5_AT_UID, uid())); + auxv.push_back(auxv_t(M5_AT_EUID, euid())); + auxv.push_back(auxv_t(M5_AT_GID, gid())); + auxv.push_back(auxv_t(M5_AT_EGID, egid())); + + } + + // Calculate how much space we need for arg & env & auxv arrays. + int argv_array_size = intSize * (argv.size() + 1); + int envp_array_size = intSize * (envp.size() + 1); + int auxv_array_size = intSize * 2 * (auxv.size() + 1); + + int arg_data_size = 0; + for (int i = 0; i < argv.size(); ++i) { + arg_data_size += argv[i].size() + 1; + } + int env_data_size = 0; + for (int i = 0; i < envp.size(); ++i) { + env_data_size += envp[i].size() + 1; + } + + int space_needed = + argv_array_size + + envp_array_size + + auxv_array_size + + arg_data_size + + env_data_size; + + if (space_needed < 32*1024) + space_needed = 32*1024; + + // set bottom of stack + stack_min = stack_base - space_needed; + // align it + stack_min = roundDown(stack_min, pageSize); + stack_size = stack_base - stack_min; + // map memory + pTable->allocate(stack_min, roundUp(stack_size, pageSize)); + + // map out initial stack contents + Addr argv_array_base = stack_min + intSize; // room for argc + Addr envp_array_base = argv_array_base + argv_array_size; + Addr auxv_array_base = envp_array_base + envp_array_size; + Addr arg_data_base = auxv_array_base + auxv_array_size; + Addr env_data_base = arg_data_base + arg_data_size; + + // write contents to stack + uint64_t argc = argv.size(); + if (intSize == 8) + argc = htog((uint64_t)argc); + else if (intSize == 4) + argc = htog((uint32_t)argc); + else + panic("Unknown int size"); + + initVirtMem->writeBlob(stack_min, (uint8_t*)&argc, intSize); + + copyStringArray(argv, argv_array_base, arg_data_base, initVirtMem); + copyStringArray(envp, envp_array_base, env_data_base, initVirtMem); + + //Copy the aux stuff + for(int x = 0; x < auxv.size(); x++) + { + initVirtMem->writeBlob(auxv_array_base + x * 2 * intSize, + (uint8_t*)&(auxv[x].a_type), intSize); + initVirtMem->writeBlob(auxv_array_base + (x * 2 + 1) * intSize, + (uint8_t*)&(auxv[x].a_val), intSize); + } + + assert(NumArgumentRegs >= 2); + + ThreadContext *tc = system->getThreadContext(contextIds[0]); + + tc->setIntReg(ArgumentReg[0], argc); + tc->setIntReg(ArgumentReg[1], argv_array_base); + tc->setIntReg(StackPointerReg, stack_min); + + Addr prog_entry = objFile->entryPoint(); + tc->setPC(prog_entry); + tc->setNextPC(prog_entry + sizeof(MachInst)); + +#if THE_ISA != ALPHA_ISA //e.g. MIPS or Sparc + tc->setNextNPC(prog_entry + (2 * sizeof(MachInst))); +#endif + + +} + +void AlphaLiveProcess::startup() { if (checkpointRestored) return; + Process::startup(); + argsInit(MachineBytes, VMPageSize); ThreadContext *tc = system->getThreadContext(contextIds[0]); diff --git a/src/arch/alpha/process.hh b/src/arch/alpha/process.hh index 0aeeb25db..65c4624ae 100644 --- a/src/arch/alpha/process.hh +++ b/src/arch/alpha/process.hh @@ -34,15 +34,14 @@ #include "sim/process.hh" -class ObjectFile; -class System; - class AlphaLiveProcess : public LiveProcess { protected: AlphaLiveProcess(LiveProcessParams *params, ObjectFile *objFile); void startup(); + + void argsInit(int intSize, int pageSize); }; #endif // __ARCH_ALPHA_PROCESS_HH__ diff --git a/src/arch/sparc/process.hh b/src/arch/sparc/process.hh index a37760139..95abb93d3 100644 --- a/src/arch/sparc/process.hh +++ b/src/arch/sparc/process.hh @@ -71,26 +71,6 @@ class SparcLiveProcess : public LiveProcess virtual void flushWindows(ThreadContext *tc) = 0; }; -template<class IntType> -struct M5_auxv_t -{ - IntType a_type; - union { - IntType a_val; - IntType a_ptr; - IntType a_fcn; - }; - - M5_auxv_t() - {} - - M5_auxv_t(IntType type, IntType val) - { - a_type = SparcISA::htog(type); - a_val = SparcISA::htog(val); - } -}; - class Sparc32LiveProcess : public SparcLiveProcess { protected: diff --git a/src/arch/x86/process.cc b/src/arch/x86/process.cc index 52933b7f4..8d0cd5038 100644 --- a/src/arch/x86/process.cc +++ b/src/arch/x86/process.cc @@ -103,11 +103,6 @@ using namespace std; using namespace X86ISA; -M5_64_auxv_t::M5_64_auxv_t(int64_t type, int64_t val) -{ - a_type = X86ISA::htog(type); - a_val = X86ISA::htog(val); -} X86LiveProcess::X86LiveProcess(LiveProcessParams * params, ObjectFile *objFile) @@ -205,7 +200,9 @@ X86LiveProcess::startup() void X86LiveProcess::argsInit(int intSize, int pageSize) { - typedef M5_64_auxv_t auxv_t; + typedef M5_auxv_t<uint64_t> auxv_t; + std::vector<auxv_t> auxv; + Process::startup(); string filename; diff --git a/src/arch/x86/process.hh b/src/arch/x86/process.hh index 5def9e13d..d034d990e 100644 --- a/src/arch/x86/process.hh +++ b/src/arch/x86/process.hh @@ -64,26 +64,10 @@ namespace X86ISA { - struct M5_64_auxv_t - { - int64_t a_type; - union { - int64_t a_val; - int64_t a_ptr; - int64_t a_fcn; - }; - - M5_64_auxv_t() - {} - - M5_64_auxv_t(int64_t type, int64_t val); - }; class X86LiveProcess : public LiveProcess { protected: - std::vector<M5_64_auxv_t> auxv; - X86LiveProcess(LiveProcessParams * params, ObjectFile *objFile); void startup(); diff --git a/src/base/loader/elf_object.cc b/src/base/loader/elf_object.cc index f71c4456b..edaf323c7 100644 --- a/src/base/loader/elf_object.cc +++ b/src/base/loader/elf_object.cc @@ -291,6 +291,8 @@ ElfObject::ElfObject(const string &_filename, int _fd, data.size = phdr.p_filesz; data.fileImage = fileData + phdr.p_offset; } else { + // If it's none of the above but is loadable, + // load the filesize worth of data Segment extra; extra.baseAddr = phdr.p_paddr; extra.size = phdr.p_filesz; diff --git a/src/sim/process.cc b/src/sim/process.cc index dab374d84..244fb9297 100644 --- a/src/sim/process.cc +++ b/src/sim/process.cc @@ -86,6 +86,16 @@ using namespace TheISA; // current number of allocated processes int num_processes = 0; +template<class IntType> +M5_auxv_t<IntType>::M5_auxv_t(IntType type, IntType val) +{ + a_type = TheISA::htog(type); + a_val = TheISA::htog(val); +} + +template class M5_auxv_t<uint32_t>; +template class M5_auxv_t<uint64_t>; + Process::Process(ProcessParams * params) : SimObject(params), system(params->system), checkpointRestored(false), max_stack_size(params->max_stack_size) @@ -658,11 +668,6 @@ LiveProcess::create(LiveProcessParams * params) if (objFile->getArch() != ObjectFile::Alpha) fatal("Object file architecture does not match compiled ISA (Alpha)."); - if (objFile->hasTLS()) - fatal("Object file has a TLS section and single threaded TLS is not\n" - " currently supported for Alpha! Please recompile your " - "executable with \n a non-TLS toolchain.\n"); - switch (objFile->getOpSys()) { case ObjectFile::Tru64: process = new AlphaTru64Process(params, objFile); diff --git a/src/sim/process.hh b/src/sim/process.hh index d6ed59ced..996663847 100644 --- a/src/sim/process.hh +++ b/src/sim/process.hh @@ -61,6 +61,22 @@ namespace TheISA class RemoteGDB; } +template<class IntType> +struct M5_auxv_t +{ + IntType a_type; + union { + IntType a_val; + IntType a_ptr; + IntType a_fcn; + }; + + M5_auxv_t() + {} + + M5_auxv_t(IntType type, IntType val); +}; + class Process : public SimObject { public: |