Implemented interrupt driven tx
This commit is contained in:
parent
496bb3d4d1
commit
51a9d30c0a
17
hardware.hpp
17
hardware.hpp
@ -45,7 +45,7 @@ class Hardware {
|
|||||||
*Registers::CTRL_STAT_REG_C = controlRegC;
|
*Registers::CTRL_STAT_REG_C = controlRegC;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void txByteBlocking(typename cfg::data_t byte) FORCE_INLINE
|
static void txByteBlocking(const typename cfg::data_t &byte) FORCE_INLINE
|
||||||
{
|
{
|
||||||
while (!(*Registers::CTRL_STAT_REG_A & (1 << CtrlFlagsA::DATA_REG_EMPTY)))
|
while (!(*Registers::CTRL_STAT_REG_A & (1 << CtrlFlagsA::DATA_REG_EMPTY)))
|
||||||
;
|
;
|
||||||
@ -53,6 +53,21 @@ class Hardware {
|
|||||||
*Registers::IO_REG = byte;
|
*Registers::IO_REG = byte;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void txByteInterrupt(volatile const typename cfg::data_t &byte) FORCE_INLINE
|
||||||
|
{
|
||||||
|
*Registers::IO_REG = byte;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void enableDataRegEmptyInt() FORCE_INLINE
|
||||||
|
{
|
||||||
|
*Registers::CTRL_STAT_REG_B |= (1 << CtrlFlagsB::DATA_REG_EMPTY_INT_ENABLE);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void disableDataRegEmptyInt() FORCE_INLINE
|
||||||
|
{
|
||||||
|
*Registers::CTRL_STAT_REG_B &= ~(1 << CtrlFlagsB::DATA_REG_EMPTY_INT_ENABLE);
|
||||||
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
struct DataBitsVal {
|
struct DataBitsVal {
|
||||||
uint8_t regCVal = 0;
|
uint8_t regCVal = 0;
|
||||||
|
@ -127,9 +127,16 @@ class Hardware0<mode, cfg, Driven::INTERRUPT> {
|
|||||||
HardwareImpl::init();
|
HardwareImpl::init();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void txByte(data_t byte) FORCE_INLINE
|
static void txByte(const data_t &byte) FORCE_INLINE
|
||||||
{
|
{
|
||||||
HardwareImpl::txByteBlocking(byte);
|
uint8_t tmpHead = (sm_txHead + 1) % TX_BUFFER_SIZE;
|
||||||
|
while (tmpHead == sm_txTail)
|
||||||
|
;
|
||||||
|
|
||||||
|
sm_txBuffer[tmpHead] = byte;
|
||||||
|
sm_txHead = tmpHead;
|
||||||
|
|
||||||
|
HardwareImpl::enableDataRegEmptyInt();
|
||||||
}
|
}
|
||||||
|
|
||||||
static data_t rxByte() FORCE_INLINE {}
|
static data_t rxByte() FORCE_INLINE {}
|
||||||
@ -140,14 +147,25 @@ class Hardware0<mode, cfg, Driven::INTERRUPT> {
|
|||||||
using HardwareImpl = detail::Hardware<detail::Registers0, detail::ControlFlagsA0, detail::ControlFlagsB0,
|
using HardwareImpl = detail::Hardware<detail::Registers0, detail::ControlFlagsA0, detail::ControlFlagsB0,
|
||||||
detail::ControlFlagsC0, cfg, mode, Driven::INTERRUPT>;
|
detail::ControlFlagsC0, cfg, mode, Driven::INTERRUPT>;
|
||||||
|
|
||||||
|
static constexpr auto TX_BUFFER_SIZE = 16;
|
||||||
|
|
||||||
|
static volatile uint8_t sm_txHead;
|
||||||
|
static volatile uint8_t sm_txTail;
|
||||||
|
static volatile data_t sm_txBuffer[TX_BUFFER_SIZE];
|
||||||
|
|
||||||
static void rxIntHandler()
|
static void rxIntHandler()
|
||||||
{
|
{
|
||||||
// TODO
|
// TODO
|
||||||
}
|
}
|
||||||
|
|
||||||
static void dataRegEmptyIntHandler()
|
static void dataRegEmptyIntHandler() FORCE_INLINE
|
||||||
{
|
{
|
||||||
// TODO
|
if (sm_txHead != sm_txTail) {
|
||||||
|
uint8_t tmpTail = (sm_txTail + 1) % TX_BUFFER_SIZE;
|
||||||
|
sm_txTail = tmpTail;
|
||||||
|
HardwareImpl::txByteInterrupt(sm_txBuffer[tmpTail]);
|
||||||
|
} else
|
||||||
|
HardwareImpl::disableDataRegEmptyInt();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void txIntHandler()
|
static void txIntHandler()
|
||||||
@ -156,6 +174,14 @@ class Hardware0<mode, cfg, Driven::INTERRUPT> {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
template <Mode mode, class cfg>
|
||||||
|
volatile uint8_t Hardware0<mode, cfg, Driven::INTERRUPT>::sm_txHead = 0;
|
||||||
|
template <Mode mode, class cfg>
|
||||||
|
volatile uint8_t Hardware0<mode, cfg, Driven::INTERRUPT>::sm_txTail = 0;
|
||||||
|
template <Mode mode, class cfg>
|
||||||
|
volatile typename Hardware0<mode, cfg, Driven::INTERRUPT>::data_t
|
||||||
|
Hardware0<mode, cfg, Driven::INTERRUPT>::sm_txBuffer[TX_BUFFER_SIZE];
|
||||||
|
|
||||||
} // namespace uart
|
} // namespace uart
|
||||||
|
|
||||||
#undef FORCE_INLINE
|
#undef FORCE_INLINE
|
||||||
|
@ -102,7 +102,7 @@ class Hardware1 {
|
|||||||
HardwareImpl::init();
|
HardwareImpl::init();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void txByte(data_t byte) FORCE_INLINE
|
static void txByte(const data_t &byte) FORCE_INLINE
|
||||||
{
|
{
|
||||||
HardwareImpl::txByteBlocking(byte);
|
HardwareImpl::txByteBlocking(byte);
|
||||||
}
|
}
|
||||||
@ -131,9 +131,16 @@ class Hardware1<mode, cfg, Driven::INTERRUPT> {
|
|||||||
HardwareImpl::init();
|
HardwareImpl::init();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void txByte(data_t byte) FORCE_INLINE
|
static void txByte(const data_t &byte) FORCE_INLINE
|
||||||
{
|
{
|
||||||
HardwareImpl::txByteBlocking(byte);
|
uint8_t tmpHead = (sm_txHead + 1) % TX_BUFFER_SIZE;
|
||||||
|
while (tmpHead == sm_txTail)
|
||||||
|
;
|
||||||
|
|
||||||
|
sm_txBuffer[tmpHead] = byte;
|
||||||
|
sm_txHead = tmpHead;
|
||||||
|
|
||||||
|
HardwareImpl::enableDataRegEmptyInt();
|
||||||
}
|
}
|
||||||
|
|
||||||
static data_t rxByte() FORCE_INLINE {}
|
static data_t rxByte() FORCE_INLINE {}
|
||||||
@ -144,14 +151,25 @@ class Hardware1<mode, cfg, Driven::INTERRUPT> {
|
|||||||
using HardwareImpl = detail::Hardware<detail::Registers1, detail::ControlFlagsA1, detail::ControlFlagsB1,
|
using HardwareImpl = detail::Hardware<detail::Registers1, detail::ControlFlagsA1, detail::ControlFlagsB1,
|
||||||
detail::ControlFlagsC1, cfg, mode, Driven::INTERRUPT>;
|
detail::ControlFlagsC1, cfg, mode, Driven::INTERRUPT>;
|
||||||
|
|
||||||
|
static constexpr auto TX_BUFFER_SIZE = 16;
|
||||||
|
|
||||||
|
static volatile uint8_t sm_txHead;
|
||||||
|
static volatile uint8_t sm_txTail;
|
||||||
|
static volatile data_t sm_txBuffer[TX_BUFFER_SIZE];
|
||||||
|
|
||||||
static void rxIntHandler()
|
static void rxIntHandler()
|
||||||
{
|
{
|
||||||
// TODO
|
// TODO
|
||||||
}
|
}
|
||||||
|
|
||||||
static void dataRegEmptyIntHandler()
|
static void dataRegEmptyIntHandler() FORCE_INLINE
|
||||||
{
|
{
|
||||||
// TODO
|
if (sm_txHead != sm_txTail) {
|
||||||
|
uint8_t tmpTail = (sm_txTail + 1) % TX_BUFFER_SIZE;
|
||||||
|
sm_txTail = tmpTail;
|
||||||
|
HardwareImpl::txByteInterrupt(sm_txBuffer[tmpTail]);
|
||||||
|
} else
|
||||||
|
HardwareImpl::disableDataRegEmptyInt();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void txIntHandler()
|
static void txIntHandler()
|
||||||
@ -160,6 +178,14 @@ class Hardware1<mode, cfg, Driven::INTERRUPT> {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
template <Mode mode, class cfg>
|
||||||
|
volatile uint8_t Hardware1<mode, cfg, Driven::INTERRUPT>::sm_txHead = 0;
|
||||||
|
template <Mode mode, class cfg>
|
||||||
|
volatile uint8_t Hardware1<mode, cfg, Driven::INTERRUPT>::sm_txTail = 0;
|
||||||
|
template <Mode mode, class cfg>
|
||||||
|
volatile typename Hardware1<mode, cfg, Driven::INTERRUPT>::data_t
|
||||||
|
Hardware1<mode, cfg, Driven::INTERRUPT>::sm_txBuffer[TX_BUFFER_SIZE];
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
} // namespace uart
|
} // namespace uart
|
||||||
|
Loading…
Reference in New Issue
Block a user