Browse Source

fix 2nd frame detection

for 2ch HM
and add faster exiting CMT wait state
pull/1394/head
rejoe2 9 months ago
committed by GitHub
parent
commit
bfedf4f0c2
No known key found for this signature in database GPG Key ID: B5690EEEBB952194
  1. 25
      src/hm/Communication.h
  2. 48
      src/hm/Heuristic.h
  3. 3
      src/hm/HeuristicInv.h
  4. 24
      src/hm/hmRadio.h
  5. 5
      src/hm/radio.h
  6. 5
      src/hms/hmsRadio.h

25
src/hm/Communication.h

@ -86,7 +86,7 @@ class Communication : public CommQueue<> {
mIsRetransmit = false;
if(NULL == q->iv->radio)
cmdDone(false); // can't communicate while radio is not defined!
mFirstTry = q->iv->isAvailable();
mFirstTry = INV_RADIO_TYPE_NRF == q->iv->ivRadioType && q->iv->isAvailable();
q->iv->mCmd = q->cmd;
q->iv->mIsSingleframeReq = false;
mFramesExpected = getFramesExpected(q); // function to get expected frame count.
@ -134,20 +134,23 @@ class Communication : public CommQueue<> {
DPRINT_IVID(DBG_INFO, q->iv->id);
DBGPRINT(F("request timeout: "));
DBGPRINT(String(q->iv->radio->mRadioWaitTime.getRunTime()));
DBGPRINT(F("ms"));
if(INV_RADIO_TYPE_NRF == q->iv->ivRadioType) {
DBGPRINTLN(F("ms"));
/*if(INV_RADIO_TYPE_NRF == q->iv->ivRadioType) {
DBGPRINT(F(", retries "));
DBGPRINTLN(String(q->iv->radio->mTxRetriesNext));
DBGPRINT(F(", ARC "));
DBGPRINT(String(q->iv->radio->getARC()));
DBGPRINT(F(", PLOS "));
DBGPRINTLN(String(q->iv->radio->getPLOS()));
} else
DBGPRINTLN("");
DBGPRINTLN("");*/
}
if(!q->iv->mGotFragment) {
if(INV_RADIO_TYPE_CMT == q->iv->ivRadioType) {
q->iv->radio->switchFrequency(q->iv, HOY_BOOT_FREQ_KHZ, (q->iv->config->frequency*FREQ_STEP_KHZ + HOY_BASE_FREQ_KHZ));
mWaitTime.startTimeMonitor(1000);
} else {
mHeu.setIvRetriesBad(q->iv);
if(IV_MI == q->iv->ivGen)
q->iv->mIvTxCnt++;
@ -180,8 +183,11 @@ class Communication : public CommQueue<> {
q->iv->mDtuRxCnt++;
if (p->packet[0] == (TX_REQ_INFO + ALL_FRAMES)) { // response from get information command
if(parseFrame(p))
if(parseFrame(p)) {
q->iv->curFrmCnt++;
if(!mIsRetransmit && (p->packet[9] == 0x02 || p->packet[9] == 0x82) && p->millis < 85)
mHeu.setIvRetriesGood(q->iv,p->millis < 70);
}
} else if (p->packet[0] == (TX_REQ_DEVCONTROL + ALL_FRAMES)) { // response from dev control command
if(parseDevCtrl(p, q))
closeRequest(q, true);
@ -291,10 +297,10 @@ class Communication : public CommQueue<> {
DBGPRINT(String(p->millis));
DBGPRINT(F("ms | "));
DBGPRINT(String(p->len));
DBGPRINT(F(", ARC "));
/*DBGPRINT(F(", ARC "));
DBGPRINT(String(p->arc));
DBGPRINT(F(", PLOS "));
DBGPRINT(String(p->plos));
DBGPRINT(String(p->plos));*/
DBGPRINT(F(" |"));
if(INV_RADIO_TYPE_NRF == q->iv->ivRadioType) {
DBGPRINT(F(" CH"));
@ -417,6 +423,8 @@ class Communication : public CommQueue<> {
}
inline bool parseMiFrame(packet_t *p, const queue_s *q) {
if(!mIsRetransmit && p->packet[9] == 0x00 && p->millis < 35) //first frame is fast?
mHeu.setIvRetriesGood(q->iv,p->millis < 22);
if ((p->packet[0] == MI_REQ_CH1 + ALL_FRAMES)
|| (p->packet[0] == MI_REQ_CH2 + ALL_FRAMES)
|| ((p->packet[0] >= (MI_REQ_4CH + ALL_FRAMES))
@ -436,7 +444,6 @@ class Communication : public CommQueue<> {
record_t<> *rec = q->iv->getRecordStruct(RealTimeRunData_Debug); // choose the record structure
rec->ts = q->ts;
miStsConsolidate(q, ((p->packet[0] == 0x88) ? 1 : 2), rec, p->packet[10], p->packet[12], p->packet[9], p->packet[11]);
//mHeu.setGotFragment(q->iv); only do this when we are through the cycle?
}
return true;
@ -527,7 +534,7 @@ class Communication : public CommQueue<> {
len -= 2;
DPRINT_IVID(DBG_INFO, q->iv->id);
//DPRINT_IVID(DBG_INFO, q->iv->id);
DBGPRINT(F("Payload ("));
DBGPRINT(String(len));
if(*mPrintWholeTrace) {

48
src/hm/Heuristic.h

@ -23,8 +23,8 @@
class Heuristic {
public:
uint8_t getTxCh(Inverter<> *iv) {
if((IV_HMS == iv->ivGen) || (IV_HMT == iv->ivGen))
return 0; // not used for these inverter types
if(iv->ivRadioType != INV_RADIO_TYPE_NRF)
return 0; // not used for other than nRF inverter types
HeuristicInv *ih = &iv->heuristics;
@ -66,6 +66,8 @@ class Heuristic {
ih->testPeriodFailCnt = 0;
}
iv->radio->mTxRetriesNext = getIvRetries(iv);
return id2Ch(ih->txRfChId);
}
@ -155,6 +157,48 @@ class Heuristic {
DBGPRINTLN(String(iv->config->powerLevel));
}
uint8_t getIvRetries(Inverter<> *iv) {
if(iv->heuristics.rxSpeeds[0])
return 5;
if(iv->heuristics.rxSpeeds[1])
return 10;
return 15;
}
void setIvRetriesGood(Inverter<> *iv, bool veryGood) {
if(iv->ivRadioType != INV_RADIO_TYPE_NRF)
return; // not used for other than nRF inverter types
if(iv->heuristics.rxSpeedCnt[veryGood] > 9)
return;
iv->heuristics.rxSpeedCnt[veryGood]++;
iv->heuristics.rxSpeeds[veryGood] = true;
}
void setIvRetriesBad(Inverter<> *iv) {
if(iv->ivRadioType != INV_RADIO_TYPE_NRF)
return; // not used for other than nRF inverter types
if(iv->heuristics.rxSpeedCnt[0]) {
iv->heuristics.rxSpeedCnt[0]--;
return;
}
if(iv->heuristics.rxSpeeds[0]) {
iv->heuristics.rxSpeeds[0] = false;
return;
}
if(iv->heuristics.rxSpeedCnt[1]) {
iv->heuristics.rxSpeedCnt[1]--;
return;
}
if(iv->heuristics.rxSpeeds[1]) {
iv->heuristics.rxSpeeds[1] = false;
return;
}
return;
}
private:
bool isNewTxCh(HeuristicInv *ih) {
return ih->txRfChId != ih->lastBestTxChId;

3
src/hm/HeuristicInv.h

@ -27,6 +27,9 @@ class HeuristicInv {
uint8_t testChId = 0;
int8_t saveOldTestQuality = -6;
uint8_t lastRxFragments = 0;
bool rxSpeeds[2] = {false,false}; // is inverter responding very fast respective fast?
uint8_t rxSpeedCnt[2] = {0,0}; // count how many messages had been received very fast respective fast (10 max)
};
#endif /*__HEURISTIC_INV_H__*/

24
src/hm/hmRadio.h

@ -161,7 +161,7 @@ class HmRadio : public Radio {
rxPendular = false;
mNRFloopChannels = (mLastIv->ivGen == IV_MI);
innerLoopTimeout = DURATION_TXFRAME;
innerLoopTimeout = mLastIv->ivGen != IV_MI ? DURATION_TXFRAME : DURATION_ONEFRAME;
}
if(rx_ready) {
@ -293,13 +293,13 @@ class HmRadio : public Radio {
return mNrf24->isPVariant();
}
uint8_t getARC(void) {
/*uint8_t getARC(void) {
return mNrf24->getARC();
}
uint8_t getPLOS(void) {
return mNrf24->getPLOS();
}
}*/
private:
inline bool getReceived(void) {
@ -315,8 +315,8 @@ class HmRadio : public Radio {
p.len = (len > MAX_RF_PAYLOAD_SIZE) ? MAX_RF_PAYLOAD_SIZE : len;
p.rssi = mNrf24->testRPD() ? -64 : -75;
p.millis = millis() - mMillis;
p.arc = mNrf24->getARC();
p.plos = mNrf24->getPLOS();
//p.arc = mNrf24->getARC();
//p.plos = mNrf24->getPLOS();
mNrf24->read(p.packet, p.len);
if (p.packet[0] != 0x00) {
@ -356,18 +356,23 @@ class HmRadio : public Radio {
mTxChIdx = iv->heuristics.txRfChId;
if(*mSerialDebug) {
/* remark rejoe2: imo this has no added value here.
As this belongs to the last tx cycle, we should print that info
directly when switching from tx to rx. Otherwise we might confuse users.
if(!isRetransmit) {
DPRINT(DBG_INFO, "last tx setup: ");
DBGPRINT(String(mTxSetupTime));
DBGPRINTLN("ms");
}
}*/
DPRINT_IVID(DBG_INFO, iv->id);
DBGPRINT(F("TX "));
DBGPRINT(String(len));
DBGPRINT(" CH");
DBGPRINT(String(mRfChLst[mTxChIdx]));
DBGPRINT(F(" | "));
DBGPRINT(F(", "));
DBGPRINT(String(mTxRetriesNext));
DBGPRINT(F(" retries | "));
if(*mPrintWholeTrace) {
if(*mPrivacyMode)
ah::dumpBuf(mTxBuf, len, 1, 4);
@ -383,6 +388,10 @@ class HmRadio : public Radio {
}
mNrf24->stopListening();
if(!isRetransmit && mTxRetries != mTxRetriesNext) {
mNrf24->setRetries(3, mTxRetriesNext);
mTxRetries = mTxRetriesNext;
}
mNrf24->setChannel(mRfChLst[mTxChIdx]);
mNrf24->openWritingPipe(reinterpret_cast<uint8_t*>(&iv->radioId.u64));
mNrf24->startWrite(mTxBuf, len, false); // false = request ACK response
@ -425,6 +434,7 @@ class HmRadio : public Radio {
bool rxPendular = false;
uint32_t innerLoopTimeout = DURATION_LISTEN_MIN;
uint8_t mTxSetupTime = 0;
uint8_t mTxRetries = 15; // memorize last setting for mNrf24->setRetries(3, 15);
std::unique_ptr<SPIClass> mSpi;
std::unique_ptr<RF24> mNrf24;

5
src/hm/radio.h

@ -29,8 +29,8 @@ class Radio {
virtual bool switchFrequencyCh(Inverter<> *iv, uint8_t fromCh, uint8_t toCh) { return true; }
virtual bool isChipConnected(void) { return false; }
virtual bool loop(void) = 0;
virtual uint8_t getARC(void) { return 0xff; }
virtual uint8_t getPLOS(void) { return 0xff; }
//virtual uint8_t getARC(void) { return 0xff; }
//virtual uint8_t getPLOS(void) { return 0xff; }
void handleIntr(void) {
mIrqRcvd = true;
@ -78,6 +78,7 @@ class Radio {
std::queue<packet_t> mBufCtrl;
uint8_t mIrqOk = IRQ_UNKNOWN;
TimeMonitor mRadioWaitTime = TimeMonitor(0, true); // start as expired (due to code in RESET state)
uint8_t mTxRetriesNext = 15; // let heuristics tell us the next reties count (for nRF type radios only)
protected:
virtual void sendPacket(Inverter<> *iv, uint8_t len, bool isRetransmit, bool appendCrc16=true) = 0;

5
src/hms/hmsRadio.h

@ -166,9 +166,10 @@ class CmtRadio : public Radio {
mBufCtrl.push(p);
// this code completly stops communication!
//if(p.packet[9] > ALL_FRAMES) // indicates last frame
if(p.packet[9] > ALL_FRAMES) // indicates last frame
// mRadioWaitTime.stopTimeMonitor(); // we got everything we expected and can exit rx mode...
//optionally instead: mRadioWaitTime.startTimeMonitor(DURATION_PAUSE_LASTFR); // let the inverter first get back to rx mode?
//optionally instead:
mRadioWaitTime.startTimeMonitor(DURATION_PAUSE_LASTFR); // let the inverter first get back to rx mode?
}
CmtType mCmt;

Loading…
Cancel
Save