diff options
| author | Alejandro Soto <alejandro@34project.org> | 2022-12-13 21:43:25 -0600 |
|---|---|---|
| committer | Alejandro Soto <alejandro@34project.org> | 2022-12-16 16:29:10 -0600 |
| commit | 0c63c46e31642d0102542a745af6b445a9d22b3b (patch) | |
| tree | 0e8b6db18829e4a3d6c894af206f2b5257815827 /tb/interrupt.cpp | |
| parent | d564e3538a3654facc94bb4cd1ee021830dfcf52 (diff) | |
Implement interrupt controller
Diffstat (limited to 'tb/interrupt.cpp')
| -rw-r--r-- | tb/interrupt.cpp | 63 |
1 files changed, 63 insertions, 0 deletions
diff --git a/tb/interrupt.cpp b/tb/interrupt.cpp new file mode 100644 index 0000000..4164bb7 --- /dev/null +++ b/tb/interrupt.cpp @@ -0,0 +1,63 @@ +#include <cstdint> + +#include "avalon.hpp" + +namespace taller::avalon +{ + interrupt_controller::interrupt_controller(std::uint32_t base) noexcept + : slave(base, 8, 4) + {} + + bool interrupt_controller::read(std::uint32_t addr, std::uint32_t &data) noexcept + { + switch(addr) + { + case 0: + data = status(); + break; + + case 1: + data = mask; + break; + } + + return true; + } + + bool interrupt_controller::write(std::uint32_t addr, std::uint32_t data, unsigned byte_enable) noexcept + { + switch(addr) + { + case 0: + break; + + case 1: + mask = data; + break; + } + + return true; + } + + bool interrupt_controller::irq() noexcept + { + return status() != 0; + } + + std::uint32_t interrupt_controller::status() noexcept + { + std::uint32_t lines = 0; + + if(irqs.timer) + { + lines |= irqs.timer->irq() << 0; + } + + if(irqs.jtaguart) + { + lines |= irqs.jtaguart->irq() << 1; + } + + return lines & mask; + } +} |
