Lots of fixes to serialization and naming of various device
objects. The improper serialization of arrays was particularly bad. dev/alpha_console.cc: dev/isa_fake.cc: dev/ns_gige.cc: dev/pciconfigall.cc: dev/tsunami_cchip.cc: dev/tsunami_io.cc: dev/tsunami_pchip.cc: the pio interface is a different simobject and should have a different name. dev/ethertap.cc: fix serialization. dev/ide_ctrl.cc: - the pio interface is a different simobject and should have a different name. - properly initialize variables - When serializing an array, the size is the number of elements, not the number of bytes! dev/pcidev.cc: When serializing an array, the size is the number of elements, not the number of bytes! dev/tsunami_io.hh: Don't make objects SimObjects if they're not exposed to python. Don't add serialization functions to events, it's generally not what you want. allow the real time clock and interval timer to serialize themselves, must pass a base name since it is not a SimObject and the values will be going into the section of the parent. --HG-- extra : convert_revision : 3fc5de9b858ed770c8f385cf38b53242cf859c33
This commit is contained in:
parent
1771ee203f
commit
c761aaae65
11 changed files with 157 additions and 192 deletions
|
@ -63,7 +63,7 @@ AlphaConsole::AlphaConsole(const string &name, SimConsole *cons, SimpleDisk *d,
|
|||
mmu->add_child(this, RangeSize(addr, size));
|
||||
|
||||
if (bus) {
|
||||
pioInterface = newPioInterface(name, hier, bus, this,
|
||||
pioInterface = newPioInterface(name + ".pio", hier, bus, this,
|
||||
&AlphaConsole::cacheAccess);
|
||||
pioInterface->addAddrRange(RangeSize(addr, size));
|
||||
}
|
||||
|
|
|
@ -270,7 +270,8 @@ EtherTap::serialize(ostream &os)
|
|||
{
|
||||
SERIALIZE_SCALAR(socket);
|
||||
SERIALIZE_SCALAR(buflen);
|
||||
SERIALIZE_ARRAY((uint8_t *)buffer,buflen);
|
||||
uint8_t *buffer = (uint8_t *)this->buffer;
|
||||
SERIALIZE_ARRAY(buffer, buflen);
|
||||
SERIALIZE_SCALAR(buffer_offset);
|
||||
SERIALIZE_SCALAR(data_len);
|
||||
|
||||
|
@ -290,7 +291,8 @@ EtherTap::unserialize(Checkpoint *cp, const std::string §ion)
|
|||
{
|
||||
UNSERIALIZE_SCALAR(socket);
|
||||
UNSERIALIZE_SCALAR(buflen);
|
||||
UNSERIALIZE_ARRAY((uint8_t *)buffer,buflen);
|
||||
uint8_t *buffer = (uint8_t *)this->buffer;
|
||||
UNSERIALIZE_ARRAY(buffer, buflen);
|
||||
UNSERIALIZE_SCALAR(buffer_offset);
|
||||
UNSERIALIZE_SCALAR(data_len);
|
||||
|
||||
|
|
|
@ -92,7 +92,7 @@ IdeController::IdeController(Params *p)
|
|||
|
||||
// create the PIO and DMA interfaces
|
||||
if (params()->host_bus) {
|
||||
pioInterface = newPioInterface(name(), params()->hier,
|
||||
pioInterface = newPioInterface(name() + ".pio", params()->hier,
|
||||
params()->host_bus, this,
|
||||
&IdeController::cacheAccess);
|
||||
|
||||
|
@ -101,10 +101,13 @@ IdeController::IdeController(Params *p)
|
|||
params()->host_bus, 1,
|
||||
true);
|
||||
pioLatency = params()->pio_latency * params()->host_bus->clockRate;
|
||||
} else {
|
||||
pioInterface = NULL;
|
||||
dmaInterface = NULL;
|
||||
}
|
||||
|
||||
// setup the disks attached to controller
|
||||
memset(disks, 0, sizeof(IdeDisk *) * 4);
|
||||
memset(disks, 0, sizeof(disks));
|
||||
dev[0] = 0;
|
||||
dev[1] = 0;
|
||||
|
||||
|
@ -648,14 +651,17 @@ IdeController::serialize(std::ostream &os)
|
|||
SERIALIZE_SCALAR(bmi_size);
|
||||
|
||||
// Serialize registers
|
||||
SERIALIZE_ARRAY(bmi_regs.data, sizeof(bmi_regs));
|
||||
SERIALIZE_ARRAY(dev, sizeof(dev));
|
||||
SERIALIZE_ARRAY(config_regs.data, sizeof(config_regs));
|
||||
SERIALIZE_ARRAY(bmi_regs.data,
|
||||
sizeof(bmi_regs.data) / sizeof(bmi_regs.data[0]));
|
||||
SERIALIZE_ARRAY(dev, sizeof(dev) / sizeof(dev[0]));
|
||||
SERIALIZE_ARRAY(config_regs.data,
|
||||
sizeof(config_regs.data) / sizeof(config_regs.data[0]));
|
||||
|
||||
// Serialize internal state
|
||||
SERIALIZE_SCALAR(io_enabled);
|
||||
SERIALIZE_SCALAR(bm_enabled);
|
||||
SERIALIZE_ARRAY(cmd_in_progress, sizeof(cmd_in_progress));
|
||||
SERIALIZE_ARRAY(cmd_in_progress,
|
||||
sizeof(cmd_in_progress) / sizeof(cmd_in_progress[0]));
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -677,14 +683,17 @@ IdeController::unserialize(Checkpoint *cp, const std::string §ion)
|
|||
UNSERIALIZE_SCALAR(bmi_size);
|
||||
|
||||
// Unserialize registers
|
||||
UNSERIALIZE_ARRAY(bmi_regs.data, sizeof(bmi_regs));
|
||||
UNSERIALIZE_ARRAY(dev, sizeof(dev));
|
||||
UNSERIALIZE_ARRAY(config_regs.data, sizeof(config_regs));
|
||||
UNSERIALIZE_ARRAY(bmi_regs.data,
|
||||
sizeof(bmi_regs.data) / sizeof(bmi_regs.data[0]));
|
||||
UNSERIALIZE_ARRAY(dev, sizeof(dev) / sizeof(dev[0]));
|
||||
UNSERIALIZE_ARRAY(config_regs.data,
|
||||
sizeof(config_regs.data) / sizeof(config_regs.data[0]));
|
||||
|
||||
// Unserialize internal state
|
||||
UNSERIALIZE_SCALAR(io_enabled);
|
||||
UNSERIALIZE_SCALAR(bm_enabled);
|
||||
UNSERIALIZE_ARRAY(cmd_in_progress, sizeof(cmd_in_progress));
|
||||
UNSERIALIZE_ARRAY(cmd_in_progress,
|
||||
sizeof(cmd_in_progress) / sizeof(cmd_in_progress[0]));
|
||||
|
||||
if (pioInterface) {
|
||||
pioInterface->addAddrRange(RangeSize(pri_cmd_addr, pri_cmd_size));
|
||||
|
|
|
@ -53,7 +53,7 @@ IsaFake::IsaFake(const string &name, Addr a, MemoryController *mmu,
|
|||
mmu->add_child(this, RangeSize(addr, size));
|
||||
|
||||
if (bus) {
|
||||
pioInterface = newPioInterface(name, hier, bus, this,
|
||||
pioInterface = newPioInterface(name + ".pio", hier, bus, this,
|
||||
&IsaFake::cacheAccess);
|
||||
pioInterface->addAddrRange(RangeSize(addr, size));
|
||||
}
|
||||
|
|
|
@ -110,7 +110,7 @@ NSGigE::NSGigE(Params *p)
|
|||
intrEvent(0), interface(0)
|
||||
{
|
||||
if (p->header_bus) {
|
||||
pioInterface = newPioInterface(name(), p->hier,
|
||||
pioInterface = newPioInterface(name() + ".pio", p->hier,
|
||||
p->header_bus, this,
|
||||
&NSGigE::cacheAccess);
|
||||
|
||||
|
@ -127,7 +127,7 @@ NSGigE::NSGigE(Params *p)
|
|||
p->header_bus, 1,
|
||||
p->dma_no_allocate);
|
||||
} else if (p->payload_bus) {
|
||||
pioInterface = newPioInterface(name(), p->hier,
|
||||
pioInterface = newPioInterface(name() + ".pio2", p->hier,
|
||||
p->payload_bus, this,
|
||||
&NSGigE::cacheAccess);
|
||||
|
||||
|
|
|
@ -56,7 +56,7 @@ PciConfigAll::PciConfigAll(const string &name,
|
|||
mmu->add_child(this, RangeSize(addr, size));
|
||||
|
||||
if (bus) {
|
||||
pioInterface = newPioInterface(name, hier, bus, this,
|
||||
pioInterface = newPioInterface(name + ".pio", hier, bus, this,
|
||||
&PciConfigAll::cacheAccess);
|
||||
pioInterface->addAddrRange(RangeSize(addr, size));
|
||||
pioLatency = pio_latency * bus->clockRate;
|
||||
|
|
|
@ -228,17 +228,18 @@ PciDev::writeConfig(int offset, int size, const uint8_t *data)
|
|||
void
|
||||
PciDev::serialize(ostream &os)
|
||||
{
|
||||
SERIALIZE_ARRAY(BARSize, sizeof(BARSize));
|
||||
SERIALIZE_ARRAY(BARAddrs, sizeof(BARAddrs));
|
||||
SERIALIZE_ARRAY(config.data, sizeof(config.data));
|
||||
SERIALIZE_ARRAY(BARSize, sizeof(BARSize) / sizeof(BARSize[0]));
|
||||
SERIALIZE_ARRAY(BARAddrs, sizeof(BARAddrs) / sizeof(BARAddrs[0]));
|
||||
SERIALIZE_ARRAY(config.data, sizeof(config.data) / sizeof(config.data[0]));
|
||||
}
|
||||
|
||||
void
|
||||
PciDev::unserialize(Checkpoint *cp, const std::string §ion)
|
||||
{
|
||||
UNSERIALIZE_ARRAY(BARSize, sizeof(BARSize));
|
||||
UNSERIALIZE_ARRAY(BARAddrs, sizeof(BARAddrs));
|
||||
UNSERIALIZE_ARRAY(config.data, sizeof(config.data));
|
||||
UNSERIALIZE_ARRAY(BARSize, sizeof(BARSize) / sizeof(BARSize[0]));
|
||||
UNSERIALIZE_ARRAY(BARAddrs, sizeof(BARAddrs) / sizeof(BARAddrs[0]));
|
||||
UNSERIALIZE_ARRAY(config.data,
|
||||
sizeof(config.data) / sizeof(config.data[0]));
|
||||
|
||||
// Add the MMU mappings for the BARs
|
||||
for (int i=0; i < 6; i++) {
|
||||
|
|
|
@ -56,7 +56,7 @@ TsunamiCChip::TsunamiCChip(const string &name, Tsunami *t, Addr a,
|
|||
mmu->add_child(this, RangeSize(addr, size));
|
||||
|
||||
if (bus) {
|
||||
pioInterface = newPioInterface(name, hier, bus, this,
|
||||
pioInterface = newPioInterface(name + ".pio", hier, bus, this,
|
||||
&TsunamiCChip::cacheAccess);
|
||||
pioInterface->addAddrRange(RangeSize(addr, size));
|
||||
pioLatency = pio_latency * bus->clockRate;
|
||||
|
|
|
@ -51,8 +51,8 @@
|
|||
|
||||
using namespace std;
|
||||
|
||||
TsunamiIO::RTC::RTC(Tsunami* t, Tick i)
|
||||
: SimObject("RTC"), event(t, i), addr(0)
|
||||
TsunamiIO::RTC::RTC(const string &name, Tsunami* t, Tick i)
|
||||
: _name(name), event(t, i), addr(0)
|
||||
{
|
||||
memset(clock_data, 0, sizeof(clock_data));
|
||||
stat_regA = RTCA_32768HZ | RTCA_1024HZ;
|
||||
|
@ -142,28 +142,28 @@ TsunamiIO::RTC::readData(uint8_t *data)
|
|||
}
|
||||
|
||||
void
|
||||
TsunamiIO::RTC::serialize(std::ostream &os)
|
||||
TsunamiIO::RTC::serialize(const string &base, ostream &os)
|
||||
{
|
||||
SERIALIZE_SCALAR(addr);
|
||||
SERIALIZE_ARRAY(clock_data, sizeof(clock_data));
|
||||
SERIALIZE_SCALAR(stat_regA);
|
||||
SERIALIZE_SCALAR(stat_regB);
|
||||
|
||||
// serialize the RTC event
|
||||
nameOut(os, csprintf("%s.event", name()));
|
||||
event.serialize(os);
|
||||
paramOut(os, base + ".addr", addr);
|
||||
arrayParamOut(os, base + ".clock_data", clock_data, sizeof(clock_data));
|
||||
paramOut(os, base + ".stat_regA", stat_regA);
|
||||
paramOut(os, base + ".stat_regB", stat_regB);
|
||||
}
|
||||
|
||||
void
|
||||
TsunamiIO::RTC::unserialize(Checkpoint *cp, const std::string §ion)
|
||||
TsunamiIO::RTC::unserialize(const string &base, Checkpoint *cp,
|
||||
const string §ion)
|
||||
{
|
||||
UNSERIALIZE_SCALAR(addr);
|
||||
UNSERIALIZE_ARRAY(clock_data, sizeof(clock_data));
|
||||
UNSERIALIZE_SCALAR(stat_regA);
|
||||
UNSERIALIZE_SCALAR(stat_regB);
|
||||
paramIn(cp, section, base + ".addr", addr);
|
||||
arrayParamIn(cp, section, base + ".clock_data", clock_data,
|
||||
sizeof(clock_data));
|
||||
paramIn(cp, section, base + ".stat_regA", stat_regA);
|
||||
paramIn(cp, section, base + ".stat_regB", stat_regB);
|
||||
|
||||
// unserialze the event
|
||||
event.unserialize(cp, csprintf("%s.event", section));
|
||||
// We're not unserializing the event here, but we need to
|
||||
// rescehedule the event since curTick was moved forward by the
|
||||
// checkpoint
|
||||
event.reschedule(curTick + event.interval);
|
||||
}
|
||||
|
||||
TsunamiIO::RTC::RTCEvent::RTCEvent(Tsunami*t, Tick i)
|
||||
|
@ -194,26 +194,13 @@ TsunamiIO::RTC::RTCEvent::description()
|
|||
return "tsunami RTC interrupt";
|
||||
}
|
||||
|
||||
void
|
||||
TsunamiIO::RTC::RTCEvent::serialize(std::ostream &os)
|
||||
TsunamiIO::PITimer::PITimer(const string &name)
|
||||
: _name(name), counter0(name + ".counter0"), counter1(name + ".counter1"),
|
||||
counter2(name + ".counter2")
|
||||
{
|
||||
Tick time = when();
|
||||
SERIALIZE_SCALAR(time);
|
||||
}
|
||||
|
||||
void
|
||||
TsunamiIO::RTC::RTCEvent::unserialize(Checkpoint *cp, const std::string §ion)
|
||||
{
|
||||
Tick time;
|
||||
UNSERIALIZE_SCALAR(time);
|
||||
reschedule(time);
|
||||
}
|
||||
|
||||
TsunamiIO::PITimer::PITimer()
|
||||
: SimObject("PITimer"), counter0(counter[0]), counter1(counter[1]),
|
||||
counter2(counter[2])
|
||||
{
|
||||
|
||||
counter[0] = &counter0;
|
||||
counter[1] = &counter0;
|
||||
counter[2] = &counter0;
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -230,39 +217,35 @@ TsunamiIO::PITimer::writeControl(const uint8_t *data)
|
|||
rw = GET_CTRL_RW(*data);
|
||||
|
||||
if (rw == PIT_RW_LATCH_COMMAND)
|
||||
counter[sel].latchCount();
|
||||
counter[sel]->latchCount();
|
||||
else {
|
||||
counter[sel].setRW(rw);
|
||||
counter[sel].setMode(GET_CTRL_MODE(*data));
|
||||
counter[sel].setBCD(GET_CTRL_BCD(*data));
|
||||
counter[sel]->setRW(rw);
|
||||
counter[sel]->setMode(GET_CTRL_MODE(*data));
|
||||
counter[sel]->setBCD(GET_CTRL_BCD(*data));
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
TsunamiIO::PITimer::serialize(std::ostream &os)
|
||||
TsunamiIO::PITimer::serialize(const string &base, ostream &os)
|
||||
{
|
||||
// serialize the counters
|
||||
nameOut(os, csprintf("%s.counter0", name()));
|
||||
counter0.serialize(os);
|
||||
|
||||
nameOut(os, csprintf("%s.counter1", name()));
|
||||
counter1.serialize(os);
|
||||
|
||||
nameOut(os, csprintf("%s.counter2", name()));
|
||||
counter2.serialize(os);
|
||||
counter0.serialize(base + ".counter0", os);
|
||||
counter1.serialize(base + ".counter1", os);
|
||||
counter2.serialize(base + ".counter2", os);
|
||||
}
|
||||
|
||||
void
|
||||
TsunamiIO::PITimer::unserialize(Checkpoint *cp, const std::string §ion)
|
||||
TsunamiIO::PITimer::unserialize(const string &base, Checkpoint *cp,
|
||||
const string §ion)
|
||||
{
|
||||
// unserialze the counters
|
||||
counter0.unserialize(cp, csprintf("%s.counter0", section));
|
||||
counter1.unserialize(cp, csprintf("%s.counter1", section));
|
||||
counter2.unserialize(cp, csprintf("%s.counter2", section));
|
||||
counter0.unserialize(base + ".counter0", cp, section);
|
||||
counter1.unserialize(base + ".counter1", cp, section);
|
||||
counter2.unserialize(base + ".counter2", cp, section);
|
||||
}
|
||||
|
||||
TsunamiIO::PITimer::Counter::Counter()
|
||||
: SimObject("Counter"), event(this), count(0), latched_count(0), period(0),
|
||||
TsunamiIO::PITimer::Counter::Counter(const string &name)
|
||||
: _name(name), event(this), count(0), latched_count(0), period(0),
|
||||
mode(0), output_high(false), latch_on(false), read_byte(LSB),
|
||||
write_byte(LSB)
|
||||
{
|
||||
|
@ -327,7 +310,8 @@ TsunamiIO::PITimer::Counter::write(const uint8_t *data)
|
|||
period = count;
|
||||
|
||||
if (period > 0) {
|
||||
DPRINTF(Tsunami, "Timer set to curTick + %d\n", count * event.interval);
|
||||
DPRINTF(Tsunami, "Timer set to curTick + %d\n",
|
||||
count * event.interval);
|
||||
event.schedule(curTick + count * event.interval);
|
||||
}
|
||||
write_byte = LSB;
|
||||
|
@ -366,36 +350,40 @@ TsunamiIO::PITimer::Counter::outputHigh()
|
|||
}
|
||||
|
||||
void
|
||||
TsunamiIO::PITimer::Counter::serialize(std::ostream &os)
|
||||
TsunamiIO::PITimer::Counter::serialize(const string &base, ostream &os)
|
||||
{
|
||||
SERIALIZE_SCALAR(count);
|
||||
SERIALIZE_SCALAR(latched_count);
|
||||
SERIALIZE_SCALAR(period);
|
||||
SERIALIZE_SCALAR(mode);
|
||||
SERIALIZE_SCALAR(output_high);
|
||||
SERIALIZE_SCALAR(latch_on);
|
||||
SERIALIZE_SCALAR(read_byte);
|
||||
SERIALIZE_SCALAR(write_byte);
|
||||
paramOut(os, base + ".count", count);
|
||||
paramOut(os, base + ".latched_count", latched_count);
|
||||
paramOut(os, base + ".period", period);
|
||||
paramOut(os, base + ".mode", mode);
|
||||
paramOut(os, base + ".output_high", output_high);
|
||||
paramOut(os, base + ".latch_on", latch_on);
|
||||
paramOut(os, base + ".read_byte", read_byte);
|
||||
paramOut(os, base + ".write_byte", write_byte);
|
||||
|
||||
// serialize the counter event
|
||||
nameOut(os, csprintf("%s.event", name()));
|
||||
event.serialize(os);
|
||||
Tick event_tick = 0;
|
||||
if (event.scheduled())
|
||||
event_tick = event.when();
|
||||
paramOut(os, base + ".event_tick", event_tick);
|
||||
}
|
||||
|
||||
void
|
||||
TsunamiIO::PITimer::Counter::unserialize(Checkpoint *cp, const std::string §ion)
|
||||
TsunamiIO::PITimer::Counter::unserialize(const string &base, Checkpoint *cp,
|
||||
const string §ion)
|
||||
{
|
||||
UNSERIALIZE_SCALAR(count);
|
||||
UNSERIALIZE_SCALAR(latched_count);
|
||||
UNSERIALIZE_SCALAR(period);
|
||||
UNSERIALIZE_SCALAR(mode);
|
||||
UNSERIALIZE_SCALAR(output_high);
|
||||
UNSERIALIZE_SCALAR(latch_on);
|
||||
UNSERIALIZE_SCALAR(read_byte);
|
||||
UNSERIALIZE_SCALAR(write_byte);
|
||||
paramIn(cp, section, base + ".count", count);
|
||||
paramIn(cp, section, base + ".latched_count", latched_count);
|
||||
paramIn(cp, section, base + ".period", period);
|
||||
paramIn(cp, section, base + ".mode", mode);
|
||||
paramIn(cp, section, base + ".output_high", output_high);
|
||||
paramIn(cp, section, base + ".latch_on", latch_on);
|
||||
paramIn(cp, section, base + ".read_byte", read_byte);
|
||||
paramIn(cp, section, base + ".write_byte", write_byte);
|
||||
|
||||
// unserialze the counter event
|
||||
event.unserialize(cp, csprintf("%s.event", section));
|
||||
Tick event_tick;
|
||||
paramIn(cp, section, base + ".event_tick", event_tick);
|
||||
if (event_tick)
|
||||
event.schedule(event_tick);
|
||||
}
|
||||
|
||||
TsunamiIO::PITimer::Counter::CounterEvent::CounterEvent(Counter* c_ptr)
|
||||
|
@ -426,33 +414,16 @@ TsunamiIO::PITimer::Counter::CounterEvent::description()
|
|||
return "tsunami 8254 Interval timer";
|
||||
}
|
||||
|
||||
void
|
||||
TsunamiIO::PITimer::Counter::CounterEvent::serialize(std::ostream &os)
|
||||
{
|
||||
Tick time = scheduled() ? when() : 0;
|
||||
SERIALIZE_SCALAR(time);
|
||||
SERIALIZE_SCALAR(interval);
|
||||
}
|
||||
|
||||
void
|
||||
TsunamiIO::PITimer::Counter::CounterEvent::unserialize(Checkpoint *cp, const std::string §ion)
|
||||
{
|
||||
Tick time;
|
||||
UNSERIALIZE_SCALAR(time);
|
||||
UNSERIALIZE_SCALAR(interval);
|
||||
if (time)
|
||||
schedule(time);
|
||||
}
|
||||
|
||||
TsunamiIO::TsunamiIO(const string &name, Tsunami *t, time_t init_time,
|
||||
Addr a, MemoryController *mmu, HierParams *hier, Bus *bus,
|
||||
Tick pio_latency, Tick ci)
|
||||
: PioDevice(name, t), addr(a), clockInterval(ci), tsunami(t), rtc(t, ci)
|
||||
: PioDevice(name, t), addr(a), clockInterval(ci), tsunami(t),
|
||||
pitimer(name + "pitimer"), rtc(name + ".rtc", t, ci)
|
||||
{
|
||||
mmu->add_child(this, RangeSize(addr, size));
|
||||
|
||||
if (bus) {
|
||||
pioInterface = newPioInterface(name, hier, bus, this,
|
||||
pioInterface = newPioInterface(name + ".pio", hier, bus, this,
|
||||
&TsunamiIO::cacheAccess);
|
||||
pioInterface->addAddrRange(RangeSize(addr, size));
|
||||
pioLatency = pio_latency * bus->clockRate;
|
||||
|
@ -680,7 +651,7 @@ TsunamiIO::cacheAccess(MemReqPtr &req)
|
|||
}
|
||||
|
||||
void
|
||||
TsunamiIO::serialize(std::ostream &os)
|
||||
TsunamiIO::serialize(ostream &os)
|
||||
{
|
||||
SERIALIZE_SCALAR(timerData);
|
||||
SERIALIZE_SCALAR(mask1);
|
||||
|
@ -691,14 +662,12 @@ TsunamiIO::serialize(std::ostream &os)
|
|||
SERIALIZE_SCALAR(picInterrupting);
|
||||
|
||||
// Serialize the timers
|
||||
nameOut(os, csprintf("%s.pitimer", name()));
|
||||
pitimer.serialize(os);
|
||||
nameOut(os, csprintf("%s.rtc", name()));
|
||||
rtc.serialize(os);
|
||||
pitimer.serialize("pitimer", os);
|
||||
rtc.serialize("rtc", os);
|
||||
}
|
||||
|
||||
void
|
||||
TsunamiIO::unserialize(Checkpoint *cp, const std::string §ion)
|
||||
TsunamiIO::unserialize(Checkpoint *cp, const string §ion)
|
||||
{
|
||||
UNSERIALIZE_SCALAR(timerData);
|
||||
UNSERIALIZE_SCALAR(mask1);
|
||||
|
@ -709,8 +678,8 @@ TsunamiIO::unserialize(Checkpoint *cp, const std::string §ion)
|
|||
UNSERIALIZE_SCALAR(picInterrupting);
|
||||
|
||||
// Unserialize the timers
|
||||
pitimer.unserialize(cp, csprintf("%s.pitimer", section));
|
||||
rtc.unserialize(cp, csprintf("%s.rtc", section));
|
||||
pitimer.unserialize("pitimer", cp, section);
|
||||
rtc.unserialize("rtc", cp, section);
|
||||
}
|
||||
|
||||
BEGIN_DECLARE_SIM_OBJECT_PARAMS(TsunamiIO)
|
||||
|
|
|
@ -54,45 +54,33 @@ class TsunamiIO : public PioDevice
|
|||
struct tm tm;
|
||||
|
||||
protected:
|
||||
|
||||
/** Real-Time Clock (MC146818) */
|
||||
class RTC : public SimObject
|
||||
class RTC
|
||||
{
|
||||
/** Event for RTC periodic interrupt */
|
||||
class RTCEvent : public Event
|
||||
{
|
||||
private:
|
||||
/** A pointer back to tsunami to create interrupt the processor. */
|
||||
Tsunami* tsunami;
|
||||
Tick interval;
|
||||
private:
|
||||
/** Event for RTC periodic interrupt */
|
||||
struct RTCEvent : public Event
|
||||
{
|
||||
/** A pointer back to tsunami to create interrupt the processor. */
|
||||
Tsunami* tsunami;
|
||||
Tick interval;
|
||||
|
||||
public:
|
||||
RTCEvent(Tsunami* t, Tick i);
|
||||
RTCEvent(Tsunami* t, Tick i);
|
||||
|
||||
/** Schedule the RTC periodic interrupt */
|
||||
void scheduleIntr();
|
||||
/** Schedule the RTC periodic interrupt */
|
||||
void scheduleIntr();
|
||||
|
||||
/** Event process to occur at interrupt*/
|
||||
virtual void process();
|
||||
/** Event process to occur at interrupt*/
|
||||
virtual void process();
|
||||
|
||||
/** Event description */
|
||||
virtual const char *description();
|
||||
|
||||
/**
|
||||
* Serialize this object to the given output stream.
|
||||
* @param os The stream to serialize to.
|
||||
*/
|
||||
virtual void serialize(std::ostream &os);
|
||||
|
||||
/**
|
||||
* Reconstruct the state of this object from a checkpoint.
|
||||
* @param cp The checkpoint use.
|
||||
* @param section The section name of this object
|
||||
*/
|
||||
virtual void unserialize(Checkpoint *cp, const std::string §ion);
|
||||
};
|
||||
/** Event description */
|
||||
virtual const char *description();
|
||||
};
|
||||
|
||||
private:
|
||||
std::string _name;
|
||||
const std::string &name() const { return _name; }
|
||||
|
||||
/** RTC periodic interrupt event */
|
||||
RTCEvent event;
|
||||
|
||||
|
@ -124,7 +112,7 @@ class TsunamiIO : public PioDevice
|
|||
uint8_t stat_regB;
|
||||
|
||||
public:
|
||||
RTC(Tsunami* t, Tick i);
|
||||
RTC(const std::string &name, Tsunami* t, Tick i);
|
||||
|
||||
/** Set the initial RTC time/date */
|
||||
void set_time(time_t t);
|
||||
|
@ -142,21 +130,22 @@ class TsunamiIO : public PioDevice
|
|||
* Serialize this object to the given output stream.
|
||||
* @param os The stream to serialize to.
|
||||
*/
|
||||
virtual void serialize(std::ostream &os);
|
||||
void serialize(const std::string &base, std::ostream &os);
|
||||
|
||||
/**
|
||||
* Reconstruct the state of this object from a checkpoint.
|
||||
* @param cp The checkpoint use.
|
||||
* @param section The section name of this object
|
||||
*/
|
||||
virtual void unserialize(Checkpoint *cp, const std::string §ion);
|
||||
void unserialize(const std::string &base, Checkpoint *cp,
|
||||
const std::string §ion);
|
||||
};
|
||||
|
||||
/** Programmable Interval Timer (Intel 8254) */
|
||||
class PITimer : public SimObject
|
||||
class PITimer
|
||||
{
|
||||
/** Counter element for PIT */
|
||||
class Counter : public SimObject
|
||||
class Counter
|
||||
{
|
||||
/** Event for counter interrupt */
|
||||
class CounterEvent : public Event
|
||||
|
@ -175,23 +164,13 @@ class TsunamiIO : public PioDevice
|
|||
/** Event description */
|
||||
virtual const char *description();
|
||||
|
||||
/**
|
||||
* Serialize this object to the given output stream.
|
||||
* @param os The stream to serialize to.
|
||||
*/
|
||||
virtual void serialize(std::ostream &os);
|
||||
|
||||
/**
|
||||
* Reconstruct the state of this object from a checkpoint.
|
||||
* @param cp The checkpoint use.
|
||||
* @param section The section name of this object
|
||||
*/
|
||||
virtual void unserialize(Checkpoint *cp, const std::string §ion);
|
||||
|
||||
friend class Counter;
|
||||
};
|
||||
|
||||
private:
|
||||
std::string _name;
|
||||
const std::string &name() const { return _name; }
|
||||
|
||||
CounterEvent event;
|
||||
|
||||
/** Current count value */
|
||||
|
@ -219,7 +198,7 @@ class TsunamiIO : public PioDevice
|
|||
uint8_t read_byte, write_byte;
|
||||
|
||||
public:
|
||||
Counter();
|
||||
Counter(const std::string &name);
|
||||
|
||||
/** Latch the current count (if one is not already latched) */
|
||||
void latchCount();
|
||||
|
@ -246,27 +225,31 @@ class TsunamiIO : public PioDevice
|
|||
* Serialize this object to the given output stream.
|
||||
* @param os The stream to serialize to.
|
||||
*/
|
||||
virtual void serialize(std::ostream &os);
|
||||
void serialize(const std::string &base, std::ostream &os);
|
||||
|
||||
/**
|
||||
* Reconstruct the state of this object from a checkpoint.
|
||||
* @param cp The checkpoint use.
|
||||
* @param section The section name of this object
|
||||
*/
|
||||
virtual void unserialize(Checkpoint *cp, const std::string §ion);
|
||||
void unserialize(const std::string &base, Checkpoint *cp,
|
||||
const std::string §ion);
|
||||
};
|
||||
|
||||
private:
|
||||
std::string _name;
|
||||
const std::string &name() const { return _name; }
|
||||
|
||||
/** PIT has three seperate counters */
|
||||
Counter counter[3];
|
||||
Counter *counter[3];
|
||||
|
||||
public:
|
||||
/** Public way to access individual counters (avoid array accesses) */
|
||||
Counter &counter0;
|
||||
Counter &counter1;
|
||||
Counter &counter2;
|
||||
Counter counter0;
|
||||
Counter counter1;
|
||||
Counter counter2;
|
||||
|
||||
PITimer();
|
||||
PITimer(const std::string &name);
|
||||
|
||||
/** Write control word */
|
||||
void writeControl(const uint8_t* data);
|
||||
|
@ -275,14 +258,15 @@ class TsunamiIO : public PioDevice
|
|||
* Serialize this object to the given output stream.
|
||||
* @param os The stream to serialize to.
|
||||
*/
|
||||
virtual void serialize(std::ostream &os);
|
||||
void serialize(const std::string &base, std::ostream &os);
|
||||
|
||||
/**
|
||||
* Reconstruct the state of this object from a checkpoint.
|
||||
* @param cp The checkpoint use.
|
||||
* @param section The section name of this object
|
||||
*/
|
||||
virtual void unserialize(Checkpoint *cp, const std::string §ion);
|
||||
void unserialize(const std::string &base, Checkpoint *cp,
|
||||
const std::string §ion);
|
||||
};
|
||||
|
||||
/** Mask of the PIC1 */
|
||||
|
|
|
@ -62,7 +62,7 @@ TsunamiPChip::TsunamiPChip(const string &name, Tsunami *t, Addr a,
|
|||
}
|
||||
|
||||
if (bus) {
|
||||
pioInterface = newPioInterface(name, hier, bus, this,
|
||||
pioInterface = newPioInterface(name + ".pio", hier, bus, this,
|
||||
&TsunamiPChip::cacheAccess);
|
||||
pioInterface->addAddrRange(RangeSize(addr, size));
|
||||
pioLatency = pio_latency * bus->clockRate;
|
||||
|
|
Loading…
Reference in a new issue