Double Side Two Way Ranging (DS-TWR)

Hi All,

I try to test Double Side Two Way Ranging (DS-TWR) using three messages with my own code,
There is an issue that i didn’n understand. When i calculate propagation time Tprop using timestamps, the value is negative

My code works in the following way,

  1. Device A send packet at time T1A (delayed send)
  2. Device B get the packet at time T1B ,
  3. Device B respond at time T2B (delayed send)
  4. Device A get the respond at time T2A
  5. Device A send packet at time T3A (delayed send)
  6. Device B get the respond at time T3B

Here is one of the test timings (timestamps)

T1A = 0x00FF9EBE00 (4288593408)
T2A = 0x011588B0AC (4656246956)
T3A = 0x0133C0D600 (5163243008)

T1B = 0x5340EB22AC (357571437228)
T2B = 0x5358B35800 (357970434048)
T3B = 0x5376EC883F (358477498431)

When i calculate the propagation time Tprop (You can see the formula below figure 38 in DW1000 user manual)
Tprop = -8909809

Does anyone have any idea about this issue?

Regards

Metin

In your case, T1B-T2B is greater than T2A-T1A which means that your turnaround time is shorter than delayed send time. Check the way you programm delayed send value or you read timestamps.

Regards,

Bartosz Kawłatow

Hi Bartosz,

Yes, Treply1 is greater than Tround1.
I test it many time but result is same.
I clear all code to be sure and debuging, but always same.

My code do only that;

In Tag’s code: I write to TX_BUFFER, select TX_MODE, when frame is send select RX_MODE, reading TX_TIME, when frame is received read RX_TIME, that is all in tag side.
In Anchor’s code: Select RX_MODE, when frame is received read RX_TIME, write to TX_BUFFER, select TX_MODE, when frame is send read TX_TIME, that is all in anchor side

I think the clocks are different

Regards

Metin

I think it is quite hard to help you with the code when we didn’t see even a single line of it :slight_smile:

Regards,

Bartosz Kawłatow

TAG’s code

       dwt_writetodevice(TX_BUFFER_ID,0,27,Tx_Buffer_DSTWR);
        Mode_Slct(Tx_Mode);
        for(;;)
        {
          dwt_readfromdevice(SYS_STATUS_ID,0,1,&SYS_STATUS_Byte_0);
          if(SYS_STATUS_TXFRS & SYS_STATUS_Byte_0)        
          {
            dwt_readfromdevice(TX_TIME_ID,0,10,Tx_Time_Stamp);
            Mode_Slct(Rx_Mode);
            for(;;)
            {
              if(1 == Receive_Data())
              {
                 dwt_readfromdevice(RX_TIME_ID,0,14,Rx_Time_Stamp_Gelen);
                 RS485_Dizi_Yaz(10,Tx_Time_Stamp);
                 YAZ_RS485(0x3A);
                 RS485_Dizi_Yaz(14,Rx_Time_Stamp_Gelen);
                 for(;;);
                 
              }
              else if(2 == Receive_Data())                         // receive yaparken hata oluştu,
              {
                // burada tekrardan state 1 e geçilmesi gerekiyor, ranging başarısız oldu
              }
            }
          }
        }


                                                     Anchor's code

        Mode_Slct(Rx_Mode);
        for(;;)
        {
          if(1 == Receive_Data())
          {
              dwt_readfromdevice(RX_TIME_ID,0,14,Rx_Time_Stamp_DSTWR_State_1);
              dwt_writetodevice(TX_BUFFER_ID,0,28,Tx_Buffer_DSTWR);
              Mode_Slct(Tx_Mode);
              for(;;)
              {
                  dwt_readfromdevice(SYS_STATUS_ID,0,1,&SYS_STATUS_Byte_0);
                  if(SYS_STATUS_TXFRS & SYS_STATUS_Byte_0)        
                  {
                    dwt_readfromdevice(TX_TIME_ID,0,10,Tx_Time_Stamp);
                    RS485_Dizi_Yaz(10,Tx_Time_Stamp);
                    YAZ_RS485(0x3A);
                    RS485_Dizi_Yaz(14,Rx_Time_Stamp_DSTWR_State_1);
                    for(;;);
                  }
              }
          }
        }

