mirror of
https://github.com/DCC-EX/CommandStation-EX.git
synced 2024-11-30 03:26:13 +01:00
Make own interrupt routine selection array as RMT api only can have one interrupt routine with one argument
This commit is contained in:
parent
e5ce76e703
commit
33c9155f6e
21
DCCRMT.cpp
21
DCCRMT.cpp
|
@ -57,9 +57,15 @@ void setEOT(rmt_item32_t* item) {
|
||||||
item->val = 0;
|
item->val = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// This is an array that contains the this pointers
|
||||||
|
// to all uses channel objects. This is used to determine
|
||||||
|
// which of the channels was triggering the ISR as there
|
||||||
|
// is only ONE common ISR routine for all channels.
|
||||||
|
RMTChannel *channelHandle[8] = { 0 };
|
||||||
|
|
||||||
void IRAM_ATTR interrupt(rmt_channel_t channel, void *t) {
|
void IRAM_ATTR interrupt(rmt_channel_t channel, void *t) {
|
||||||
RMTChannel *tt = (RMTChannel *)t;
|
RMTChannel *tt = channelHandle[channel];
|
||||||
tt->RMTinterrupt();
|
if (tt) tt->RMTinterrupt();
|
||||||
}
|
}
|
||||||
|
|
||||||
RMTChannel::RMTChannel(byte pin, bool isMain) {
|
RMTChannel::RMTChannel(byte pin, bool isMain) {
|
||||||
|
@ -133,18 +139,17 @@ RMTChannel::RMTChannel(byte pin, bool isMain) {
|
||||||
DIAG(F("Register interrupt on core %d"), xPortGetCoreID());
|
DIAG(F("Register interrupt on core %d"), xPortGetCoreID());
|
||||||
|
|
||||||
ESP_ERROR_CHECK(rmt_set_tx_loop_mode(channel, true));
|
ESP_ERROR_CHECK(rmt_set_tx_loop_mode(channel, true));
|
||||||
rmt_register_tx_end_callback(interrupt, this);
|
channelHandle[channel] = this; // used by interrupt
|
||||||
|
rmt_register_tx_end_callback(interrupt, 0);
|
||||||
rmt_set_tx_intr_en(channel, true);
|
rmt_set_tx_intr_en(channel, true);
|
||||||
|
|
||||||
DIAG(F("Starting channel %d signal generator"), config.channel);
|
DIAG(F("Starting channel %d signal generator for %s"), config.channel, isMainTrack ? "MAIN" : "PROG");
|
||||||
|
|
||||||
// send one bit to kickstart the signal, remaining data will come from the
|
// send one bit to kickstart the signal, remaining data will come from the
|
||||||
// packet queue. We intentionally do not wait for the RMT TX complete here.
|
// packet queue. We intentionally do not wait for the RMT TX complete here.
|
||||||
//rmt_write_items(channel, preamble, preambleLen, false);
|
//rmt_write_items(channel, preamble, preambleLen, false);
|
||||||
RMTprefill();
|
RMTprefill();
|
||||||
preambleNext = true;
|
|
||||||
dataReady = false;
|
dataReady = false;
|
||||||
RMTinterrupt();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void RMTChannel::RMTprefill() {
|
void RMTChannel::RMTprefill() {
|
||||||
|
@ -161,10 +166,10 @@ int RMTChannel::RMTfillData(const byte buffer[], byte byteCount, byte repeatCoun
|
||||||
// to the HW. dataRepeat on the other hand signals back to
|
// to the HW. dataRepeat on the other hand signals back to
|
||||||
// the caller of this function if the data has been sent enough
|
// the caller of this function if the data has been sent enough
|
||||||
// times (0 to 3 means 1 to 4 times in total).
|
// times (0 to 3 means 1 to 4 times in total).
|
||||||
if (dataReady == true)
|
|
||||||
return 1000;
|
|
||||||
if (dataRepeat > 0) // we have still old work to do
|
if (dataRepeat > 0) // we have still old work to do
|
||||||
return dataRepeat;
|
return dataRepeat;
|
||||||
|
if (dataReady == true) // the packet is not copied out yet
|
||||||
|
return 1000;
|
||||||
if (DATA_LEN(byteCount) > maxDataLen) { // this would overun our allocated memory for data
|
if (DATA_LEN(byteCount) > maxDataLen) { // this would overun our allocated memory for data
|
||||||
DIAG(F("Can not convert DCC bytes # %d to DCC bits %d, buffer too small"), byteCount, maxDataLen);
|
DIAG(F("Can not convert DCC bytes # %d to DCC bits %d, buffer too small"), byteCount, maxDataLen);
|
||||||
return -1; // something very broken, can not convert packet
|
return -1; // something very broken, can not convert packet
|
||||||
|
|
6
DCCRMT.h
6
DCCRMT.h
|
@ -36,6 +36,11 @@ class RMTChannel {
|
||||||
void RMTprefill();
|
void RMTprefill();
|
||||||
//int RMTfillData(dccPacket packet);
|
//int RMTfillData(dccPacket packet);
|
||||||
int RMTfillData(const byte buffer[], byte byteCount, byte repeatCount);
|
int RMTfillData(const byte buffer[], byte byteCount, byte repeatCount);
|
||||||
|
inline bool busy() {
|
||||||
|
if (dataRepeat > 0) // we have still old work to do
|
||||||
|
return true;
|
||||||
|
return dataReady;
|
||||||
|
};
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
|
@ -50,7 +55,6 @@ class RMTChannel {
|
||||||
byte dataLen;
|
byte dataLen;
|
||||||
byte maxDataLen;
|
byte maxDataLen;
|
||||||
// flags
|
// flags
|
||||||
volatile bool preambleNext = true; // alternate between preamble and content
|
|
||||||
volatile bool dataReady = false; // do we have real data available or send idle
|
volatile bool dataReady = false; // do we have real data available or send idle
|
||||||
volatile byte dataRepeat = 0;
|
volatile byte dataRepeat = 0;
|
||||||
};
|
};
|
||||||
|
|
Loading…
Reference in New Issue
Block a user