summaryrefslogtreecommitdiff
path: root/src/sim/syscall_emul.hh
diff options
context:
space:
mode:
authorBrandon Potter <brandon.potter@amd.com>2016-11-09 14:27:42 -0600
committerBrandon Potter <brandon.potter@amd.com>2016-11-09 14:27:42 -0600
commitd3d983caf94375b992940b017aeb4a73da28833c (patch)
tree7e6bf4226c9235ad187c0137c6518b3897b64752 /src/sim/syscall_emul.hh
parent6c41181b8e39e776ea2f018bf383fed2782c3d4a (diff)
downloadgem5-d3d983caf94375b992940b017aeb4a73da28833c.tar.xz
syscall_emul: [patch 10/22] refactor fdentry and add fdarray class
Several large changes happen in this patch. The FDEntry class is rewritten so that file descriptors now correspond to types: 'File' which is normal file-backed file with the file open on the host machine, 'Pipe' which is a pipe that has been opened on the host machine, and 'Device' which does not have an open file on the host yet acts as a pseudo device with which to issue ioctls. Other types which might be added in the future are directory entries and sockets (off the top of my head). The FDArray class was create to hold most of the file descriptor handling that was stuffed into the Process class. It uses shared pointers and the std::array type to hold the FDEntries mentioned above. The changes to these two classes needed to be propagated out to the rest of the code so there were quite a few changes for that. Also, comments were added where I thought they were needed to help others and extend our DOxygen coverage.
Diffstat (limited to 'src/sim/syscall_emul.hh')
-rw-r--r--src/sim/syscall_emul.hh152
1 files changed, 77 insertions, 75 deletions
diff --git a/src/sim/syscall_emul.hh b/src/sim/syscall_emul.hh
index c75784f79..376ae6f32 100644
--- a/src/sim/syscall_emul.hh
+++ b/src/sim/syscall_emul.hh
@@ -78,6 +78,7 @@
#include <unistd.h>
#include <cerrno>
+#include <memory>
#include <string>
#include "base/intmath.hh"
@@ -570,31 +571,35 @@ copyOutStatfsBuf(SETranslatingPortProxy &mem, Addr addr,
/// not TTYs to provide repeatable results.
template <class OS>
SyscallReturn
-ioctlFunc(SyscallDesc *desc, int callnum, Process *process,
- ThreadContext *tc)
+ioctlFunc(SyscallDesc *desc, int callnum, Process *p, ThreadContext *tc)
{
int index = 0;
- int tgt_fd = process->getSyscallArg(tc, index);
- unsigned req = process->getSyscallArg(tc, index);
+ int tgt_fd = p->getSyscallArg(tc, index);
+ unsigned req = p->getSyscallArg(tc, index);
DPRINTF(SyscallVerbose, "ioctl(%d, 0x%x, ...)\n", tgt_fd, req);
- FDEntry *fde = process->getFDEntry(tgt_fd);
+ if (OS::isTtyReq(req))
+ return -ENOTTY;
- if (fde == NULL) {
- // doesn't map to any simulator fd: not a valid target fd
+ auto dfdp = std::dynamic_pointer_cast<DeviceFDEntry>((*p->fds)[tgt_fd]);
+ if (!dfdp)
return -EBADF;
- }
- if (fde->driver != NULL) {
- return fde->driver->ioctl(process, tc, req);
- }
-
- if (OS::isTtyReq(req)) {
- return -ENOTTY;
- }
+ /**
+ * If the driver is valid, issue the ioctl through it. Otherwise,
+ * there's an implicit assumption that the device is a TTY type and we
+ * return that we do not have a valid TTY.
+ */
+ EmulatedDriver *emul_driver = dfdp->getDriver();
+ if (emul_driver)
+ return emul_driver->ioctl(p, tc, req);
- warn("Unsupported ioctl call: ioctl(%d, 0x%x, ...) @ \n",
+ /**
+ * For lack of a better return code, return ENOTTY. Ideally, we should
+ * return something better here, but at least we issue the warning.
+ */
+ warn("Unsupported ioctl call (return ENOTTY): ioctl(%d, 0x%x, ...) @ \n",
tgt_fd, req, tc->pcState());
return -ENOTTY;
}
@@ -645,7 +650,7 @@ openFunc(SyscallDesc *desc, int callnum, Process *process,
}
EmulatedDriver *drv = process->findDriver(filename);
- if (drv != NULL) {
+ if (drv) {
// the driver's open method will allocate a fd from the
// process if necessary.
return drv->open(process, tc, mode, hostFlags);
@@ -671,7 +676,9 @@ openFunc(SyscallDesc *desc, int callnum, Process *process,
if (fd == -1)
return -local_errno;
- return process->allocFD(fd, path.c_str(), hostFlags, mode, false);
+ std::shared_ptr<FileFDEntry> ffdp =
+ std::make_shared<FileFDEntry>(fd, hostFlags, path.c_str(), false);
+ return process->fds->allocFD(ffdp);
}
/// Target open() handler.
@@ -827,28 +834,22 @@ chmodFunc(SyscallDesc *desc, int callnum, Process *process,
/// Target fchmod() handler.
template <class OS>
SyscallReturn
-fchmodFunc(SyscallDesc *desc, int callnum, Process *process,
- ThreadContext *tc)
+fchmodFunc(SyscallDesc *desc, int callnum, Process *p, ThreadContext *tc)
{
int index = 0;
- int tgt_fd = process->getSyscallArg(tc, index);
- uint32_t mode = process->getSyscallArg(tc, index);
+ int tgt_fd = p->getSyscallArg(tc, index);
+ uint32_t mode = p->getSyscallArg(tc, index);
- int sim_fd = process->getSimFD(tgt_fd);
- if (sim_fd < 0)
+ auto ffdp = std::dynamic_pointer_cast<FileFDEntry>((*p->fds)[tgt_fd]);
+ if (!ffdp)
return -EBADF;
+ int sim_fd = ffdp->getSimFD();
- mode_t hostMode = 0;
+ mode_t hostMode = mode;
- // XXX translate mode flags via OS::someting???
- hostMode = mode;
-
- // do the fchmod
int result = fchmod(sim_fd, hostMode);
- if (result < 0)
- return -errno;
- return 0;
+ return (result < 0) ? -errno : 0;
}
/// Target mremap() handler.
@@ -1021,16 +1022,16 @@ fstatat64Func(SyscallDesc *desc, int callnum, Process *process,
/// Target fstat64() handler.
template <class OS>
SyscallReturn
-fstat64Func(SyscallDesc *desc, int callnum, Process *process,
- ThreadContext *tc)
+fstat64Func(SyscallDesc *desc, int callnum, Process *p, ThreadContext *tc)
{
int index = 0;
- int tgt_fd = process->getSyscallArg(tc, index);
- Addr bufPtr = process->getSyscallArg(tc, index);
+ int tgt_fd = p->getSyscallArg(tc, index);
+ Addr bufPtr = p->getSyscallArg(tc, index);
- int sim_fd = process->getSimFD(tgt_fd);
- if (sim_fd < 0)
+ auto ffdp = std::dynamic_pointer_cast<FileFDEntry>((*p->fds)[tgt_fd]);
+ if (!ffdp)
return -EBADF;
+ int sim_fd = ffdp->getSimFD();
#if NO_STAT64
struct stat hostBuf;
@@ -1115,18 +1116,18 @@ lstat64Func(SyscallDesc *desc, int callnum, Process *process,
/// Target fstat() handler.
template <class OS>
SyscallReturn
-fstatFunc(SyscallDesc *desc, int callnum, Process *process,
- ThreadContext *tc)
+fstatFunc(SyscallDesc *desc, int callnum, Process *p, ThreadContext *tc)
{
int index = 0;
- int tgt_fd = process->getSyscallArg(tc, index);
- Addr bufPtr = process->getSyscallArg(tc, index);
+ int tgt_fd = p->getSyscallArg(tc, index);
+ Addr bufPtr = p->getSyscallArg(tc, index);
DPRINTF_SYSCALL(Verbose, "fstat(%d, ...)\n", tgt_fd);
- int sim_fd = process->getSimFD(tgt_fd);
- if (sim_fd < 0)
+ auto ffdp = std::dynamic_pointer_cast<FileFDEntry>((*p->fds)[tgt_fd]);
+ if (!ffdp)
return -EBADF;
+ int sim_fd = ffdp->getSimFD();
struct stat hostBuf;
int result = fstat(sim_fd, &hostBuf);
@@ -1176,16 +1177,16 @@ statfsFunc(SyscallDesc *desc, int callnum, Process *process,
/// Target fstatfs() handler.
template <class OS>
SyscallReturn
-fstatfsFunc(SyscallDesc *desc, int callnum, Process *process,
- ThreadContext *tc)
+fstatfsFunc(SyscallDesc *desc, int callnum, Process *p, ThreadContext *tc)
{
int index = 0;
- int tgt_fd = process->getSyscallArg(tc, index);
- Addr bufPtr = process->getSyscallArg(tc, index);
+ int tgt_fd = p->getSyscallArg(tc, index);
+ Addr bufPtr = p->getSyscallArg(tc, index);
- int sim_fd = process->getSimFD(tgt_fd);
- if (sim_fd < 0)
+ auto ffdp = std::dynamic_pointer_cast<FileFDEntry>((*p->fds)[tgt_fd]);
+ if (!ffdp)
return -EBADF;
+ int sim_fd = ffdp->getSimFD();
struct statfs hostBuf;
int result = fstatfs(sim_fd, &hostBuf);
@@ -1202,29 +1203,29 @@ fstatfsFunc(SyscallDesc *desc, int callnum, Process *process,
/// Target writev() handler.
template <class OS>
SyscallReturn
-writevFunc(SyscallDesc *desc, int callnum, Process *process,
- ThreadContext *tc)
+writevFunc(SyscallDesc *desc, int callnum, Process *p, ThreadContext *tc)
{
int index = 0;
- int tgt_fd = process->getSyscallArg(tc, index);
+ int tgt_fd = p->getSyscallArg(tc, index);
- int sim_fd = process->getSimFD(tgt_fd);
- if (sim_fd < 0)
+ auto hbfdp = std::dynamic_pointer_cast<HBFDEntry>((*p->fds)[tgt_fd]);
+ if (!hbfdp)
return -EBADF;
+ int sim_fd = hbfdp->getSimFD();
- SETranslatingPortProxy &p = tc->getMemProxy();
- uint64_t tiov_base = process->getSyscallArg(tc, index);
- size_t count = process->getSyscallArg(tc, index);
+ SETranslatingPortProxy &prox = tc->getMemProxy();
+ uint64_t tiov_base = p->getSyscallArg(tc, index);
+ size_t count = p->getSyscallArg(tc, index);
struct iovec hiov[count];
for (size_t i = 0; i < count; ++i) {
typename OS::tgt_iovec tiov;
- p.readBlob(tiov_base + i*sizeof(typename OS::tgt_iovec),
- (uint8_t*)&tiov, sizeof(typename OS::tgt_iovec));
+ prox.readBlob(tiov_base + i*sizeof(typename OS::tgt_iovec),
+ (uint8_t*)&tiov, sizeof(typename OS::tgt_iovec));
hiov[i].iov_len = TheISA::gtoh(tiov.iov_len);
hiov[i].iov_base = new char [hiov[i].iov_len];
- p.readBlob(TheISA::gtoh(tiov.iov_base), (uint8_t *)hiov[i].iov_base,
- hiov[i].iov_len);
+ prox.readBlob(TheISA::gtoh(tiov.iov_base), (uint8_t *)hiov[i].iov_base,
+ hiov[i].iov_len);
}
int result = writev(sim_fd, hiov, count);
@@ -1296,19 +1297,19 @@ mmapImpl(SyscallDesc *desc, int num, Process *p, ThreadContext *tc,
int sim_fd = -1;
uint8_t *pmap = nullptr;
if (!(tgt_flags & OS::TGT_MAP_ANONYMOUS)) {
- // Check for EmulatedDriver mmap
- FDEntry *fde = p->getFDEntry(tgt_fd);
- if (fde == NULL)
- return -EBADF;
+ std::shared_ptr<FDEntry> fdep = (*p->fds)[tgt_fd];
- if (fde->driver != NULL) {
- return fde->driver->mmap(p, tc, start, length, prot,
+ auto dfdp = std::dynamic_pointer_cast<DeviceFDEntry>(fdep);
+ if (dfdp) {
+ EmulatedDriver *emul_driver = dfdp->getDriver();
+ return emul_driver->mmap(p, tc, start, length, prot,
tgt_flags, tgt_fd, offset);
}
- sim_fd = fde->fd;
- if (sim_fd < 0)
+ auto ffdp = std::dynamic_pointer_cast<FileFDEntry>(fdep);
+ if (!ffdp)
return -EBADF;
+ sim_fd = ffdp->getSimFD();
pmap = (decltype(pmap))mmap(NULL, length, PROT_READ, MAP_PRIVATE,
sim_fd, offset);
@@ -1393,9 +1394,9 @@ mmapImpl(SyscallDesc *desc, int num, Process *p, ThreadContext *tc,
Addr pc = tc->pcState().pc();
if (pc >= text_start && pc < text_end) {
- FDEntry *fde = p->getFDEntry(tgt_fd);
-
- ObjectFile *lib = createObjectFile(fde->filename);
+ std::shared_ptr<FDEntry> fdep = (*p->fds)[tgt_fd];
+ auto ffdp = std::dynamic_pointer_cast<FileFDEntry>(fdep);
+ ObjectFile *lib = createObjectFile(ffdp->getFileName());
if (lib) {
lib->loadAllSymbols(debugSymbolTable,
@@ -1422,9 +1423,10 @@ pwrite64Func(SyscallDesc *desc, int num, Process *p, ThreadContext *tc)
int nbytes = p->getSyscallArg(tc, index);
int offset = p->getSyscallArg(tc, index);
- int sim_fd = p->getSimFD(tgt_fd);
- if (sim_fd < 0)
+ auto ffdp = std::dynamic_pointer_cast<FileFDEntry>((*p->fds)[tgt_fd]);
+ if (!ffdp)
return -EBADF;
+ int sim_fd = ffdp->getSimFD();
BufferArg bufArg(bufPtr, nbytes);
bufArg.copyIn(tc->getMemProxy());