Just randomly receive ACK-packet

Started by Smu_Puh, March 21, 2016, 12:38:21 PM

Smu_Puh

Hi

my setup is as following:
code: PIC24 = Node
          PCDuino = Gateway
distance = 1m
antenna = 83mm cable

PIC24 <-SPI-> RFM69CW        )))))))sendWithRetry())))))->        RFM69CW <-SPI-> PCDuino (receiving every paket. RSSI = -105)

PCDuino <-SPI-> RFM69CW     ))))))))sendACK())))))))->       RFM69CW <-SPI-> PIC24 (receiving ACK only each 3-10 time. RSSI = -30)

My problem is, i don´t know where i have to search for the problem. Does the RSSI shows that the radio on PIC24 have problems with receiving or do the radio on the PCDuino have problems with sending?
It´s curious that the ACK is randomly receiving.

BR from germany

Felix

Quote from: Smu_Puh on March 21, 2016, 12:38:21 PM
my setup is as following:
code: PIC24 = Node
          PCDuino = Gateway
Hi,
What is PIC24 and PCDuino?

Smu_Puh

PIC24 is the running µC (PIC24FJ256DA210) on that the node-project is running and PCDuino is an PC-like Arduino with linux on it (PCDuino V3) and the gateway running on it.

Felix

Sorry, not familiar with that hardware.

Smu_Puh

 ;D The Hardware will not be the point.

My question focus on the problem-finding-path. I see that one of my transeivers have problem with sending or receiving. I´m not so familiar with the RSSI function, so i don´t know what the bad value of -105 tells me.
Tells me that the sending of PIC24-side is poor or the receiving on PCDuino-side is poor?



WhiteHare

#5
Maybe the PcDuino is the wrong tool for the job: it's using its very fast arm processor to more or less run a software emulation of an atmega328, but it's only getting time slices from the linux OS, which has an overhead during which it can't be paying  full attention.  i.e. it's not deterministic real-time like a dedicated mcu.  Plus, who knows how good (or not) the emulation really is?  I don't see any meaningful upside to justify this approach.


Smu_Puh

#6
So you think the PCDuino is the problem in this case?
Because the SPI-communication works correct and i´m using the arduinish header pis for communication with the RFM module.
Am i right, that the rssi value, my PCDuino-gateway-code shows me, after receiving the packet, tells me that the PCDuino do have a problem?

The gateway-side (PCDuino) receives everything. But the PIC24-side receives only randomly.

WhiteHare

#7
I'm just saying that if you're going to plug in something exotic, it's less headache to start first with standardized hardware that's known to work, verify it's working, and then later go exotic.  Otherwise, there's too many uncontrolled variables in effect all at once, which (obviously) makes troubleshooting difficult.

Smu_Puh

Ok, but what do the RSSI-values tell me exactly (first post) ?

WhiteHare

#9
Simply put, the -105 tells you the radio, as presently configured, is registering a relatively weak signal.  In contrast, -30 is a very strong signal.  Assuming those values are typical, I'm not sure what would explain such a large asymmetry in your particular case.  There are many different possibilities as to why that might happen, and I doubt anyone could  be  a priori certain as to which is in play based purely on the information you have provided.  You might get lucky and find the cause right away, or it might lead in unexpected directions and take a very long time to sort.  By now I've logged enough time debugging RFM69 related issues that I appreciate the value of starting out with a backstop to limit the downside: i.e. it mitigates against the otherwise unprotected risk of falling into an unexpectedly deep hole of unknowns.

Anyhow, good luck with your project.


Smu_Puh

Thank you WhiteHare,
I´m also a friend of developing upwards step-by-step to know at a certain points what´s going on everytime.
By know, i have no big choise to start with for example moteino-modules and go on porting it to my system. Because i know the moteinos will work. Nevermind.

I think i have a new clue, which points on the big difference between both RSSI values.
On the PIC side, runs the Node-project. I´ve ported the whole library (rfm.cpp rfm.h node ...) to C without trouble. The only thing that i have problems with is the arduinish millis(),which in my port is not exactly everytime 1ms.

When i add a certain delay direct after the "setMode(RF69_MODE_TX)" in "void RFM69::sendFrame", like 10ms, the received RSSI-value on the PCDuino-side changes from ca. -100 to ca. -35 dBm.

In my understanding, the TX-mode need some time to warm up. Maybe i have the same problem with the RX-mode, that it warms not long enough up, that i loose some ACK-pakets sended from PCDuino <-> PIC.

Am i thinking in the right direction? Do i have to check the mode-changes?

WhiteHare

#11
Quote from: Smu_Puh on March 23, 2016, 04:44:33 PM
Do i have to check the mode-changes?

That's a very good question, and I don't know whether or not it has ever been definitely proven one way or the other.  Maybe a careful reading of the datasheet would answer the question, but I have not embarked upon that for this particular question. 

Smu_Puh

I´ve putted
while ((rfm69_readReg(REG_IRQFLAGS1) & RF_IRQFLAGS1_MODEREADY) == 0x00);
after each setMode as seen here:

