Author Topic: Address filtering in AT86RF231 does not work  (Read 4212 times)

0 Members and 1 Guest are viewing this topic.

Offline ananth_muraliTopic starter

  • Newbie
  • Posts: 8
  • Country: us
Address filtering in AT86RF231 does not work
« on: February 16, 2016, 04:39:09 pm »
Hi,

I am using the AT86RF231 radio in extended mode to get the hardware ACKs working. When a receiver receives a message, the following interrupts are raised: RX_START, AMI (Address Match Interrupt) followed by end of reception (TRX_END interrupt). The transmitter gets back the ACK successfully as well. However, when there are 2 receivers and a msg is meant only to one of them, both of them receive the msg and send back an ACK. This means that somehow the address filtering logic is not working. I need help figuring this out please. Here are my configuration details:

1. The transmission msg header is as follows:
     a. FCF (2 bytes) - bit 0 to 15 - 34851
         Bit 0,1,2 - Frame type is MAC - 011
         Bit 3 (security enabled) - 0
         Bit 4 (frame pending) - 0
         Bit 5 (Ack request) - 1
         Bit 6 (Intra pan) - 0 (src PAN is not omitted)
         Bit 7,8,9 (Reserved) - 000
         Bit 10, 11 (16-bit short src address) - 10
         Bit 12, 13 (Frame version) - 00
         Bit 14,15 (dest address) - 10
    b. Sequence number - 1 byte
    c. Dest pan - 2 bytes
    d. Dest address - 2 bytes
    e. Src pan - 2 bytes
    f. Src address - 2 bytes
    g. Some extra information needed by my MAC protocol such as length, type of the msg - 4 bytes. Not sure if including this in the header causes any problems.

2. AACK_UPLD_RES_FT and AACK_FLTR_RES_FT - set to 0
3. AACK_FVN_MODE - set to 00 so that only frame version 0 is acknowledged.
In the initialization routine of the radio, the address and PAN_IDs are set as follows:
            UINT16 addressHigh = GetAddress() >> 8;
            UINT16 addressLow = GetAddress() & 0xFF;
            WriteRegister(RF230_SHORT_ADDR_0, addressLow);
            WriteRegister(RF230_SHORT_ADDR_1, addressHigh);

However, only when AACK_UPLD_RES_FT and AACK_FLTR_RES_FT are set to 1 and AACK_FVN_MODE is set to 11, are ACKs generated. This indicates that my msg header has some reserved fields. I am not sure what I am doing wrong. Any help in this regard would be great.

UPDATE 1:

1. AACK_FVN_MODE is set to 01 (Acknowledge frames with version number 0 or 1) and AACK_UPLD_RES_FT and AACK_FLTR_RES_FT are set to 0 (not process reserved frame types).
2. FCF is set to 33809 (No reserved frame types).
         Bit 0,1,2 - Frame type is DATA - 100
         Bit 3 (security enabled) - 0
         Bit 4 (frame pending) - 0
         Bit 5 (Ack request) - 1
         Bit 6 (Intra pan) - 0 (srcpan is ignored)
         Bit 7,8,9 (Reserved) - 000
         Bit 10, 11 (16-bit short src address) - 01
         Bit 12, 13 (Frame version) - 00
         Bit 14,15 (dest address) - 01
3. Radio's address is set to 0x0.
            WriteRegister(RF230_SHORT_ADDR_0, 0x00);
            WriteRegister(RF230_SHORT_ADDR_1, 0x00);
4. Transmitter sends msg to 0x00 (dest address is 0x00), then an AMI and TRX_END interrupts are generated and an ACK is generated as well.
5. However, if transmitter sends msg to 0x1111 for instance (dest address is still 0x00), then an AMI and TRX_END interrupts along with an ACK are generated. This should not happen if address filtering works correctly.
     b. This indicates that there is something wrong with the address field configuration. I am not sure what the problem is though.


Thanks,
Ananth.       
« Last Edit: February 16, 2016, 08:06:10 pm by ananth_murali »
 

