summaryrefslogtreecommitdiff
path: root/src/sim
diff options
context:
space:
mode:
Diffstat (limited to 'src/sim')
-rw-r--r--src/sim/System.py5
-rw-r--r--src/sim/arguments.cc5
-rw-r--r--src/sim/eventq.hh2
-rw-r--r--src/sim/process.cc28
-rw-r--r--src/sim/process.hh12
-rw-r--r--src/sim/pseudo_inst.cc4
-rw-r--r--src/sim/syscall_emul.cc215
-rw-r--r--src/sim/syscall_emul.hh238
-rw-r--r--src/sim/system.cc3
-rw-r--r--src/sim/system.hh8
10 files changed, 379 insertions, 141 deletions
diff --git a/src/sim/System.py b/src/sim/System.py
index 3b0bc1e46..06a54a78d 100644
--- a/src/sim/System.py
+++ b/src/sim/System.py
@@ -27,9 +27,10 @@
# Authors: Nathan Binkert
from m5.SimObject import SimObject
+from m5.defines import buildEnv
from m5.params import *
from m5.proxy import *
-from m5 import build_env
+
from PhysicalMemory import *
class MemoryMode(Enum): vals = ['invalid', 'atomic', 'timing']
@@ -40,7 +41,7 @@ class System(SimObject):
physmem = Param.PhysicalMemory(Parent.any, "physical memory")
mem_mode = Param.MemoryMode('atomic', "The mode the memory system is in")
- if build_env['FULL_SYSTEM']:
+ if buildEnv['FULL_SYSTEM']:
abstract = True
boot_cpu_frequency = Param.Frequency(Self.cpu[0].clock.frequency,
"boot processor frequency")
diff --git a/src/sim/arguments.cc b/src/sim/arguments.cc
index 5aa57755a..339a57f90 100644
--- a/src/sim/arguments.cc
+++ b/src/sim/arguments.cc
@@ -28,11 +28,10 @@
* Authors: Nathan Binkert
*/
-#include "sim/arguments.hh"
#include "arch/utility.hh"
+#include "config/the_isa.hh"
#include "cpu/thread_context.hh"
-
-using namespace TheISA;
+#include "sim/arguments.hh"
Arguments::Data::~Data()
{
diff --git a/src/sim/eventq.hh b/src/sim/eventq.hh
index 29efdeb6f..92c38142c 100644
--- a/src/sim/eventq.hh
+++ b/src/sim/eventq.hh
@@ -471,7 +471,7 @@ class EventWrapper : public Event
inline void
EventQueue::schedule(Event *event, Tick when)
{
- assert(when >= curTick);
+ assert((UTick)when >= (UTick)curTick);
assert(!event->scheduled());
#ifdef EVENTQ_DEBUG
assert((event->flags & Event::Initialized) == Event::Initialized);
diff --git a/src/sim/process.cc b/src/sim/process.cc
index 55bd2f209..343d2ad5a 100644
--- a/src/sim/process.cc
+++ b/src/sim/process.cc
@@ -32,6 +32,8 @@
#include <unistd.h>
#include <fcntl.h>
+
+#include <cstdio>
#include <string>
#include "arch/remote_gdb.hh"
@@ -40,6 +42,7 @@
#include "base/loader/symtab.hh"
#include "base/statistics.hh"
#include "config/full_system.hh"
+#include "config/the_isa.hh"
#include "cpu/thread_context.hh"
#include "mem/page_table.hh"
#include "mem/physical.hh"
@@ -53,7 +56,6 @@
#include "sim/syscall_emul.hh"
#include "sim/system.hh"
-#include "arch/isa_specific.hh"
#if THE_ISA == ALPHA_ISA
#include "arch/alpha/linux/process.hh"
#include "arch/alpha/tru64/process.hh"
@@ -66,6 +68,8 @@
#include "arch/arm/linux/process.hh"
#elif THE_ISA == X86_ISA
#include "arch/x86/linux/process.hh"
+#elif THE_ISA == POWER_ISA
+#include "arch/power/linux/process.hh"
#else
#error "THE_ISA not set"
#endif
@@ -626,7 +630,7 @@ LiveProcess::argsInit(int intSize, int pageSize)
tc->setPC(prog_entry);
tc->setNextPC(prog_entry + sizeof(MachInst));
-#if THE_ISA != ALPHA_ISA //e.g. MIPS or Sparc
+#if THE_ISA != ALPHA_ISA && THE_ISA != POWER_ISA //e.g. MIPS or Sparc
tc->setNextNPC(prog_entry + (2 * sizeof(MachInst)));
#endif
@@ -645,6 +649,12 @@ LiveProcess::syscall(int64_t callnum, ThreadContext *tc)
desc->doSyscall(callnum, this, tc);
}
+IntReg
+LiveProcess::getSyscallArg(ThreadContext *tc, int &i, int width)
+{
+ return getSyscallArg(tc, i);
+}
+
LiveProcess *
LiveProcess::create(LiveProcessParams * params)
{
@@ -754,6 +764,20 @@ LiveProcess::create(LiveProcessParams * params)
default:
fatal("Unknown/unsupported operating system.");
}
+#elif THE_ISA == POWER_ISA
+ if (objFile->getArch() != ObjectFile::Power)
+ fatal("Object file architecture does not match compiled ISA (Power).");
+ switch (objFile->getOpSys()) {
+ case ObjectFile::UnknownOpSys:
+ warn("Unknown operating system; assuming Linux.");
+ // fall through
+ case ObjectFile::Linux:
+ process = new PowerLinuxProcess(params, objFile);
+ break;
+
+ default:
+ fatal("Unknown/unsupported operating system.");
+ }
#else
#error "THE_ISA not set"
#endif
diff --git a/src/sim/process.hh b/src/sim/process.hh
index 05a48071a..ab9d64cf3 100644
--- a/src/sim/process.hh
+++ b/src/sim/process.hh
@@ -47,9 +47,11 @@
#include "arch/registers.hh"
#include "base/statistics.hh"
#include "base/types.hh"
+#include "config/the_isa.hh"
#include "sim/sim_object.hh"
#include "sim/syscallreturn.hh"
+class BaseRemoteGDB;
class GDBListener;
class PageTable;
class ProcessParams;
@@ -58,10 +60,6 @@ class SyscallDesc;
class System;
class ThreadContext;
class TranslatingPort;
-namespace TheISA
-{
- class RemoteGDB;
-}
template<class IntType>
struct AuxVector
@@ -94,7 +92,7 @@ class Process : public SimObject
std::vector<int> contextIds;
// remote gdb objects
- std::vector<TheISA::RemoteGDB *> remoteGDB;
+ std::vector<BaseRemoteGDB *> remoteGDB;
std::vector<GDBListener *> gdbListen;
bool breakpoint();
@@ -327,7 +325,9 @@ class LiveProcess : public Process
std::string getcwd() const { return cwd; }
virtual void syscall(int64_t callnum, ThreadContext *tc);
- virtual TheISA::IntReg getSyscallArg(ThreadContext *tc, int i) = 0;
+
+ virtual TheISA::IntReg getSyscallArg(ThreadContext *tc, int &i) = 0;
+ virtual TheISA::IntReg getSyscallArg(ThreadContext *tc, int &i, int width);
virtual void setSyscallArg(ThreadContext *tc,
int i, TheISA::IntReg val) = 0;
virtual void setSyscallReturn(ThreadContext *tc,
diff --git a/src/sim/pseudo_inst.cc b/src/sim/pseudo_inst.cc
index 6182150d4..cf063818b 100644
--- a/src/sim/pseudo_inst.cc
+++ b/src/sim/pseudo_inst.cc
@@ -35,10 +35,10 @@
#include <fstream>
#include <string>
-#include "config/full_system.hh"
-
#include "arch/vtophys.hh"
#include "base/debug.hh"
+#include "config/full_system.hh"
+#include "config/the_isa.hh"
#include "cpu/base.hh"
#include "cpu/thread_context.hh"
#include "cpu/quiesce_event.hh"
diff --git a/src/sim/syscall_emul.cc b/src/sim/syscall_emul.cc
index 811bdb73a..4726decc5 100644
--- a/src/sim/syscall_emul.cc
+++ b/src/sim/syscall_emul.cc
@@ -32,18 +32,19 @@
#include <fcntl.h>
#include <unistd.h>
-#include <string>
+#include <cstdio>
#include <iostream>
+#include <string>
#include "sim/syscall_emul.hh"
#include "base/chunk_generator.hh"
#include "base/trace.hh"
+#include "config/the_isa.hh"
#include "cpu/thread_context.hh"
#include "cpu/base.hh"
#include "mem/page_table.hh"
#include "sim/process.hh"
#include "sim/system.hh"
-
#include "sim/sim_exit.hh"
using namespace std;
@@ -52,11 +53,16 @@ using namespace TheISA;
void
SyscallDesc::doSyscall(int callnum, LiveProcess *process, ThreadContext *tc)
{
+#if TRACING_ON
+ int index = 0;
+#endif
DPRINTFR(SyscallVerbose,
"%d: %s: syscall %s called w/arguments %d,%d,%d,%d\n",
curTick, tc->getCpuPtr()->name(), name,
- process->getSyscallArg(tc, 0), process->getSyscallArg(tc, 1),
- process->getSyscallArg(tc, 2), process->getSyscallArg(tc, 3));
+ process->getSyscallArg(tc, index),
+ process->getSyscallArg(tc, index),
+ process->getSyscallArg(tc, index),
+ process->getSyscallArg(tc, index));
SyscallReturn retval = (*funcPtr)(this, callnum, process, tc);
@@ -82,8 +88,9 @@ SyscallReturn
ignoreFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
+ int index = 0;
warn("ignoring syscall %s(%d, %d, ...)", desc->name,
- process->getSyscallArg(tc, 0), process->getSyscallArg(tc, 1));
+ process->getSyscallArg(tc, index), process->getSyscallArg(tc, index));
return 0;
}
@@ -95,8 +102,9 @@ exitFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
{
if (process->system->numRunningContexts() == 1) {
// Last running context... exit simulator
+ int index = 0;
exitSimLoop("target called exit()",
- process->getSyscallArg(tc, 0) & 0xff);
+ process->getSyscallArg(tc, index) & 0xff);
} else {
// other running threads... just halt this one
tc->halt();
@@ -112,8 +120,9 @@ exitGroupFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
{
// really should just halt all thread contexts belonging to this
// process in case there's another process running...
+ int index = 0;
exitSimLoop("target called exit()",
- process->getSyscallArg(tc, 0) & 0xff);
+ process->getSyscallArg(tc, index) & 0xff);
return 1;
}
@@ -130,7 +139,8 @@ SyscallReturn
brkFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
// change brk addr to first arg
- Addr new_brk = p->getSyscallArg(tc, 0);
+ int index = 0;
+ Addr new_brk = p->getSyscallArg(tc, index);
// in Linux at least, brk(0) returns the current break value
// (note that the syscall and the glibc function have different behavior)
@@ -144,6 +154,24 @@ brkFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
if (!p->pTable->translate(gen.addr()))
p->pTable->allocate(roundDown(gen.addr(), VMPageSize),
VMPageSize);
+
+ // if the address is already there, zero it out
+ else {
+ uint8_t zero = 0;
+ TranslatingPort *tp = tc->getMemPort();
+
+ // split non-page aligned accesses
+ Addr next_page = roundUp(gen.addr(), VMPageSize);
+ uint32_t size_needed = next_page - gen.addr();
+ tp->memsetBlob(gen.addr(), zero, size_needed);
+ if (gen.addr() + VMPageSize > next_page &&
+ next_page < new_brk &&
+ p->pTable->translate(next_page))
+ {
+ size_needed = VMPageSize - size_needed;
+ tp->memsetBlob(next_page, zero, size_needed);
+ }
+ }
}
}
@@ -156,7 +184,8 @@ brkFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
SyscallReturn
closeFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
- int target_fd = p->getSyscallArg(tc, 0);
+ int index = 0;
+ int target_fd = p->getSyscallArg(tc, index);
int status = close(p->sim_fd(target_fd));
if (status >= 0)
p->free_fd(target_fd);
@@ -167,9 +196,11 @@ closeFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
SyscallReturn
readFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
- int fd = p->sim_fd(p->getSyscallArg(tc, 0));
- int nbytes = p->getSyscallArg(tc, 2);
- BufferArg bufArg(p->getSyscallArg(tc, 1), nbytes);
+ int index = 0;
+ int fd = p->sim_fd(p->getSyscallArg(tc, index));
+ Addr bufPtr = p->getSyscallArg(tc, index);
+ int nbytes = p->getSyscallArg(tc, index);
+ BufferArg bufArg(bufPtr, nbytes);
int bytes_read = read(fd, bufArg.bufferPtr(), nbytes);
@@ -182,9 +213,11 @@ readFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
SyscallReturn
writeFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
- int fd = p->sim_fd(p->getSyscallArg(tc, 0));
- int nbytes = p->getSyscallArg(tc, 2);
- BufferArg bufArg(p->getSyscallArg(tc, 1), nbytes);
+ int index = 0;
+ int fd = p->sim_fd(p->getSyscallArg(tc, index));
+ Addr bufPtr = p->getSyscallArg(tc, index);
+ int nbytes = p->getSyscallArg(tc, index);
+ BufferArg bufArg(bufPtr, nbytes);
bufArg.copyIn(tc->getMemPort());
@@ -199,9 +232,10 @@ writeFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
SyscallReturn
lseekFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
- int fd = p->sim_fd(p->getSyscallArg(tc, 0));
- uint64_t offs = p->getSyscallArg(tc, 1);
- int whence = p->getSyscallArg(tc, 2);
+ int index = 0;
+ int fd = p->sim_fd(p->getSyscallArg(tc, index));
+ uint64_t offs = p->getSyscallArg(tc, index);
+ int whence = p->getSyscallArg(tc, index);
off_t result = lseek(fd, offs, whence);
@@ -212,11 +246,12 @@ lseekFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
SyscallReturn
_llseekFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
- int fd = p->sim_fd(p->getSyscallArg(tc, 0));
- uint64_t offset_high = p->getSyscallArg(tc, 1);
- uint32_t offset_low = p->getSyscallArg(tc, 2);
- Addr result_ptr = p->getSyscallArg(tc, 3);
- int whence = p->getSyscallArg(tc, 4);
+ int index = 0;
+ int fd = p->sim_fd(p->getSyscallArg(tc, index));
+ uint64_t offset_high = p->getSyscallArg(tc, index);
+ uint32_t offset_low = p->getSyscallArg(tc, index);
+ Addr result_ptr = p->getSyscallArg(tc, index);
+ int whence = p->getSyscallArg(tc, index);
uint64_t offset = (offset_high << 32) | offset_low;
@@ -255,8 +290,10 @@ const char *hostname = "m5.eecs.umich.edu";
SyscallReturn
gethostnameFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
- int name_len = p->getSyscallArg(tc, 1);
- BufferArg name(p->getSyscallArg(tc, 0), name_len);
+ int index = 0;
+ Addr bufPtr = p->getSyscallArg(tc, index);
+ int name_len = p->getSyscallArg(tc, index);
+ BufferArg name(bufPtr, name_len);
strncpy((char *)name.bufferPtr(), hostname, name_len);
@@ -269,8 +306,10 @@ SyscallReturn
getcwdFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
int result = 0;
- unsigned long size = p->getSyscallArg(tc, 1);
- BufferArg buf(p->getSyscallArg(tc, 0), size);
+ int index = 0;
+ Addr bufPtr = p->getSyscallArg(tc, index);
+ unsigned long size = p->getSyscallArg(tc, index);
+ BufferArg buf(bufPtr, size);
// Is current working directory defined?
string cwd = p->getcwd();
@@ -302,14 +341,17 @@ readlinkFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
string path;
- if (!tc->getMemPort()->tryReadString(path, p->getSyscallArg(tc, 0)))
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path, p->getSyscallArg(tc, index)))
return (TheISA::IntReg)-EFAULT;
// Adjust path for current working directory
path = p->fullPath(path);
- size_t bufsiz = p->getSyscallArg(tc, 2);
- BufferArg buf(p->getSyscallArg(tc, 1), bufsiz);
+ Addr bufPtr = p->getSyscallArg(tc, index);
+ size_t bufsiz = p->getSyscallArg(tc, index);
+
+ BufferArg buf(bufPtr, bufsiz);
int result = readlink(path.c_str(), (char *)buf.bufferPtr(), bufsiz);
@@ -323,7 +365,8 @@ unlinkFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
string path;
- if (!tc->getMemPort()->tryReadString(path, p->getSyscallArg(tc, 0)))
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path, p->getSyscallArg(tc, index)))
return (TheISA::IntReg)-EFAULT;
// Adjust path for current working directory
@@ -339,13 +382,14 @@ mkdirFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
string path;
- if (!tc->getMemPort()->tryReadString(path, p->getSyscallArg(tc, 0)))
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path, p->getSyscallArg(tc, index)))
return (TheISA::IntReg)-EFAULT;
// Adjust path for current working directory
path = p->fullPath(path);
- mode_t mode = p->getSyscallArg(tc, 1);
+ mode_t mode = p->getSyscallArg(tc, index);
int result = mkdir(path.c_str(), mode);
return (result == -1) ? -errno : result;
@@ -356,12 +400,13 @@ renameFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
string old_name;
- if (!tc->getMemPort()->tryReadString(old_name, p->getSyscallArg(tc, 0)))
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(old_name, p->getSyscallArg(tc, index)))
return -EFAULT;
string new_name;
- if (!tc->getMemPort()->tryReadString(new_name, p->getSyscallArg(tc, 1)))
+ if (!tc->getMemPort()->tryReadString(new_name, p->getSyscallArg(tc, index)))
return -EFAULT;
// Adjust path for current working directory
@@ -377,10 +422,11 @@ truncateFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
string path;
- if (!tc->getMemPort()->tryReadString(path, p->getSyscallArg(tc, 0)))
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path, p->getSyscallArg(tc, index)))
return -EFAULT;
- off_t length = p->getSyscallArg(tc, 1);
+ off_t length = p->getSyscallArg(tc, index);
// Adjust path for current working directory
path = p->fullPath(path);
@@ -393,18 +439,62 @@ SyscallReturn
ftruncateFunc(SyscallDesc *desc, int num,
LiveProcess *process, ThreadContext *tc)
{
- int fd = process->sim_fd(process->getSyscallArg(tc, 0));
+ int index = 0;
+ int fd = process->sim_fd(process->getSyscallArg(tc, index));
if (fd < 0)
return -EBADF;
- off_t length = process->getSyscallArg(tc, 1);
+ off_t length = process->getSyscallArg(tc, index);
int result = ftruncate(fd, length);
return (result == -1) ? -errno : result;
}
SyscallReturn
+truncate64Func(SyscallDesc *desc, int num,
+ LiveProcess *process, ThreadContext *tc)
+{
+ int index = 0;
+ string path;
+
+ if (!tc->getMemPort()->tryReadString(path, process->getSyscallArg(tc, index)))
+ return -EFAULT;
+
+ int64_t length = process->getSyscallArg(tc, index, 64);
+
+ // Adjust path for current working directory
+ path = process->fullPath(path);
+
+#if NO_STAT64
+ int result = truncate(path.c_str(), length);
+#else
+ int result = truncate64(path.c_str(), length);
+#endif
+ return (result == -1) ? -errno : result;
+}
+
+SyscallReturn
+ftruncate64Func(SyscallDesc *desc, int num,
+ LiveProcess *process, ThreadContext *tc)
+{
+ int index = 0;
+ int fd = process->sim_fd(process->getSyscallArg(tc, index));
+
+ if (fd < 0)
+ return -EBADF;
+
+ int64_t length = process->getSyscallArg(tc, index, 64);
+
+#if NO_STAT64
+ int result = ftruncate(fd, length);
+#else
+ int result = ftruncate64(fd, length);
+#endif
+ return (result == -1) ? -errno : result;
+}
+
+SyscallReturn
umaskFunc(SyscallDesc *desc, int num, LiveProcess *process, ThreadContext *tc)
{
// Letting the simulated program change the simulator's umask seems like
@@ -420,13 +510,14 @@ chownFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
string path;
- if (!tc->getMemPort()->tryReadString(path, p->getSyscallArg(tc, 0)))
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path, p->getSyscallArg(tc, index)))
return -EFAULT;
/* XXX endianess */
- uint32_t owner = p->getSyscallArg(tc, 1);
+ uint32_t owner = p->getSyscallArg(tc, index);
uid_t hostOwner = owner;
- uint32_t group = p->getSyscallArg(tc, 2);
+ uint32_t group = p->getSyscallArg(tc, index);
gid_t hostGroup = group;
// Adjust path for current working directory
@@ -439,15 +530,16 @@ chownFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
SyscallReturn
fchownFunc(SyscallDesc *desc, int num, LiveProcess *process, ThreadContext *tc)
{
- int fd = process->sim_fd(process->getSyscallArg(tc, 0));
+ int index = 0;
+ int fd = process->sim_fd(process->getSyscallArg(tc, index));
if (fd < 0)
return -EBADF;
/* XXX endianess */
- uint32_t owner = process->getSyscallArg(tc, 1);
+ uint32_t owner = process->getSyscallArg(tc, index);
uid_t hostOwner = owner;
- uint32_t group = process->getSyscallArg(tc, 2);
+ uint32_t group = process->getSyscallArg(tc, index);
gid_t hostGroup = group;
int result = fchown(fd, hostOwner, hostGroup);
@@ -458,11 +550,12 @@ fchownFunc(SyscallDesc *desc, int num, LiveProcess *process, ThreadContext *tc)
SyscallReturn
dupFunc(SyscallDesc *desc, int num, LiveProcess *process, ThreadContext *tc)
{
- int fd = process->sim_fd(process->getSyscallArg(tc, 0));
+ int index = 0;
+ int fd = process->sim_fd(process->getSyscallArg(tc, index));
if (fd < 0)
return -EBADF;
- Process::FdMap *fdo = process->sim_fd_obj(process->getSyscallArg(tc, 0));
+ Process::FdMap *fdo = process->sim_fd_obj(fd);
int result = dup(fd);
return (result == -1) ? -errno :
@@ -474,12 +567,13 @@ SyscallReturn
fcntlFunc(SyscallDesc *desc, int num, LiveProcess *process,
ThreadContext *tc)
{
- int fd = process->getSyscallArg(tc, 0);
+ int index = 0;
+ int fd = process->getSyscallArg(tc, index);
if (fd < 0 || process->sim_fd(fd) < 0)
return -EBADF;
- int cmd = process->getSyscallArg(tc, 1);
+ int cmd = process->getSyscallArg(tc, index);
switch (cmd) {
case 0: // F_DUPFD
// if we really wanted to support this, we'd need to do it
@@ -516,12 +610,13 @@ SyscallReturn
fcntl64Func(SyscallDesc *desc, int num, LiveProcess *process,
ThreadContext *tc)
{
- int fd = process->getSyscallArg(tc, 0);
+ int index = 0;
+ int fd = process->getSyscallArg(tc, index);
if (fd < 0 || process->sim_fd(fd) < 0)
return -EBADF;
- int cmd = process->getSyscallArg(tc, 1);
+ int cmd = process->getSyscallArg(tc, index);
switch (cmd) {
case 33: //F_GETLK64
warn("fcntl64(%d, F_GETLK64) not supported, error returned\n", fd);
@@ -605,7 +700,8 @@ setuidFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
// can't fathom why a benchmark would call this.
- warn("Ignoring call to setuid(%d)\n", process->getSyscallArg(tc, 0));
+ int index = 0;
+ warn("Ignoring call to setuid(%d)\n", process->getSyscallArg(tc, index));
return 0;
}
@@ -661,17 +757,20 @@ SyscallReturn
cloneFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
+ int index = 0;
+ IntReg flags = process->getSyscallArg(tc, index);
+ IntReg newStack = process->getSyscallArg(tc, index);
+
DPRINTF(SyscallVerbose, "In sys_clone:\n");
- DPRINTF(SyscallVerbose, " Flags=%llx\n", process->getSyscallArg(tc, 0));
- DPRINTF(SyscallVerbose, " Child stack=%llx\n",
- process->getSyscallArg(tc, 1));
+ DPRINTF(SyscallVerbose, " Flags=%llx\n", flags);
+ DPRINTF(SyscallVerbose, " Child stack=%llx\n", newStack);
- if (process->getSyscallArg(tc, 0) != 0x10f00) {
+ if (flags != 0x10f00) {
warn("This sys_clone implementation assumes flags "
"CLONE_VM|CLONE_FS|CLONE_FILES|CLONE_SIGHAND|CLONE_THREAD "
"(0x10f00), and may not work correctly with given flags "
- "0x%llx\n", process->getSyscallArg(tc, 0));
+ "0x%llx\n", flags);
}
ThreadContext* ctc; // child thread context
@@ -704,7 +803,7 @@ cloneFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
#endif
// Set up stack register
- ctc->setIntReg(TheISA::StackPointerReg, process->getSyscallArg(tc, 1));
+ ctc->setIntReg(TheISA::StackPointerReg, newStack);
// Set up syscall return values in parent and child
ctc->setIntReg(ReturnValueReg, 0); // return value, child
diff --git a/src/sim/syscall_emul.hh b/src/sim/syscall_emul.hh
index 5f2ebd428..66e800183 100644
--- a/src/sim/syscall_emul.hh
+++ b/src/sim/syscall_emul.hh
@@ -55,10 +55,12 @@
#include "base/misc.hh"
#include "base/trace.hh"
#include "base/types.hh"
+#include "config/the_isa.hh"
#include "cpu/base.hh"
#include "cpu/thread_context.hh"
#include "mem/translating_port.hh"
#include "mem/page_table.hh"
+#include "sim/system.hh"
#include "sim/process.hh"
///
@@ -258,6 +260,15 @@ SyscallReturn ftruncateFunc(SyscallDesc *desc, int num,
LiveProcess *p, ThreadContext *tc);
+/// Target truncate64() handler.
+SyscallReturn truncate64Func(SyscallDesc *desc, int num,
+ LiveProcess *p, ThreadContext *tc);
+
+/// Target ftruncate64() handler.
+SyscallReturn ftruncate64Func(SyscallDesc *desc, int num,
+ LiveProcess *p, ThreadContext *tc);
+
+
/// Target umask() handler.
SyscallReturn umaskFunc(SyscallDesc *desc, int num,
LiveProcess *p, ThreadContext *tc);
@@ -462,7 +473,7 @@ copyOutStat64Buf(TranslatingPort * mem, Addr addr,
{
typedef TypedBufferArg<typename OS::tgt_stat64> tgt_stat_buf;
tgt_stat_buf tgt(addr);
- convertStatBuf<tgt_stat_buf, hst_stat64>(tgt, host, fakeTTY);
+ convertStat64Buf<tgt_stat_buf, hst_stat64>(tgt, host, fakeTTY);
tgt.copyOut(mem);
}
@@ -474,8 +485,9 @@ SyscallReturn
ioctlFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
- int fd = process->getSyscallArg(tc, 0);
- unsigned req = process->getSyscallArg(tc, 1);
+ int index = 0;
+ int fd = process->getSyscallArg(tc, index);
+ unsigned req = process->getSyscallArg(tc, index);
DPRINTF(SyscallVerbose, "ioctl(%d, 0x%x, ...)\n", fd, req);
@@ -493,6 +505,7 @@ ioctlFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
case OS::TIOCGETC_:
case OS::TIOCGETS_:
case OS::TIOCGETA_:
+ case OS::TCSETAW_:
return -ENOTTY;
default:
@@ -509,7 +522,9 @@ openFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
{
std::string path;
- if (!tc->getMemPort()->tryReadString(path, process->getSyscallArg(tc, 0)))
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path,
+ process->getSyscallArg(tc, index)))
return -EFAULT;
if (path == "/dev/sysdev0") {
@@ -519,8 +534,8 @@ openFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
return -ENOENT;
}
- int tgtFlags = process->getSyscallArg(tc, 1);
- int mode = process->getSyscallArg(tc, 2);
+ int tgtFlags = process->getSyscallArg(tc, index);
+ int mode = process->getSyscallArg(tc, index);
int hostFlags = 0;
// translate open flags
@@ -558,6 +573,24 @@ openFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
}
+/// Target sysinfo() handler.
+template <class OS>
+SyscallReturn
+sysinfoFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
+ ThreadContext *tc)
+{
+
+ int index = 0;
+ TypedBufferArg<typename OS::tgt_sysinfo>
+ sysinfo(process->getSyscallArg(tc, index));
+
+ sysinfo->uptime=seconds_since_epoch;
+ sysinfo->totalram=process->system->memSize();
+
+ sysinfo.copyOut(tc->getMemPort());
+
+ return 0;
+}
/// Target chmod() handler.
template <class OS>
@@ -567,10 +600,13 @@ chmodFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
{
std::string path;
- if (!tc->getMemPort()->tryReadString(path, process->getSyscallArg(tc, 0)))
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path,
+ process->getSyscallArg(tc, index))) {
return -EFAULT;
+ }
- uint32_t mode = process->getSyscallArg(tc, 1);
+ uint32_t mode = process->getSyscallArg(tc, index);
mode_t hostMode = 0;
// XXX translate mode flags via OS::something???
@@ -594,13 +630,14 @@ SyscallReturn
fchmodFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
- int fd = process->getSyscallArg(tc, 0);
+ int index = 0;
+ int fd = process->getSyscallArg(tc, index);
if (fd < 0 || process->sim_fd(fd) < 0) {
// doesn't map to any simulator fd: not a valid target fd
return -EBADF;
}
- uint32_t mode = process->getSyscallArg(tc, 1);
+ uint32_t mode = process->getSyscallArg(tc, index);
mode_t hostMode = 0;
// XXX translate mode flags via OS::someting???
@@ -619,10 +656,11 @@ template <class OS>
SyscallReturn
mremapFunc(SyscallDesc *desc, int callnum, LiveProcess *process, ThreadContext *tc)
{
- Addr start = process->getSyscallArg(tc, 0);
- uint64_t old_length = process->getSyscallArg(tc, 1);
- uint64_t new_length = process->getSyscallArg(tc, 2);
- uint64_t flags = process->getSyscallArg(tc, 3);
+ int index = 0;
+ Addr start = process->getSyscallArg(tc, index);
+ uint64_t old_length = process->getSyscallArg(tc, index);
+ uint64_t new_length = process->getSyscallArg(tc, index);
+ uint64_t flags = process->getSyscallArg(tc, index);
if ((start % TheISA::VMPageSize != 0) ||
(new_length % TheISA::VMPageSize != 0)) {
@@ -668,8 +706,12 @@ statFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
{
std::string path;
- if (!tc->getMemPort()->tryReadString(path, process->getSyscallArg(tc, 0)))
- return -EFAULT;
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path,
+ process->getSyscallArg(tc, index))) {
+ return -EFAULT;
+ }
+ Addr bufPtr = process->getSyscallArg(tc, index);
// Adjust path for current working directory
path = process->fullPath(path);
@@ -680,8 +722,7 @@ statFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
if (result < 0)
return -errno;
- copyOutStatBuf<OS>(tc->getMemPort(), process->getSyscallArg(tc, 1),
- &hostBuf);
+ copyOutStatBuf<OS>(tc->getMemPort(), bufPtr, &hostBuf);
return 0;
}
@@ -695,8 +736,11 @@ stat64Func(SyscallDesc *desc, int callnum, LiveProcess *process,
{
std::string path;
- if (!tc->getMemPort()->tryReadString(path, process->getSyscallArg(tc, 0)))
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path,
+ process->getSyscallArg(tc, index)))
return -EFAULT;
+ Addr bufPtr = process->getSyscallArg(tc, index);
// Adjust path for current working directory
path = process->fullPath(path);
@@ -712,8 +756,7 @@ stat64Func(SyscallDesc *desc, int callnum, LiveProcess *process,
if (result < 0)
return -errno;
- copyOutStat64Buf<OS>(tc->getMemPort(), process->getSyscallArg(tc, 1),
- &hostBuf);
+ copyOutStat64Buf<OS>(tc->getMemPort(), bufPtr, &hostBuf);
return 0;
}
@@ -725,7 +768,9 @@ SyscallReturn
fstat64Func(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
- int fd = process->getSyscallArg(tc, 0);
+ int index = 0;
+ int fd = process->getSyscallArg(tc, index);
+ Addr bufPtr = process->getSyscallArg(tc, index);
if (fd < 0 || process->sim_fd(fd) < 0) {
// doesn't map to any simulator fd: not a valid target fd
return -EBADF;
@@ -742,8 +787,7 @@ fstat64Func(SyscallDesc *desc, int callnum, LiveProcess *process,
if (result < 0)
return -errno;
- copyOutStat64Buf<OS>(tc->getMemPort(), process->getSyscallArg(tc, 1),
- &hostBuf, (fd == 1));
+ copyOutStat64Buf<OS>(tc->getMemPort(), bufPtr, &hostBuf, (fd == 1));
return 0;
}
@@ -757,8 +801,12 @@ lstatFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
{
std::string path;
- if (!tc->getMemPort()->tryReadString(path, process->getSyscallArg(tc, 0)))
- return -EFAULT;
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path,
+ process->getSyscallArg(tc, index))) {
+ return -EFAULT;
+ }
+ Addr bufPtr = process->getSyscallArg(tc, index);
// Adjust path for current working directory
path = process->fullPath(path);
@@ -769,8 +817,7 @@ lstatFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
if (result < 0)
return -errno;
- copyOutStatBuf<OS>(tc->getMemPort(), process->getSyscallArg(tc, 1),
- &hostBuf);
+ copyOutStatBuf<OS>(tc->getMemPort(), bufPtr, &hostBuf);
return 0;
}
@@ -783,8 +830,12 @@ lstat64Func(SyscallDesc *desc, int callnum, LiveProcess *process,
{
std::string path;
- if (!tc->getMemPort()->tryReadString(path, process->getSyscallArg(tc, 0)))
- return -EFAULT;
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path,
+ process->getSyscallArg(tc, index))) {
+ return -EFAULT;
+ }
+ Addr bufPtr = process->getSyscallArg(tc, index);
// Adjust path for current working directory
path = process->fullPath(path);
@@ -800,8 +851,7 @@ lstat64Func(SyscallDesc *desc, int callnum, LiveProcess *process,
if (result < 0)
return -errno;
- copyOutStat64Buf<OS>(tc->getMemPort(), process->getSyscallArg(tc, 1),
- &hostBuf);
+ copyOutStat64Buf<OS>(tc->getMemPort(), bufPtr, &hostBuf);
return 0;
}
@@ -812,7 +862,9 @@ SyscallReturn
fstatFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
- int fd = process->sim_fd(process->getSyscallArg(tc, 0));
+ int index = 0;
+ int fd = process->sim_fd(process->getSyscallArg(tc, index));
+ Addr bufPtr = process->getSyscallArg(tc, index);
DPRINTF(SyscallVerbose, "fstat(%d, ...)\n", fd);
@@ -825,8 +877,7 @@ fstatFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
if (result < 0)
return -errno;
- copyOutStatBuf<OS>(tc->getMemPort(), process->getSyscallArg(tc, 1),
- &hostBuf, (fd == 1));
+ copyOutStatBuf<OS>(tc->getMemPort(), bufPtr, &hostBuf, (fd == 1));
return 0;
}
@@ -840,8 +891,12 @@ statfsFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
{
std::string path;
- if (!tc->getMemPort()->tryReadString(path, process->getSyscallArg(tc, 0)))
- return -EFAULT;
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path,
+ process->getSyscallArg(tc, index))) {
+ return -EFAULT;
+ }
+ Addr bufPtr = process->getSyscallArg(tc, index);
// Adjust path for current working directory
path = process->fullPath(path);
@@ -852,8 +907,7 @@ statfsFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
if (result < 0)
return -errno;
- OS::copyOutStatfsBuf(tc->getMemPort(),
- (Addr)(process->getSyscallArg(tc, 1)), &hostBuf);
+ OS::copyOutStatfsBuf(tc->getMemPort(), bufPtr, &hostBuf);
return 0;
}
@@ -865,7 +919,9 @@ SyscallReturn
fstatfsFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
- int fd = process->sim_fd(process->getSyscallArg(tc, 0));
+ int index = 0;
+ int fd = process->sim_fd(process->getSyscallArg(tc, index));
+ Addr bufPtr = process->getSyscallArg(tc, index);
if (fd < 0)
return -EBADF;
@@ -876,8 +932,7 @@ fstatfsFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
if (result < 0)
return -errno;
- OS::copyOutStatfsBuf(tc->getMemPort(), process->getSyscallArg(tc, 1),
- &hostBuf);
+ OS::copyOutStatfsBuf(tc->getMemPort(), bufPtr, &hostBuf);
return 0;
}
@@ -889,15 +944,16 @@ SyscallReturn
writevFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
- int fd = process->getSyscallArg(tc, 0);
+ int index = 0;
+ int fd = process->getSyscallArg(tc, index);
if (fd < 0 || process->sim_fd(fd) < 0) {
// doesn't map to any simulator fd: not a valid target fd
return -EBADF;
}
TranslatingPort *p = tc->getMemPort();
- uint64_t tiov_base = process->getSyscallArg(tc, 1);
- size_t count = process->getSyscallArg(tc, 2);
+ uint64_t tiov_base = process->getSyscallArg(tc, index);
+ size_t count = process->getSyscallArg(tc, index);
struct iovec hiov[count];
for (size_t i = 0; i < count; ++i) {
typename OS::tgt_iovec tiov;
@@ -938,12 +994,13 @@ template <class OS>
SyscallReturn
mmapFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
{
- Addr start = p->getSyscallArg(tc, 0);
- uint64_t length = p->getSyscallArg(tc, 1);
- // int prot = p->getSyscallArg(tc, 2);
- int flags = p->getSyscallArg(tc, 3);
- // int fd = p->sim_fd(p->getSyscallArg(tc, 4));
- // int offset = p->getSyscallArg(tc, 5);
+ int index = 0;
+ Addr start = p->getSyscallArg(tc, index);
+ uint64_t length = p->getSyscallArg(tc, index);
+ index++; // int prot = p->getSyscallArg(tc, index);
+ int flags = p->getSyscallArg(tc, index);
+ int fd = p->sim_fd(p->getSyscallArg(tc, index));
+ // int offset = p->getSyscallArg(tc, index);
if ((start % TheISA::VMPageSize) != 0 ||
@@ -960,13 +1017,18 @@ mmapFunc(SyscallDesc *desc, int num, LiveProcess *p, ThreadContext *tc)
}
// pick next address from our "mmap region"
- start = p->mmap_end;
+ if (OS::mmapGrowsDown()) {
+ start = p->mmap_end - length;
+ p->mmap_end = start;
+ } else {
+ start = p->mmap_end;
+ p->mmap_end += length;
+ }
p->pTable->allocate(start, length);
- p->mmap_end += length;
if (!(flags & OS::TGT_MAP_ANONYMOUS)) {
warn("allowing mmap of file @ fd %d. "
- "This will break if not /dev/zero.", p->getSyscallArg(tc, 4));
+ "This will break if not /dev/zero.", fd);
}
return start;
@@ -978,8 +1040,9 @@ SyscallReturn
getrlimitFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
- unsigned resource = process->getSyscallArg(tc, 0);
- TypedBufferArg<typename OS::rlimit> rlp(process->getSyscallArg(tc, 1));
+ int index = 0;
+ unsigned resource = process->getSyscallArg(tc, index);
+ TypedBufferArg<typename OS::rlimit> rlp(process->getSyscallArg(tc, index));
switch (resource) {
case OS::TGT_RLIMIT_STACK:
@@ -1013,7 +1076,8 @@ SyscallReturn
gettimeofdayFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
- TypedBufferArg<typename OS::timeval> tp(process->getSyscallArg(tc, 0));
+ int index = 0;
+ TypedBufferArg<typename OS::timeval> tp(process->getSyscallArg(tc, index));
getElapsedTime(tp->tv_sec, tp->tv_usec);
tp->tv_sec += seconds_since_epoch;
@@ -1034,10 +1098,14 @@ utimesFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
{
std::string path;
- if (!tc->getMemPort()->tryReadString(path, process->getSyscallArg(tc, 0)))
- return -EFAULT;
+ int index = 0;
+ if (!tc->getMemPort()->tryReadString(path,
+ process->getSyscallArg(tc, index))) {
+ return -EFAULT;
+ }
- TypedBufferArg<typename OS::timeval [2]> tp(process->getSyscallArg(tc, 1));
+ TypedBufferArg<typename OS::timeval [2]>
+ tp(process->getSyscallArg(tc, index));
tp.copyIn(tc->getMemPort());
struct timeval hostTimeval[2];
@@ -1063,8 +1131,9 @@ SyscallReturn
getrusageFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
ThreadContext *tc)
{
- int who = process->getSyscallArg(tc, 0); // THREAD, SELF, or CHILDREN
- TypedBufferArg<typename OS::rusage> rup(process->getSyscallArg(tc, 1));
+ int index = 0;
+ int who = process->getSyscallArg(tc, index); // THREAD, SELF, or CHILDREN
+ TypedBufferArg<typename OS::rusage> rup(process->getSyscallArg(tc, index));
rup->ru_utime.tv_sec = 0;
rup->ru_utime.tv_usec = 0;
@@ -1108,7 +1177,52 @@ getrusageFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
return 0;
}
+/// Target times() function.
+template <class OS>
+SyscallReturn
+timesFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
+ ThreadContext *tc)
+{
+ int index = 0;
+ TypedBufferArg<typename OS::tms> bufp(process->getSyscallArg(tc, index));
+
+ // Fill in the time structure (in clocks)
+ int64_t clocks = curTick * OS::M5_SC_CLK_TCK / Clock::Int::s;
+ bufp->tms_utime = clocks;
+ bufp->tms_stime = 0;
+ bufp->tms_cutime = 0;
+ bufp->tms_cstime = 0;
+ // Convert to host endianness
+ bufp->tms_utime = htog(bufp->tms_utime);
+
+ // Write back
+ bufp.copyOut(tc->getMemPort());
+
+ // Return clock ticks since system boot
+ return clocks;
+}
+
+/// Target time() function.
+template <class OS>
+SyscallReturn
+timeFunc(SyscallDesc *desc, int callnum, LiveProcess *process,
+ ThreadContext *tc)
+{
+ typename OS::time_t sec, usec;
+ getElapsedTime(sec, usec);
+ sec += seconds_since_epoch;
+
+ int index = 0;
+ Addr taddr = (Addr)process->getSyscallArg(tc, index);
+ if(taddr != 0) {
+ typename OS::time_t t = sec;
+ t = htog(t);
+ TranslatingPort *p = tc->getMemPort();
+ p->writeBlob(taddr, (uint8_t*)&t, (int)sizeof(typename OS::time_t));
+ }
+ return sec;
+}
#endif // __SIM_SYSCALL_EMUL_HH__
diff --git a/src/sim/system.cc b/src/sim/system.cc
index f10167bba..da77f1995 100644
--- a/src/sim/system.cc
+++ b/src/sim/system.cc
@@ -38,11 +38,14 @@
#include "base/loader/symtab.hh"
#include "base/trace.hh"
#include "cpu/thread_context.hh"
+#include "config/full_system.hh"
+#include "config/the_isa.hh"
#include "mem/mem_object.hh"
#include "mem/physical.hh"
#include "sim/byteswap.hh"
#include "sim/system.hh"
#include "sim/debug.hh"
+
#if FULL_SYSTEM
#include "arch/vtophys.hh"
#include "kern/kernel_stats.hh"
diff --git a/src/sim/system.hh b/src/sim/system.hh
index aa89866bd..eabbc8351 100644
--- a/src/sim/system.hh
+++ b/src/sim/system.hh
@@ -45,6 +45,7 @@
#include "mem/port.hh"
#include "params/System.hh"
#include "sim/sim_object.hh"
+
#if FULL_SYSTEM
#include "kern/system_events.hh"
#include "mem/vport.hh"
@@ -59,10 +60,7 @@ class PhysicalMemory;
class Platform;
#endif
class GDBListener;
-namespace TheISA
-{
- class RemoteGDB;
-}
+class BaseRemoteGDB;
class System : public SimObject
{
@@ -187,7 +185,7 @@ class System : public SimObject
#endif
public:
- std::vector<TheISA::RemoteGDB *> remoteGDB;
+ std::vector<BaseRemoteGDB *> remoteGDB;
std::vector<GDBListener *> gdbListen;
bool breakpoint();