:slight_smile: this is all the code, as you see there is nothing special, only send and receive :), but i can’t understand why the response time is greater then round time.
DW1000 works in default configurations

Regards

Metin

Is this the formula you use, to calculate Tprop (Decawave’s UM):f

Yes,

This is the formula which i use. To debug the code, i discard the last propagation, Because Treply1 is greater than Tround1, now i try to find why Treply1 is greater than Tround1

Metin

Tag and anchor clocks run at different frequencies, as they are independent clocks, the two times should be close (as the TOF is in ns… very small), what are the actual delays you are using? The feature of the double sided ranging is that these clock differences cancel out. Have you read the application note from Decawave (APS011) on TWR error sources?

ag and anchor clocks run at different frequencies, as they are independent clocks, the two times should be close (as the TOF is in ns… very small), what are the actual delays you are using? The feature of the double sided ranging is that these clock differences cancel out. Have you read the application note from Decawave (APS011) on TWR error sources?

I can understand the clocks difference, i change the code of tag and anchor (mean that change tag to anchor and anchor to tag physically) to test it, but the result is close, if the clocks are different (we talk about 36.071.748 ticks. Treply1-Tround1 = 36.071.748 ), when we change the roles (tag to anchor, anchor to tag), Tround1 must be greater than Treply1, isn’t it? But the result is close…

If you have suggestions, i can try?

Regards

Metin

Hi All,

My problem is fixed,
When i doing steps on user manual page 23 (LDOLOAD) the problem is solved. In receiver mode you have to load ROM into RAM if you want to get receive timestamp, but in transmit mode it is not necessary, you can get TX timestamp without LDOLOAD. But if you don’t load ROM into RAM (LDOLOAD), transmitter’s clock is slower than receiver’s.

Let me explain on software steps, my programming steps are below

  1. Device A send packet at time T1A (delayed send)
  2. Device B get the packet at time T1B ,
  3. Device B respond at time T2B (delayed send)
  4. Device A get the respond at time T2A
  5. Device A send packet at time T3A (delayed send)
  6. Device B get the respond at time T3B

At first step, the tag is in transmit mode and there is no LDOLOAD, the anchor is in receive mode and LDOLOAD is existing (if not, RX timestamp is 0), so tag’s clock count slower than anchor’s.
Here is the result without LDOLOAD to tag

T1A = 0x00FF9EBE00 (4288593408)
T2A = 0x011588B0AC (4656246956)
T3A = 0x0133C0D600 (5163243008)

T1B = 0x5340EB22AC (357571437228)
T2B = 0x5358B35800 (357970434048)
T3B = 0x5376EC883F (358477498431)

Tprop = -8.909.809 ticks

Here is the result after LDOLOAD is aplly to tag and anchor at the begining of code

T1A = 4235201024
T2A = 4625456330
T3A = 5212858368
T1B = 421142387179
T2B = 421532575744
T3B = 422120042716

Tprop = 33.010 ticks
then
Tprop = 501.750 pS

If we calculate distance between TAG and ANCHOR, it is D = 150,5 meter,
but actual distance is 0,5 meter.

I thing it is about calibration, isn’t it?

Regards

Metin

Yes, exactly. You can fix it with the antenna delay or in software. I decided to just subtract the offset. In case of negative results, you know that your ranging attempt has failed.

Yes, i decided to just subtract the offset too :slight_smile:

Hi Metin,

This makes no sense: “But if you don’t load ROM into RAM (LDOLOAD), transmitter’s clock is slower than receiver’s.”

You are correct, the LDE has to be loaded as part of device initialisation, BEFORE ranging is started. The LDE cannot be loaded in the middle of ranging exchange, because to load the LDE the system clock is changed and this will make all of the timings incorrect.

So please load the LDE in the initialisation (as per UM/Decawave API), and then proceed to TX and RX frames.

Regards,
Zoran

So… If I change the enf of the loop in example 5a (ds_twr_init) as:
dwt_entersleep();
sleep_ms(RNG_DELAY_MS);
dwt_spicswakeup(dummy_buffer,DUMMY_BUFFER_LEN);
maybe the next poll_tx timestamp will be incorrect, will it be?

Hi. You need to config antenna delay after wakeup. See RM.

That’s the solution! thank you so much!