Online ataradov

  • Super Contributor
  • ***
  • Posts: 11259
  • Country: us
    • Personal site
Re: Address filtering in AT86RF231 does not work
« Reply #1 on: February 16, 2016, 07:11:26 pm »
Have you tried just a basic configuration without changing XAH_CTRL_1 register?

The simplest code that actually works can be found in the PHY driver of the Lightweight Mesh - http://www.atmel.com/tools/lightweight_mesh.aspx

Alex
 

Online ataradov

  • Super Contributor
  • ***
  • Posts: 11259
  • Country: us
    • Personal site
Re: Address filtering in AT86RF231 does not work
« Reply #2 on: February 16, 2016, 07:27:11 pm »
And also don't change AACK_FVN_MODE for a test. And in the UPDATE 1, do you have both radios with address 0?

I'm kind of lost in all the changes between the tests.
Alex
 

Offline ananth_muraliTopic starter

  • Newbie
  • Posts: 8
  • Country: us
Re: Address filtering in AT86RF231 does not work
« Reply #3 on: February 16, 2016, 08:05:24 pm »
Thanks for your response Alex. I will remove update 2 so that it is less confusing.

Have you tried just a basic configuration without changing XAH_CTRL_1 register?

The simplest code that actually works can be found in the PHY driver of the Lightweight Mesh - http://www.atmel.com/tools/lightweight_mesh.aspx

   Yes, I did try a basic configuration and tx always gets an ACK irrespective of what address the src is set to or the address to which the tx transmits.. There is no AMI generated (if the radios are set to their respective addresses or 0x0)

And also don't change AACK_FVN_MODE for a test. And in the UPDATE 1, do you have both radios with address 0?

    Yes, both radios are set to address 0.
« Last Edit: February 16, 2016, 08:32:33 pm by ananth_murali »
 

Online ataradov

  • Super Contributor
  • ***
  • Posts: 11259
  • Country: us
    • Personal site
Re: Address filtering in AT86RF231 does not work
« Reply #4 on: February 16, 2016, 08:18:59 pm »
If both of them have address 0, how they should react? They both will ACK the frame, of course.
Alex
 

Offline ananth_muraliTopic starter

  • Newbie
  • Posts: 8
  • Country: us
Re: Address filtering in AT86RF231 does not work
« Reply #5 on: February 16, 2016, 08:38:18 pm »
If both of them have address 0, how they should react? They both will ACK the frame, of course.

If receiver's address is something like 0x1ABE and transmitter sends to address 0x1000, then also frame is ACKd.
Btw, I modified my previous response after updating my test.
« Last Edit: February 16, 2016, 08:43:06 pm by ananth_murali »
 

Online ataradov

  • Super Contributor
  • ***
  • Posts: 11259
  • Country: us
    • Personal site
Re: Address filtering in AT86RF231 does not work
« Reply #6 on: February 16, 2016, 08:53:52 pm »
There must be something else configured. The radio should not (and it does not) behave this way.

Do you have a sniffer to confirm this? Can you attach some sniffer logs and complete radio registers initialization code?
Alex
 

Offline ananth_muraliTopic starter

  • Newbie
  • Posts: 8
  • Country: us
Re: Address filtering in AT86RF231 does not work
« Reply #7 on: February 16, 2016, 09:04:27 pm »
I don't have access to a sniffer at the moment, but I am trying to get one.

Here is the radio register initialization code. These are done after setting the channel, CCA, transmit power and interrupts (at the very end of initialization).

UINT16 addressHigh = GetAddress() >> 8;
UINT16 addressLow = GetAddress() & 0xFF;
WriteRegister(RF230_SHORT_ADDR_0, addressLow);
WriteRegister(RF230_SHORT_ADDR_1, addressHigh);
WriteRegister(RF230_PAN_ID_0, 0x0);
WriteRegister(RF230_PAN_ID_1, 0x0);
WriteRegister(RF230_IEEE_ADDR_0, 0x00);
WriteRegister(RF230_IEEE_ADDR_1, 0x00);
WriteRegister(RF230_IEEE_ADDR_2, 0x00);
WriteRegister(RF230_IEEE_ADDR_3, 0x00);
WriteRegister(RF230_IEEE_ADDR_4, 0x00);
WriteRegister(RF230_IEEE_ADDR_5, 0x00);
WriteRegister(RF230_IEEE_ADDR_6, 0x00);
WriteRegister(RF230_IEEE_ADDR_7, 0x00);

