45 #include "params/Process.hh"
52 std::string
const& errout)
53 : _fdArray(), _input(input), _output(
output), _errout(errout),
55 {
"cin", STDIN_FILENO},
56 {
"stdin", STDIN_FILENO}},
58 {
"cout", STDOUT_FILENO},
59 {
"stdout", STDOUT_FILENO},
60 {
"cerr", STDERR_FILENO},
61 {
"stderr", STDERR_FILENO}}
64 std::map<std::string, int>::iterator it;
70 if ((it = _imap.find(input)) != _imap.end())
73 sim_fd = openInputFile(input);
75 auto ffd = std::make_shared<FileFDEntry>(sim_fd, O_RDONLY, input,
false);
76 _fdArray[STDIN_FILENO] = ffd;
82 if ((it = _oemap.find(
output)) != _oemap.end())
85 sim_fd = openOutputFile(
output);
87 ffd = std::make_shared<FileFDEntry>(sim_fd, O_WRONLY | O_CREAT | O_TRUNC,
89 _fdArray[STDOUT_FILENO] = ffd;
93 else if ((it = _oemap.find(errout)) != _oemap.end())
96 sim_fd = openOutputFile(errout);
98 ffd = std::make_shared<FileFDEntry>(sim_fd, O_WRONLY | O_CREAT | O_TRUNC,
100 _fdArray[STDERR_FILENO] = ffd;
112 auto ffd = std::dynamic_pointer_cast<FileFDEntry>(fdp);
121 int sim_fd = ffd->getSimFD();
122 ffd->setFileOffset(lseek(sim_fd, 0, SEEK_CUR));
136 auto seek = [] (std::shared_ptr<FileFDEntry> ffd)
138 if (lseek(ffd->getSimFD(), ffd->getFileOffset(), SEEK_SET) < 0)
139 fatal(
"Unable to seek to location in %s", ffd->getFileName());
142 std::map<std::string, int>::iterator it;
151 std::shared_ptr<FDEntry> stdin_fde =
_fdArray[STDIN_FILENO];
152 auto stdin_ffd = std::dynamic_pointer_cast<FileFDEntry>(stdin_fde);
154 if (
_input != stdin_ffd->getFileName()) {
155 warn(
"Using new input file (%s) rather than checkpointed (%s)\n",
156 _input, stdin_ffd->getFileName());
157 stdin_ffd->setFileName(
_input);
158 stdin_ffd->setFileOffset(0);
161 if ((it =
_imap.find(stdin_ffd->getFileName())) !=
_imap.end()) {
162 stdin_ffd->setSimFD(it->second);
164 stdin_ffd->setSimFD(
openInputFile(stdin_ffd->getFileName()));
175 std::shared_ptr<FDEntry> stdout_fde =
_fdArray[STDOUT_FILENO];
176 auto stdout_ffd = std::dynamic_pointer_cast<FileFDEntry>(stdout_fde);
178 if (
_output != stdout_ffd->getFileName()) {
179 warn(
"Using new output file (%s) rather than checkpointed (%s)\n",
180 _output, stdout_ffd->getFileName());
181 stdout_ffd->setFileName(
_output);
182 stdout_ffd->setFileOffset(0);
185 if ((it =
_oemap.find(stdout_ffd->getFileName())) !=
_oemap.end()) {
186 stdout_ffd->setSimFD(it->second);
199 std::shared_ptr<FDEntry> stderr_fde =
_fdArray[STDERR_FILENO];
200 auto stderr_ffd = std::dynamic_pointer_cast<FileFDEntry>(stderr_fde);
202 if (
_errout != stderr_ffd->getFileName()) {
203 warn(
"Using new error file (%s) rather than checkpointed (%s)\n",
204 _errout, stderr_ffd->getFileName());
205 stderr_ffd->setFileName(
_errout);
206 stderr_ffd->setFileOffset(0);
209 if (stdout_ffd->getFileName() == stderr_ffd->getFileName()) {
211 stderr_ffd->setSimFD(stdout_ffd->getSimFD());
212 }
else if ((it =
_oemap.find(stderr_ffd->getFileName())) !=
_oemap.end()) {
213 stderr_ffd->setSimFD(it->second);
219 for (
int tgt_fd = 3; tgt_fd <
_fdArray.size(); tgt_fd++) {
220 std::shared_ptr<FDEntry> fdp =
_fdArray[tgt_fd];
225 if (
auto pfd = std::dynamic_pointer_cast<PipeFDEntry>(fdp)) {
231 if (pfd->getEndType() == PipeFDEntry::EndType::write)
236 if (pipe(fd_pair) < 0)
237 fatal(
"Unable to create new pipe");
243 pfd->setSimFD(fd_pair[0]);
249 int prs = pfd->getPipeReadSource();
250 std::shared_ptr<FDEntry> write_fdp =
_fdArray[prs];
253 auto write_pfd = std::dynamic_pointer_cast<PipeFDEntry>(write_fdp);
256 write_pfd->setSimFD(fd_pair[1]);
260 if (
auto dfd = std::dynamic_pointer_cast<DeviceFDEntry>(fdp)) {
266 fatal(
"Unable to restore checkpoints with emulated drivers");
270 if (
auto ffd = std::dynamic_pointer_cast<FileFDEntry>(fdp)) {
278 int sim_fd =
openFile(ffd->getFileName(), ffd->getFlags(), 0664);
279 ffd->setSimFD(sim_fd);
289 std::shared_ptr<FDEntry> fdp =
_fdArray[
i];
295 fatal(
"Out of target file descriptors");
301 int sim_fd = open(filename.c_str(), flags,
mode);
304 fatal(
"Unable to open %s with mode %d", filename,
mode);
310 return openFile(filename, O_RDONLY, 00);
317 O_WRONLY | O_CREAT | O_TRUNC, 0664);
320 std::shared_ptr<FDEntry>
323 assert(0 <= tgt_fd && tgt_fd <
_fdArray.size());
330 assert(0 <= tgt_fd && tgt_fd <
_fdArray.size());
337 if (tgt_fd >=
_fdArray.size() || tgt_fd < 0)
341 auto hbfdp = std::dynamic_pointer_cast<HBFDEntry>(
_fdArray[tgt_fd]);
343 sim_fd = hbfdp->getSimFD();
359 for (
int tgt_fd = 0; tgt_fd <
_fdArray.size(); tgt_fd++) {
363 paramOut(cp,
"class", FDEntry::FDClass::fd_null);
377 "FDArray sizes do not match at unserialize!");
379 for (
int tgt_fd = 0; tgt_fd <
_fdArray.size(); tgt_fd++) {
380 if (tgt_fd == STDIN_FILENO || tgt_fd == STDOUT_FILENO ||
381 tgt_fd == STDERR_FILENO)
385 paramIn(cp,
"class", fd_class);
386 std::shared_ptr<FDEntry> fdep;
389 case FDEntry::FDClass::fd_base:
390 panic(
"Abstract fd entry was serialized");
392 case FDEntry::FDClass::fd_hb:
393 fdep = std::make_shared<HBFDEntry>(0, 0);
395 case FDEntry::FDClass::fd_file:
396 fdep = std::make_shared<FileFDEntry>(0, 0,
"", 0, 00);
398 case FDEntry::FDClass::fd_device:
399 fdep = std::make_shared<DeviceFDEntry>(
nullptr,
"");
401 case FDEntry::FDClass::fd_pipe:
402 fdep = std::make_shared<PipeFDEntry>(
403 0, 0, PipeFDEntry::EndType::read);
405 case FDEntry::FDClass::fd_socket:
406 fdep = std::make_shared<SocketFDEntry>(0, 0, 0, 0);
408 case FDEntry::FDClass::fd_null:
411 panic(
"Unrecognized fd class");
415 fdep->unserialize(cp);
417 auto this_ffd = std::dynamic_pointer_cast<FileFDEntry>(fdep);
422 mode_t
mode = this_ffd->getFileMode();
423 std::string
const&
path = this_ffd->getFileName();
424 int flags = this_ffd->getFlags();
428 this_ffd->setSimFD(sim_fd);
431 uint64_t file_offset = this_ffd->getFileOffset();
432 lseek(sim_fd, file_offset, SEEK_SET);