#ifndef __DEV_8254_HH__
#define __DEV_8254_HH__
+#include <iostream>
+#include <string>
+
#include "base/bitunion.hh"
-#include "sim/eventq.hh"
-#include "sim/host.hh"
+#include "base/types.hh"
+#include "base/trace.hh"
+#include "debug/Intel8254Timer.hh"
+#include "sim/eventq_impl.hh"
#include "sim/serialize.hh"
-#include <string>
-#include <iostream>
-
/** Programmable Interval Timer (Intel 8254) */
-class Intel8254Timer
+class Intel8254Timer : public EventManager
{
+ protected:
BitUnion8(CtrlReg)
Bitfield<7, 6> sel;
Bitfield<5, 4> rw;
CounterEvent(Counter*);
/** Event process */
- virtual void process();
+ void process();
/** Event description */
virtual const char *description() const;
friend class Counter;
void setTo(int clocks);
+
+ int clocksLeft();
+
+ Tick getInterval();
};
private:
std::string _name;
const std::string &name() const { return _name; }
+ unsigned int num;
+
CounterEvent event;
- /** Current count value */
- uint16_t count;
+ /** True after startup is called. */
+ bool running;
+
+ /** Initial count value */
+ uint16_t initial_count;
/** Latched count */
uint16_t latched_count;
/** Interrupt period */
uint16_t period;
+ /** When to start ticking */
+ Tick offset;
+
/** Current mode of operation */
uint8_t mode;
/** Determine which byte of a 16-bit count value to read/write */
uint8_t read_byte, write_byte;
+ /** Pointer to container */
+ Intel8254Timer *parent;
+
public:
- Counter(const std::string &name);
+ Counter(Intel8254Timer *p, const std::string &name, unsigned int num);
/** Latch the current count (if one is not already latched) */
void latchCount();
+ /** Get the current count for this counter */
+ int currentCount();
+
/** Set the read/write mode */
void setRW(int rw_val);
* @param base The base name of the counter object.
* @param os The stream to serialize to.
*/
- void serialize(const std::string &base, std::ostream &os);
+ void serialize(const std::string &base, CheckpointOut &cp) const;
/**
* Reconstruct the state of this object from a checkpoint.
* @param cp The checkpoint use.
* @param section The section name of this object
*/
- void unserialize(const std::string &base, Checkpoint *cp,
- const std::string §ion);
+ void unserialize(const std::string &base, CheckpointIn &cp);
+
+ /** Start ticking */
+ void startup();
};
- private:
+ protected:
std::string _name;
const std::string &name() const { return _name; }
/** PIT has three seperate counters */
Counter *counter[3];
+ virtual void
+ counterInterrupt(unsigned int num)
+ {
+ DPRINTF(Intel8254Timer, "Timer interrupt from counter %d.\n", num);
+ }
+
public:
- /** Public way to access individual counters (avoid array accesses) */
- Counter counter0;
- Counter counter1;
- Counter counter2;
- Intel8254Timer(const std::string &name);
+ virtual
+ ~Intel8254Timer()
+ {}
+
+ Intel8254Timer(EventManager *em, const std::string &name,
+ Counter *counter0, Counter *counter1, Counter *counter2);
+
+ Intel8254Timer(EventManager *em, const std::string &name);
/** Write control word */
void writeControl(const CtrlReg data);
+ uint8_t
+ readCounter(unsigned int num)
+ {
+ assert(num < 3);
+ return counter[num]->read();
+ }
+
+ void
+ writeCounter(unsigned int num, const uint8_t data)
+ {
+ assert(num < 3);
+ counter[num]->write(data);
+ }
+
+ bool
+ outputHigh(unsigned int num)
+ {
+ assert(num < 3);
+ return counter[num]->outputHigh();
+ }
+
/**
* Serialize this object to the given output stream.
* @param base The base name of the counter object.
* @param os The stream to serialize to.
*/
- void serialize(const std::string &base, std::ostream &os);
+ void serialize(const std::string &base, CheckpointOut &cp) const;
/**
* Reconstruct the state of this object from a checkpoint.
* @param cp The checkpoint use.
* @param section The section name of this object
*/
- void unserialize(const std::string &base, Checkpoint *cp,
- const std::string §ion);
+ void unserialize(const std::string &base, CheckpointIn &cp);
+
+ /** Start ticking */
+ void startup();
};
#endif // __DEV_8254_HH__