sim,sim-se: Fix restoring of VMAs of memory-mapped files
This patch fixes a problem that occurs when restoring from a checkpoint where Mapped File Buffers are not restored. This causes errors and unexpected behavior during further execution. Since the checkpoint already has the size of the area (address range) and the file name, only the offset is missing to restore the Mapped File Buffer. Having the offset value, it's possible to open those files for which an offset is specified and create a VMA with a Mapped File Buffer. Change-Id: Ib9dfa174cda6348b966b892184c36daeaba80e81 Signed-off-by: Emin Gadzhiev <e.gadzhiev.mhk@gmail.com> Issue-On: https://gem5.atlassian.net/browse/GEM5-1302 Reviewed-on: https://gem5-review.googlesource.com/c/public/gem5/+/66311 Reviewed-by: Jason Lowe-Power <power.jg@gmail.com> Tested-by: kokoro <noreply+kokoro@google.com> Maintainer: Jason Lowe-Power <power.jg@gmail.com>
This commit is contained in:
@@ -29,6 +29,9 @@
|
||||
#ifndef SRC_SIM_MEM_STATE_HH
|
||||
#define SRC_SIM_MEM_STATE_HH
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include <list>
|
||||
#include <memory>
|
||||
#include <string>
|
||||
@@ -199,6 +202,9 @@ class MemState : public Serializable
|
||||
for (auto vma : _vmaList) {
|
||||
ScopedCheckpointSection sec(cp, csprintf("Vma%d", count++));
|
||||
paramOut(cp, "name", vma.getName());
|
||||
if (vma.hasHostBuf()) {
|
||||
paramOut(cp, "fileOffset", vma.getFileMappingOffset());
|
||||
}
|
||||
paramOut(cp, "addrRangeStart", vma.start());
|
||||
paramOut(cp, "addrRangeEnd", vma.end());
|
||||
}
|
||||
@@ -223,10 +229,20 @@ class MemState : public Serializable
|
||||
std::string name;
|
||||
Addr start;
|
||||
Addr end;
|
||||
off_t offset = 0;
|
||||
int host_fd = -1;
|
||||
paramIn(cp, "name", name);
|
||||
if (optParamIn(cp, "fileOffset", offset, false)) {
|
||||
host_fd = open(name.c_str(), O_RDONLY);
|
||||
fatal_if(host_fd < 0,
|
||||
"Failed to open %s file "
|
||||
"while unserializing file-backed VMA\n", name);
|
||||
}
|
||||
paramIn(cp, "addrRangeStart", start);
|
||||
paramIn(cp, "addrRangeEnd", end);
|
||||
_vmaList.emplace_back(AddrRange(start, end), _pageBytes, name);
|
||||
_vmaList.emplace_back(AddrRange(start, end), _pageBytes, name,
|
||||
host_fd, offset);
|
||||
close(host_fd);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -120,7 +120,7 @@ VMA::sanityCheck()
|
||||
|
||||
VMA::MappedFileBuffer::MappedFileBuffer(int fd, size_t length,
|
||||
off_t offset)
|
||||
: _buffer(nullptr), _length(length)
|
||||
: _buffer(nullptr), _length(length), _offset(offset)
|
||||
{
|
||||
panic_if(_length == 0, "Tried to mmap file of length zero");
|
||||
|
||||
|
||||
@@ -105,6 +105,10 @@ class VMA
|
||||
void sliceRegionLeft(Addr slice_addr);
|
||||
|
||||
const std::string& getName() { return _vmaName; }
|
||||
off_t getFileMappingOffset() const
|
||||
{
|
||||
return hasHostBuf() ? _origHostBuf->getOffset() : 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Defer AddrRange related calls to the AddrRange.
|
||||
@@ -191,10 +195,12 @@ class VMA
|
||||
|
||||
void *getBuffer() const { return _buffer; }
|
||||
uint64_t getLength() const { return _length; }
|
||||
off_t getOffset() const { return _offset; }
|
||||
|
||||
private:
|
||||
void *_buffer; // Host buffer ptr
|
||||
size_t _length; // Length of host ptr
|
||||
off_t _offset; // Offset in file at which mapping starts
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
Reference in New Issue
Block a user