//RX_AACK configuration
WriteRegister(RF230_TRX_CTRL_2, 0x00);
WriteRegister(RF230_XAH_CTRL_1, 0x04);
WriteRegister(RF230_XAH_CTRL_0, 0x0E);
WriteRegister(RF230_CSMA_SEED_1, 0x42);
WriteRegister(RF230_CSMA_SEED_0, 0xAA);

//TX_ARET configuration
WriteRegister(RF230_TRX_CTRL_1, 0x20);
WriteRegister(RF230_CSMA_BE, 0x53);
 

Online ataradov

  • Super Contributor
  • ***
  • Posts: 11259
  • Country: us
    • Personal site
Re: Address filtering in AT86RF231 does not work
« Reply #8 on: February 16, 2016, 09:11:59 pm »
I don't have access to a sniffer at the moment, but I am trying to get one.
How do you know that frame gets ACKed then?

I don't see anything specifically wrong with your settings.
Alex
 

Offline ananth_muraliTopic starter

  • Newbie
  • Posts: 8
  • Country: us
Re: Address filtering in AT86RF231 does not work
« Reply #9 on: February 16, 2016, 09:26:42 pm »
How do you know that frame gets ACKed then?

I don't see anything specifically wrong with your settings.

On the transmitter side, as soon as the transmission is done (TRX_END interrupt), the transmitter reads the TRX_STATE register and gets the value of last 3 bits (TRAC_STATUS). If the value is 0, then the frame was ACKed.

The transmitter defines the header as follows:

typedef struct IEEE802_15_4_Header {
  UINT16 fcf;
  UINT8 dsn;         //Sequence number
  UINT16 destpan;
  UINT16 dest;
  //UINT16 srcpan;
  UINT16 src;
}IEEE802_15_4_Header_t;

Before transmission, the length of the payload (MPDU) along with CRC length (2 bytes) and timestamp length (4 bytes) are written to the frame buffer. This is followed by writing the MPDU to the buffer.
Do you see anything wrong in this?
 

Online ataradov

  • Super Contributor
  • ***
  • Posts: 11259
  • Country: us
    • Personal site
Re: Address filtering in AT86RF231 does not work
« Reply #10 on: February 16, 2016, 09:32:48 pm »
On the transmitter side, as soon as the transmission is done (TRX_END interrupt), the transmitter reads the TRX_STATE register and gets the value of last 3 bits (TRAC_STATUS). If the value is 0, then the frame was ACKed.
Is it still 0, when receiving device is physically off?

Do you see anything wrong in this?
I suspect that there is something wrong with frame buffer access or the way you send the frame.

1. Show how do you write data into the buffer. Better yet, make a byte-by-byte dump of all the bytes you write there.
2. Make sure you are using advanced mode for transmitting. No ACK is expected in the basic mode.
Alex
 

Offline ananth_muraliTopic starter

  • Newbie
  • Posts: 8
  • Country: us
Re: Address filtering in AT86RF231 does not work
« Reply #11 on: February 16, 2016, 10:40:03 pm »
Is it still 0, when receiving device is physically off?

Yes, it is 0 when receiver is off (FCF is 50705). If FCF is say 33826 (src and dest address fields are reserved), the value is 5 (NO_ACK).

I suspect that there is something wrong with frame buffer access or the way you send the frame.

1. Show how do you write data into the buffer. Better yet, make a byte-by-byte dump of all the bytes you write there.

Here is a byte-by-byte dump of the bytes written to the buffer. Please let me know if this is not clear enough. I have added comments to make it clear.

