Lora-net / LoRaMac-node

Reference implementation and documentation of a LoRa network node.
Other
1.88k stars 1.09k forks source link

How to measure accurately the RX1 and RX2 delays? #181

Closed FoujanetG closed 7 years ago

FoujanetG commented 7 years ago

Hi all,

I received the downlink frame but I would like to measure accurately the time betwwen the end of an uplink and the start of RX window.

The goal is to check that RX1 is opened after RX1_RECEIVE_DELAY1 with +/- 20µseconds.

Some delay must be tuned if the MCU is not the same, or if the clock is different(PLL@32MHz or HSI 16MHz) for example.

I play with a GPIO to measure the delay between the end of the uplink and the start of the RX1. I add a GPIO_WRITE_SET just before to call the callback RadioEvents->TxDone( ); in DIO0 handler in sx1276.c And I swith OFF the GPIO at the end of the function SX1276SetRx in sx1276.c

when I zoom in the first edge, I'am not sure of the end of the uplink? How to check accurately the end of radio transmission?

Do you think is it the good way?

thanks GF

pdemil commented 7 years ago

Another way is to use a Logic Analyzer and look at the (little) voltage drops indicating the end of your uplink transmission and the start of your RX window(s).

mluis1 commented 7 years ago

The +/- 20 µseconds precision is critical for the gateway side.

Achieving this precision on the mote side will be very hard. That's why the Rx windows timeouts are larger and dependent on the spreading factor in use (lower the SF higher the number of symbTimeout) as well as the opening of the Rx window is done earlier in time.

Example of symbTimeout usage inside the LoRaMac.c file:

    uint16_t symbTimeout = 5; // DR_2, DR_1, DR_0
    int8_t datarate = 0;
    uint32_t bandwidth = 0; // LoRa 125 kHz

...

    // For higher datarates, we increase the number of symbols generating a Rx Timeout
    if( ( datarate == DR_3 ) || ( datarate == DR_4 ) )
    { // DR_4, DR_3
        symbTimeout = 8;
    }
    else if( datarate == DR_5 )
    {
        symbTimeout = 10;
    }
    else if( datarate == DR_6 )
    {// LoRa 250 kHz
        bandwidth  = 1;
        symbTimeout = 14;
    }

Personally I have modified my radio driver as follows in order to measure the timings.

void SX1276SetOpMode( uint8_t opMode )
{
#if defined( USE_RADIO_DEBUG ) && defined( USE_DEBUG_PINS )
    switch( opMode )
    {
        case RF_OPMODE_TRANSMITTER:
            GpioWrite( &DbgPin1, 1 );
            break;
        case RF_OPMODE_RECEIVER:
        case RFLR_OPMODE_RECEIVER_SINGLE:
            GpioWrite( &DbgPin2, 1 );
            break;
        default:
            GpioWrite( &DbgPin1, 0 );
            GpioWrite( &DbgPin2, 0 );
            break;
    }
#endif
    if( opMode == RF_OPMODE_SLEEP )
    {
        SX1276SetAntSwLowPower( true );
    }
    else
    {
        SX1276SetAntSwLowPower( false );
        SX1276SetAntSw( opMode );
    }
    SX1276Write( REG_OPMODE, ( SX1276Read( REG_OPMODE ) & RF_OPMODE_MASK ) | opMode );
}