void rfm69_setMode(UINT8 newMode) {
    if (newMode == _mode)
        return;

    switch (newMode) {
        case RF69_MODE_TX:
            rfm69_writeReg(REG_OPMODE, (rfm69_readReg(REG_OPMODE) & 0xE3) | RF_OPMODE_TRANSMITTER);
            if (_isRFM69HW)rfm69_setHighPowerRegs(TRUE);
            while ((rfm69_readReg(REG_IRQFLAGS1) & RF_IRQFLAGS1_MODEREADY) == 0x00); 
//            DelayMs(10);
            break;
        case RF69_MODE_RX:
            rfm69_writeReg(REG_OPMODE, (rfm69_readReg(REG_OPMODE) & 0xE3) | RF_OPMODE_RECEIVER);
            if (_isRFM69HW)rfm69_setHighPowerRegs(FALSE);
            while ((rfm69_readReg(REG_IRQFLAGS1) & RF_IRQFLAGS1_MODEREADY) == 0x00); 
//            DelayMs(10);
            break;
        case RF69_MODE_SYNTH:
            rfm69_writeReg(REG_OPMODE, (rfm69_readReg(REG_OPMODE) & 0xE3) | RF_OPMODE_SYNTHESIZER);
            break;
        case RF69_MODE_STANDBY:
            rfm69_writeReg(REG_OPMODE, (rfm69_readReg(REG_OPMODE) & 0xE3) | RF_OPMODE_STANDBY);
//            DelayMs(10);
            break;
        case RF69_MODE_SLEEP:
            rfm69_writeReg(REG_OPMODE, (rfm69_readReg(REG_OPMODE) & 0xE3) | RF_OPMODE_SLEEP);
            break;
        default: //RF69_OP_NONE		// NONE
            return;
    }

    // we are using packet mode, so this check is not really needed
    // but waiting for mode ready is necessary when going from sleep because the FIFO may not be immediately available from previous mode
    while (_mode == RF69_MODE_SLEEP && (rfm69_readReg(REG_IRQFLAGS1) & RF_IRQFLAGS1_MODEREADY) == 0x00); // wait for ModeReady

    _mode = newMode;
}


Nothing changed on the RSSI (still bad).

Only when i put a little delay in the rfm69_sendFrame methode, the RSSI goes ca. -35dBm RSSI:

void rfm69_sendFrame(UINT8 toAddress, const void* buffer, UINT8 bufferSize, BOOL requestACK, BOOL sendACK) {
    rfm69_setMode(RF69_MODE_STANDBY); // turn off receiver to prevent reception while filling fifo
    while ((rfm69_readReg(REG_IRQFLAGS1) & RF_IRQFLAGS1_MODEREADY) == 0x00); // wait for ModeReady
    rfm69_writeReg(REG_DIOMAPPING1, RF_DIOMAPPING1_DIO0_00); // DIO0 is "Packet Sent"
    if (bufferSize > RF69_MAX_DATA_LEN) bufferSize = RF69_MAX_DATA_LEN;

    UINT8 CTLbyte = 0x00;
    if (sendACK)
        CTLbyte = RFM69_CTL_SENDACK;
    else if (requestACK)
        CTLbyte = RFM69_CTL_REQACK;

    UINT8 _address = 15; //64; //replace with nodeID
    UINT8 tmpRADIO_IE = RADIO_IE;
    RADIO_IE = 0; // disable radio ints during communication
    RADIO_CS = 0; // select radio SPI bus
    spiPut(REG_FIFO | 0x80);
    spiPut(bufferSize + 3);
    spiPut(toAddress);
    spiPut(_address);
    spiPut(CTLbyte);
    UINT8 i = 0;
    for (i; i < bufferSize; i++) {
        spiPut(((UINT8*) buffer)[i]);
    }
    RADIO_CS = 1; // de-select radio SPI bus
    RADIO_IE = tmpRADIO_IE; // restore interrupt state

    // no need to wait for transmit mode to be ready since its handled by the radio
    rfm69_setMode(RF69_MODE_TX);

    RADIO_IE = 0;
    UINT32 txStart = millis();
    while (RADIO_D0_PIN == 0 && millis() - txStart < RF69_TX_LIMIT_MS); // wait for DIO0 to turn HIGH signalling transmission finish
//    while (rfm69_readReg(REG_IRQFLAGS2) & RF_IRQFLAGS2_PACKETSENT == 0x00); // wait for ModeReady
    DelayMs(20);    
    RADIO_IF = 0;
    RADIO_IE = 1;
    rfm69_setMode(RF69_MODE_STANDBY);
    
}


:o



WhiteHare

#13
The usual way is to monitor REG_OPMODE until it shows the target mode has become operational.  Just looking at MODEREADY might give you a false positive because, for example, if moving into RX mode from idle mode, the sequencer first has to do PLL mode.

So, come to think of it, that actually answers my own question (cf. reply #11 above): it is an example that proves the need to check for mode change completion.   :)

Smu_Puh

Still the same behavior...

I have risen the
retrayWaitTime
to 400ms, the
retries
to 4 times and set a 20ms Delay right after the
while (RADIO_D0_PIN == 0);
in
sendFrame

With this setting i´m receiving 8 of 10 acknowledgements and a very low RSSI again.

Anywone else?