Length (sum of payload (18 bytes), CRC (2 bytes), timestamp (4 bytes) for a total of 24 bytes - 0x18):
  18
FCF:
  11
  c6
Seq number:
  73
  00
Destpan:
  00
  00
Dest:
  00
  10
Src:
  ba
  7b
Payload (I send an increasing sequence number at the beginning 2 bytes followed by constant values of 1,2,3,4,5):
  01
  00
  01
  02
  03
  04
  05
  00
Timestamp:
  eb
  1e
  00
  00


2. Make sure you are using advanced mode for transmitting. No ACK is expected in the basic mode.

Yes, I am using advanced mode for transmitting.
 

Online ataradov

  • Super Contributor
  • ***
  • Posts: 11259
  • Country: us
    • Personal site
Re: Address filtering in AT86RF231 does not work
« Reply #12 on: February 16, 2016, 10:54:53 pm »
I think your FCF is incorrect. Try 0x8861. This is a standard FCF for ACK REQ + PAN ID Comp. Yours does not request an ACK.

Also, sequence number is one byte.  And there  is no timestamp, but that specifically is not important right now.
Alex
 

Offline ananth_muraliTopic starter

  • Newbie
  • Posts: 8
  • Country: us
Re: Address filtering in AT86RF231 does not work
« Reply #13 on: February 16, 2016, 11:27:52 pm »
If I understand FCF correctly, 0x8861 translates to below (table 1). If so, bit 5 is set to 0. How does this configuration request an ACK? I believe the bits should be reversed (table 2). Then it makes sense and I have used this configuration, but I interpreted it incorrectly.

Table 1:
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
1 0 0 0 1 0 0 0 0 1  1  0   0   0  0   1

Table 2:
15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0
1   0  0   0   1   0  0 0 0 1 1 0 0 0 0 1


I will change the sequence number to one byte and let you know what happens.
 

Online ataradov

  • Super Contributor
  • ***
  • Posts: 11259
  • Country: us
    • Personal site
Re: Address filtering in AT86RF231 does not work
« Reply #14 on: February 16, 2016, 11:29:13 pm »
Bit 0 is an LSB. Your table 2 is correrct.
Alex
 

Offline ananth_muraliTopic starter

  • Newbie
  • Posts: 8
  • Country: us
Re: Address filtering in AT86RF231 does not work
« Reply #15 on: February 16, 2016, 11:58:34 pm »
Changing that 2 byte seq number to 1 byte, along with 0x8861 did the trick I believe. Address filtering is working (if sender sends to correct receiver, sender gets an ACK. If sender sends to an incorrect address, no ACK is received). In the struct for the 802.15.4 header, seq number is defined as 1 byte. However, GCC is packing the 1 byte into 2 bytes (because the size of the header should be 9, but I get 10). This causes the subsequent bytes to be shifted and thus causing the address filter to not work.

I believe everything should work from here onwards. If there is anything else that comes up, I will either continue this thread or start a new post.

Alex, thank you very much. You have helped me fix a bug that we have been trying to fix for about a week.
« Last Edit: February 17, 2016, 03:32:28 pm by ananth_murali »
 

Online ataradov

  • Super Contributor
  • ***
  • Posts: 11259
  • Country: us
    • Personal site
Re: Address filtering in AT86RF231 does not work
« Reply #16 on: February 17, 2016, 12:02:40 am »
You can actually pack your structures that are used in protocols.

#define PACK __attribute__ ((packed))

typedef struct PACK NwkFrameHeader_t
{
  uint16_t    macFcf;
  uint8_t     macSeq;
  uint16_t    macDstPanId;
  uint16_t    macDstAddr;
  uint16_t    macSrcAddr;
  // ........
} NwkFrameHeader_t;

This will force GCC to put all members in the packed way. This will generate less efficient code, but in my experience it is way more efficient than hand assembled structures using >>'s and &'s.
Alex
 


Share me

Digg  Facebook  SlashDot  Delicious  Technorati  Twitter  Google  Yahoo
Smf