openMSX
IRQHelper.hh
Go to the documentation of this file.
1 #ifndef IRQHELPER_HH
2 #define IRQHELPER_HH
3 
4 #include "Probe.hh"
5 #include "MSXMotherBoard.hh"
6 #include "serialize.hh"
7 #include <memory>
8 #include <string>
9 
10 namespace openmsx {
11 
12 class MSXCPU;
13 class DeviceConfig;
14 
22 // policy class for IRQ source
23 class IRQSource
24 {
25 protected:
26  explicit IRQSource(MSXCPU& cpu);
27  void raise();
28  void lower();
29 private:
30  MSXCPU& cpu;
31 };
32 
33 // supports <optional_irq> tag in hardware config
34 
35 class IRQSink
36 {
37 public:
38  virtual ~IRQSink() = default;
39  virtual void raise() = 0;
40  virtual void lower() = 0;
41 };
42 
44 {
45 protected:
46  OptionalIRQ(MSXCPU& cpu, const DeviceConfig& config);
47  void raise() { sink->raise(); }
48  void lower() { sink->lower(); }
49 private:
50  std::unique_ptr<IRQSink> sink;
51 };
52 
53 
54 // generic implementation
55 template <typename SOURCE> class IntHelper : public SOURCE
56 {
57 public:
58  IntHelper(const IntHelper&) = delete;
59  IntHelper& operator=(const IntHelper&) = delete;
60 
64  IntHelper(MSXMotherBoard& motherboard, const std::string& name)
65  : SOURCE(motherboard.getCPU())
66  , request(motherboard.getDebugger(), name,
67  "Outgoing IRQ signal.", false)
68  {
69  }
70  IntHelper(MSXMotherBoard& motherboard, const std::string& name,
71  const DeviceConfig& config)
72  : SOURCE(motherboard.getCPU(), config)
73  , request(motherboard.getDebugger(), name,
74  "Outgoing IRQ signal.", false)
75  {
76  }
77 
82  reset();
83  }
84 
87  inline void set() {
88  if (!request) {
89  request = true;
90  SOURCE::raise();
91  }
92  }
93 
96  inline void reset() {
97  if (request) {
98  request = false;
99  SOURCE::lower();
100  }
101  }
102 
105  inline void set(bool s) {
106  if (s) {
107  set();
108  } else {
109  reset();
110  }
111  }
112 
116  inline bool getState() const {
117  return request;
118  }
119 
120  template<typename Archive>
121  void serialize(Archive& ar, unsigned /*version*/)
122  {
123  bool pending = request;
124  ar.serialize("pending", pending);
125  if (ar.isLoader()) {
126  set(pending);
127  }
128  }
129 
130 private:
131  Probe<bool> request;
132 };
133 
134 // convenience types
137 
138 } // namespace openmsx
139 
140 #endif
IntHelper(MSXMotherBoard &motherboard, const std::string &name)
Create a new IntHelper.
Definition: IRQHelper.hh:64
Helper class for doing interrupt request (IRQ) administration.
Definition: IRQHelper.hh:23
Thanks to enen for testing this on a real cartridge:
Definition: Autofire.cc:5
bool getState() const
Get the interrupt state.
Definition: IRQHelper.hh:116
void reset()
Reset the interrupt request on the bus.
Definition: IRQHelper.hh:96
void serialize(Archive &ar, unsigned)
Definition: IRQHelper.hh:121
IRQSource(MSXCPU &cpu)
Definition: IRQHelper.cc:11
~IntHelper()
Destroy this IntHelper.
Definition: IRQHelper.hh:81
IntHelper(MSXMotherBoard &motherboard, const std::string &name, const DeviceConfig &config)
Definition: IRQHelper.hh:70