-PhysicalMemory::getAddressRanges(AddrRangeList &resp, bool &snoop)
-{
- snoop = false;
- resp.clear();
- resp.push_back(RangeSize(start(), params()->range.size()));
-}
-
-int
-PhysicalMemory::MemoryPort::deviceBlockSize()
-{
- return memory->deviceBlockSize();
-}
-
-Tick
-PhysicalMemory::MemoryPort::recvAtomic(PacketPtr pkt)
-{
- return memory->doAtomicAccess(pkt);
-}
-
-void
-PhysicalMemory::MemoryPort::recvFunctional(PacketPtr pkt)
-{
- pkt->pushLabel(memory->name());
-
- if (!checkFunctional(pkt)) {
- // Default implementation of SimpleTimingPort::recvFunctional()
- // calls recvAtomic() and throws away the latency; we can save a
- // little here by just not calculating the latency.
- memory->doFunctionalAccess(pkt);
- }
-
- pkt->popLabel();
-}
-
-unsigned int
-PhysicalMemory::drain(Event *de)
-{
- int count = 0;
- for (PortIterator pi = ports.begin(); pi != ports.end(); ++pi) {
- count += (*pi)->drain(de);
- }
-
- if (count)
- changeState(Draining);
- else
- changeState(Drained);
- return count;
-}
-
-void
-PhysicalMemory::serialize(ostream &os)
-{
- if (!pmemAddr)
- return;
-
- gzFile compressedMem;
- string filename = name() + ".physmem";
-
- SERIALIZE_SCALAR(filename);
-
- // write memory file
- string thefile = Checkpoint::dir() + "/" + filename.c_str();
- int fd = creat(thefile.c_str(), 0664);
- if (fd < 0) {
- perror("creat");
- fatal("Can't open physical memory checkpoint file '%s'\n", filename);
- }
-
- compressedMem = gzdopen(fd, "wb");
- if (compressedMem == NULL)
- fatal("Insufficient memory to allocate compression state for %s\n",
- filename);
-
- if (gzwrite(compressedMem, pmemAddr, params()->range.size()) !=
- params()->range.size()) {
- fatal("Write failed on physical memory checkpoint file '%s'\n",
- filename);
- }
-
- if (gzclose(compressedMem))
- fatal("Close failed on physical memory checkpoint file '%s'\n",
- filename);
-}
-
-void
-PhysicalMemory::unserialize(Checkpoint *cp, const string §ion)
-{
- if (!pmemAddr)
- return;
-
- gzFile compressedMem;
- long *tempPage;
- long *pmem_current;
- uint64_t curSize;
- uint32_t bytesRead;
- const int chunkSize = 16384;
-
- string filename;
-
- UNSERIALIZE_SCALAR(filename);
-
- filename = cp->cptDir + "/" + filename;
-
- // mmap memoryfile
- int fd = open(filename.c_str(), O_RDONLY);
- if (fd < 0) {
- perror("open");
- fatal("Can't open physical memory checkpoint file '%s'", filename);
- }
-
- compressedMem = gzdopen(fd, "rb");
- if (compressedMem == NULL)
- fatal("Insufficient memory to allocate compression state for %s\n",
- filename);
-
- // unmap file that was mmaped in the constructor
- // This is done here to make sure that gzip and open don't muck with our
- // nice large space of memory before we reallocate it
- munmap((char*)pmemAddr, params()->range.size());
-
- pmemAddr = (uint8_t *)mmap(NULL, params()->range.size(),
- PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE, -1, 0);
-
- if (pmemAddr == (void *)MAP_FAILED) {
- perror("mmap");
- fatal("Could not mmap physical memory!\n");
- }
-
- curSize = 0;
- tempPage = (long*)malloc(chunkSize);
- if (tempPage == NULL)
- fatal("Unable to malloc memory to read file %s\n", filename);
-
- /* Only copy bytes that are non-zero, so we don't give the VM system hell */
- while (curSize < params()->range.size()) {
- bytesRead = gzread(compressedMem, tempPage, chunkSize);
- if (bytesRead != chunkSize &&
- bytesRead != params()->range.size() - curSize)
- fatal("Read failed on physical memory checkpoint file '%s'"
- " got %d bytes, expected %d or %d bytes\n",
- filename, bytesRead, chunkSize,
- params()->range.size() - curSize);
-
- assert(bytesRead % sizeof(long) == 0);
-
- for (int x = 0; x < bytesRead/sizeof(long); x++)
- {
- if (*(tempPage+x) != 0) {
- pmem_current = (long*)(pmemAddr + curSize + x * sizeof(long));
- *pmem_current = *(tempPage+x);
- }
- }
- curSize += bytesRead;
- }
-
- free(tempPage);
-
- if (gzclose(compressedMem))
- fatal("Close failed on physical memory checkpoint file '%s'\n",
- filename);
-
-}
-
-PhysicalMemory *
-PhysicalMemoryParams::create()