Commit 0c80a02a2a3616aff59cb93c5edb3fe7386ef45c
receivedTue, 13. Aug 2024, 19:02:24 (by user sx)
Tue, 13 Aug 2024 17:02:24 +0000 (19:02 +0200)
authorManfred Steiner <sx@htl-kaindorf.at>
Tue, 13 Aug 2024 17:02:17 +0000 (19:02 +0200)
committerManfred Steiner <sx@htl-kaindorf.at>
Tue, 13 Aug 2024 17:02:17 +0000 (19:02 +0200)
2 files changed:
software/nano-644/test_2024-07-23/src/units/cc1101new.cpp
software/nano-644/test_2024-07-23/src/units/cc1101new.hpp

index 6a7121fe8a434f4a92073cf4921b86d231dedcab..00342d24fe3704cf370a1bd9c20dc9fdb1f68544 100644 (file)
    // PB6 ... MISO
    // PB7 ... SCK
 
-   int8_t Cc1101New::run (uint8_t subtest) {
-      if (subtest == 0 && mode == Test) {
-         while (wait(0) == EOF) {
+   int8_t Cc1101New::runSend (uint8_t subtest) {
+      if (subtest == 0) {
+         bool ok = true;
+         GDOx_CFG_t cfg0 = SYNC_SENT_OR_RECEIVED_UNTIL_END_OF_PACKET;
+         ok &= writeRegister(0x02, cfg0);
+         return ok;
+      } else if (subtest > 1) {
+         return -1;
+      }
+
+      uint16_t cnt = 0;
+      do {
+         MainRadioControlState state = UNKNOWN;
+         uint8_t data[20];
+         printf_P(PSTR("\n [%04x]: state="), cnt++);
+         if (!readStatusRegister(MARCSTATE, (uint8_t *)&state)) {
+            printf_P(PSTR("E1"));
+         } else {
+            printf_P(PSTR("0x%02x"), state);
+         }
+         for (uint8_t i = 0; i < sizeof(data); i++) {
+            data[i] = i;
          }
-      } else if (subtest == 0 && mode == Send) {
-         uint16_t cnt = 0;
+         printf_P(PSTR(" --> send %d bytes ... "), sizeof(data));
+         if (!sendData(data, sizeof(data))) {
+            flashRedLed(100);
+            printf_P(PSTR("E1"));
+            continue;
+         }
+         flashGreenLed(100);
+         printf_P(PSTR("OK -> state="));
+         if (!readStatusRegister(MARCSTATE, (uint8_t *)&state)) {
+            printf_P(PSTR("E1"));
+         } else {
+            printf_P(PSTR("0x%02x"), state);
+         }
+      } while (wait(2000) == EOF);
+
+      return 0;
+   }
+
+   int8_t Cc1101New::runReceive (uint8_t subtest) {
+      if (subtest > 0) {
+         return -1;
+      }
+
+      int key = EOF;
+      uint16_t cnt = 0;
+      MainRadioControlState state;
+      while (key == EOF) {
+         printf_P(PSTR("\n [%04x] => start ... "), cnt++);
+         strobe(SRX);
          do {
-            MainRadioControlState state = UNKNOWN;
-            uint8_t data[20];
-            printf_P(PSTR("\n [%04x]: state="), cnt++);
+            state = UNKNOWN;
             if (!readStatusRegister(MARCSTATE, (uint8_t *)&state)) {
                printf_P(PSTR("E1"));
-            } else {
-               printf_P(PSTR("0x%02x"), state);
+               _delay_ms(500);
+               break;
             }
-            for (uint8_t i = 0; i < sizeof(data); i++) {
-               data[i] = i;
+            if (wait(0) != EOF) {
+               printf_P(PSTR("cancelled"));
+               _delay_ms(500);
+               break;
             }
-            printf_P(PSTR(" --> send %d bytes ... "), sizeof(data));
-            if (!sendData(data, sizeof(data))) {
-               flashRedLed(100);
-               printf_P(PSTR("E1"));
-               continue;
+            if (state == IDLE) {
+               printf_P(PSTR("? (IDLE)"));
+               _delay_ms(500);
+               break;
             }
-            flashGreenLed(100);
-            printf_P(PSTR("OK -> state="));
+
+         } while (state != RX && state != RXFIFO_OVERFLOW);
+
+         if (state != RX && state != RXFIFO_OVERFLOW) {
+            continue;
+         }
+
+         printf_P(PSTR("OK, receive ... "));
+
+         do {
+            uint8_t length;
+            uint8_t data[16];
             if (!readStatusRegister(MARCSTATE, (uint8_t *)&state)) {
-               printf_P(PSTR("E1"));
-            } else {
-               printf_P(PSTR("0x%02x"), state);
+               printf_P(PSTR("E2"));
+               _delay_ms(500);
+               continue;
+            }
+            if (wait(0) != EOF) {
+               printf_P(PSTR("cancelled"));
+               _delay_ms(500);
+               continue;
+            }
+            if (receiveData(data, &length, sizeof(data))) {
+               flashGreenLed(100);
+               printf_P(PSTR("OK, %d bytes received: "), length);
+               for (uint8_t i = 0; i < length; i++) {
+                  printf_P(PSTR(" 0x%02x"), data[i]);
+               }
+               printf_P(PSTR(" ... "));
             }
-         } while (wait(2000) == EOF);
-         return 0;
 
+         } while (state == RX || state == RXFIFO_OVERFLOW);
 
-      } else if (subtest == 0 && mode == Receive) {
-         
+         printf_P(PSTR("done (state=0x%02x)"), state);
       }
       return -1;
    }
 
+   int8_t Cc1101New::runTest (uint8_t subtest) {
+      if (subtest > 0) {
+         return -1;
+      }
+      while (wait(0) == EOF) {}
+      return -1;
+   }
+
+
+   int8_t Cc1101New::run (uint8_t subtest) {
+      switch (mode) {
+         case Send: return runSend(subtest);
+         case Receive: return runReceive(subtest);
+         case Test: return runTest(subtest);
+         default: return -1;
+      }
+   }
+
    // --------------------------------------------------------
 
    const Cc1101New::Register_t PMEM_CC1101_REGISTER_INIT PROGMEM = { 
       /* 0x00: iocfg2    0x0b (----) */ { Cc1101New::CHIP_NOT_READY, 0, 0 }, // GDO2
       /* 0x01: iocfg1    0x2e (----) */ { Cc1101New::HIGH_IMPEDANCE_WHEN_CHIP_SELECT_HIGH, 0, 0 }, // GDO1/MISO
-      /* 0x02: iocfg0    0x06 (----) */ { Cc1101New::CLK_XOSC_DIV_128, 0, 0 },  // GDO0
+      /* 0x02: iocfg0    0x06 (----) */ { Cc1101New::SYNC_SENT_OR_RECEIVED_UNTIL_END_OF_PACKET, 0, 0 },  // GDO0 -> PA5
       /* 0x03: fifothr   0x47 (0x07) */ { 7, 0, 1, 0 }, // fifo_thr = 0b111, close_in_rx=0, adc_retention = 1, (bit7=0)
       /* 0x04: sync1     0x7a (0xd3) */ 0x7a,
       /* 0x05: sync0     0x0e (0x91) */ 0x0e,
 
    bool Cc1101New::sendData (uint8_t *buffer, uint8_t length) {
       bool ok = true;
+      uint8_t txbytes;
       // ok &= writeRegister(0x3f, length);
       ok &= writeRegisters(0x3f, buffer, length);
-      ok &= strobe(STX);       // start sending bytes
-      ok &= waitForGD0High();
-      ok &= waitForGD0Low();
-      ok &= strobe(SFTX); //flush TXfifo
+      ok &= readStatusRegister(TXBYTES, &txbytes);
+      ok &= (txbytes == 20);
+      timer = 10;
+      if (ok) {
+         triggerOn();
+         ok &= strobe(STX);    // start sending bytes
+         // ok &= waitForGD0High(); // wait for start of SYNC
+         if (ok) {
+            uint8_t state;
+            do {
+               ok &= readStatusRegister(MARCSTATE, &state);
+            } while (ok && state != 0x13 && timer > 0);
+            ok &= state == 0x13; // check if in state TX
+         }
+         if (ok) {
+            do {
+               ok &= readStatusRegister(TXBYTES, &txbytes);
+            } while (ok && txbytes > 0 && timer > 0);
+            ok &= txbytes == 0;
+         }
+      }
+      if (!ok) {
+         strobe(SFTX); // flush TXfifo
+      }
+      // ok &= waitForGD0Low(); // wait for end of package
+      triggerOff();
+
+      // if (ok) {
+      //    printf_P(PSTR(" -> ? %02x %02x %02x %02x? "), state, txbytes[0], txbytes[1], txbytes[2]);
+      // }
+
       return ok;
    }
 
+   bool Cc1101New::receiveData (uint8_t *buffer, uint8_t *receivedLength, uint8_t maxBufferSize) {
+      bool ok = true;
+      STATUS_RXBYTES_t status;
+
+      ok &= readStatusRegister(RXBYTES, &status.byte);
+      if (ok && status.rxbytes.num_rxbytes > 0) {
+         uint8_t length = status.rxbytes.num_rxbytes;
+         ok &= readStatusRegister(RXBYTES, &status.byte);
+         if (ok && status.rxbytes.num_rxbytes == length) {
+            // ok &= readRegister(RXFIFO, &length);
+            if (length <= maxBufferSize) {
+               ok &= readRegisters(0xff, buffer, length);
+            } else {
+               ok = false;
+            }
+            ok &= strobe(SFRX);
+            if (ok) {
+               *receivedLength = length;
+               return ok;
+            }
+         }
+      }
+      strobe(SFRX);
+      *receivedLength = 0;
+      return false;
+   }
+
 
    void Cc1101New::printRegisters () {
       const Register_t *regValues = &PMEM_CC1101_REGISTER_INIT;
       debugPrint.byte = 0xff; // print all
       printRegisters();
 
-      triggerOn();
       for (uint8_t addr = 0; ok && addr < sizeof(Register_t); addr++) {
          uint8_t regValue;
          memcpy_P(&regValue, ((const uint8_t *)regValues) + addr, 1);
          ok &= writeRegister(addr, regValue);
       }
-      triggerOff();
 
       printRegisters();
       debugPrint.print = tmp;
index 53dc65bccdf791776b86ec0a97df29ac56066d00..807c09c29dc99acae92aef20606072b9956c506b 100644 (file)
@@ -26,11 +26,14 @@ class Cc1101New : public TestUnit {
       void tick1ms () { if (timer > 0) timer--; };
 
    private:
-      typedef enum { SRES = 0x30, SCAL = 0x33, SRX = 0x34, STX = 0x35, SFTX = 0x3b, SIDLE = 0x36 } StrobeCommand_t;
+      typedef enum { SRES = 0x30, SCAL = 0x33, SRX = 0x34, STX = 0x35, SFRX = 0x3a, SFTX = 0x3b, SIDLE = 0x36 } StrobeCommand_t;
       typedef enum { MARCSTATE = 0x35, TXBYTES = 0x3a, RXBYTES = 0x3b } StatusAddress_t;
       typedef struct { uint8_t writeRegister:1; uint8_t writeRegisters:1; uint8_t readRegister:1; uint8_t readRegisters:1; } DebugPrint_t;
 
    private:
+      int8_t runSend (uint8_t subtest);
+      int8_t runReceive (uint8_t subtest);
+      int8_t runTest (uint8_t subtest);
       uint8_t sendSpiByte (uint8_t b);
       void triggerOn();
       void triggerOff();
@@ -48,6 +51,7 @@ class Cc1101New : public TestUnit {
       bool readRegisters (uint8_t addr, uint8_t *buffer, uint8_t length);
       bool readStatusRegister (StatusAddress_t addr, uint8_t *value);
       bool sendData (uint8_t *buffer, uint8_t length);
+      bool receiveData (uint8_t *buffer, uint8_t *receivedLength, uint8_t maxBufferSize);
       void printRegisters ();
 
       bool resetCC1101 ();
@@ -176,6 +180,14 @@ class Cc1101New : public TestUnit {
       typedef struct { TXOFF_MODE_t txoff_mode:2; RXOFF_MODE_t rxoff_mode:2; CCA_MODE_t cca_mode:2; uint8_t bit76:2; } MCSM1_t;
       typedef struct { uint8_t xosc_force_on:1; uint8_t pin_ctrl_en:1; uint8_t po_timeout:2; FS_AUTOCAL_t fs_autocal:2; uint8_t bit76:2; } MCSM0_t;
 
+      typedef union {
+         uint8_t byte;
+         struct {
+            uint8_t num_rxbytes:7;
+            uint8_t rxfifo_overflow:1;
+         } rxbytes;
+      } STATUS_RXBYTES_t;
+
       typedef struct {
          IOCFG2_t iocfg2;
          IOCFG1_t iocfg1;