MRF24J40MA Transceiver Help
Chemikal
Posts: 32
So I got some new transceivers (Microchip MRF24J40MA modules) to play with, having used the XBees in the past, and I got myself stuck. I believe my issue is with my end-point not being associated with the coordinator, but it could be many other things... Rather than having a setup utility for all the addressing and registers, I am going at it from scratch, and am missing something...
Does anyone have any experience with these particular modules? If so, what is the method for getting simple data packets going between two units?
As you'll see in my code below, the WriteFIFO code result... when I run it on my endmodule, I get a 'successful TX' result (after checking the TX result from the TXSTAT register)... yet, my coordinator just sits there... where the interrupt pin never goes Low (I have the interrupt register set to trigger on RX packet), so it's not receiving anything... :sigh
Currently:
- My coordinator and endmodule have the same PANID, with the coordinator's short address and 64-bit address set to all zeros. My endmodule has $1010 for its short address and all $DD's for its 64-bit address.
- I build a packet, after following (I think?) the IEEE 802.15.4 - 2003 standard, load it into the TX FIFO of the endmodule, and try to transmit it to the coordinator... nothing happens on the coordinator end.
Here's my packet TX code (where Pointer is to a byte array of the data I want to send; Length is the number of bytes from that array to send):
- Registers set in a two-step process at boot: "SetDefaultRegisters" for all of the common registers for any unit... and then, additionally, for the coordinator "SetCoordinatorRegisters," or for the endmodule "SetEndDeviceRegisters":
Anyways - Do I have to form a MAC command or beacon packet or something to associate/link the endmodule into the coordinator's PAN, or do anything else other than setting the registers and start filling and firing FIFO data packets? Or give me some pointers of what I might want to look into?
Appreciate the help if you can -
Datasheets:
IEEE 802.15.4 - 2003: http://www.cs.jhu.edu/~cliang4/public/datasheets/802.15.4-2003.pdf
The module overview: http://ww1.microchip.com/downloads/en/DeviceDoc/70329b.pdf
The IC of the module - the registers, etc. documentation: http://ww1.microchip.com/downloads/cn/DeviceDoc/cn520295.pdf
Does anyone have any experience with these particular modules? If so, what is the method for getting simple data packets going between two units?
As you'll see in my code below, the WriteFIFO code result... when I run it on my endmodule, I get a 'successful TX' result (after checking the TX result from the TXSTAT register)... yet, my coordinator just sits there... where the interrupt pin never goes Low (I have the interrupt register set to trigger on RX packet), so it's not receiving anything... :sigh
Currently:
- My coordinator and endmodule have the same PANID, with the coordinator's short address and 64-bit address set to all zeros. My endmodule has $1010 for its short address and all $DD's for its 64-bit address.
- I build a packet, after following (I think?) the IEEE 802.15.4 - 2003 standard, load it into the TX FIFO of the endmodule, and try to transmit it to the coordinator... nothing happens on the coordinator end.
Here's my packet TX code (where Pointer is to a byte array of the data I want to send; Length is the number of bytes from that array to send):
PUB WriteFIFO(Pointer,Length) | i,Data,crc,crc1,crc2 bytefill(@TXData,0,200) TXData[0] := 9 'Header length TXData[1] := 9 + Length 'Frame length | Header length + Payload size TXData[2] := %00100010 'Frame control | Frame Type: Data, Security disabled, Single packet, No ack, No source identifier TXData[3] := %00100010 'Frame control | Destination address: 16bit short, Source address: 16-bit short TXData[4] := $53 'Sequence number ******* Each device needs to init with a UNIQUE, SINGLE number; Used with ACK ************ 'Addressing Fields ******* Future for selectable addresses, hardcoded to Coordinator ****************** TXData[5] := $25 'Destination PAN identifier TXData[6] := $25 TXData[7] := $00 'Destination address TXData[8] := $00 'Source PAN identifier: Not required (?), since Intra-PAN = "1" and dest & source addresses defined TXData[9] := $DD 'Source address TXData[10] := $DD 'Data payload: repeat i from 11 to (11+Length-1) TXData[i] := byte[Pointer][i-11] 'Calculate CRC: crc := 0 repeat i from 2 to (11+Length-1) crc := CalcCRC(TXData[i],crc) 'Set the CRC bytes: crc1 := crc >> 8 'get the first byte from the 16-bit crc result crc2 := crc | %1111111100000000 'get the second byte (2-step operation: OR, XOR) crc2 := crc2 ^ %1111111100000000 TXData[11+Length] := crc1 TXData[11+Length+1] := crc2 'Fill the TX Normal FIFO: repeat i from 0 to (TXData[1] + 1) '(TXData[1] -1) is to the end of the data, but +2 for CRC ForceLongAddress := 1 'Set ForceLongAddress to "1" to force a write to a long address Write($0000 + i,TXData[i]) Write(TXNCON,%00000001) 'Transmit the packet by setting the TXNTRIG (TXNCON 0x1B<0>) bit = 1. Auto cleared by hardware 'A TXNIF (INTSTAT 0x31<0>) interrupt will be issued. The TXNSTAT (TXSTAT 0x24<0>) bit indicates the status of the transmission: ' TXNSTAT = 1: Transmission was successful ' TXNSTAT = 0: Transmission failed, retry count exceeded 'The number of retries of the most recent transmission is contained in the TXNRETRY (TXSTAT 0x24<7:6>) bits. 'The CCAFAIL (TXSTAT 0x24<5>) bit = 1 indicates if the failed transmission was due to the channel busy (CSMA-CA timed out). repeat until ina[INTpin] == 0 Read(INTSTAT) 'Read INTSTAT to clear the interrupt Data := Read(TXSTAT) Data &= %00000001 If Data == %00000001 return 1 'Successful TX Else return 0 'Failed TX PUB CalcCRC(data,crcc):newcrc|i,icrc 'CCITT-CRC 16-bit XModem CRC calculator 'Documentation: http://web.mit.edu/6.115/www/miscfiles/amulet/amulet-help/xmodem.htm crcc:=crcc^(data<<8) repeat i from 0 to 7 if crcc&$8000 crcc:=((crcc<<1)&$FFFF)^$1021 else crcc:=(crcc<<=1)&$FFFF return crcc&$FFFF
- Registers set in a two-step process at boot: "SetDefaultRegisters" for all of the common registers for any unit... and then, additionally, for the coordinator "SetCoordinatorRegisters," or for the endmodule "SetEndDeviceRegisters":
PUB SetDefaultRegisters '' DESCRIPTION: '' Sets all of the configuration registers to the default, desired values 'Software reset Write(SOFTRST,$07) 'Set initialization parameters Write(PACON2,$98) Write(TXSTBL,$95) Write(RFCON1,$01) Write(RFCON2,$80) Write(RFCON6,$90) Write(RFCON7,$80) Write(RFCON8,$10) Write(SLPCON1,$21) Write(BBREG2,$80) Write(CCAEDTH,$60) Write(BBREG6,$40) 'Set Interrupts: Set with INTCON, read with INTSTAT Write(INTCON,%11110110) 'Set Channel Write(RFCON0,$54) 'Channel 16, 2.430GHz 'Reset RF state machine: Write(RFCTL,$04) Write(RFCTL,$00) waitcnt(16_000 + cnt) 'wait 200uS (0.0002 sec) PUB SetCoordinatorRegisters 'Program the short MAC Address, 0x2525 Write(PANIDL,$25) Write(PANIDH,$25) Write(SADRL,$00) Write(SADRH,$00) 'Program Long MAC Address, 0x0000000000000000 Write(EADR0, $00) Write(EADR1, $00) Write(EADR2, $00) Write(EADR3, $00) Write(EADR4, $00) Write(EADR5, $00) Write(EADR6, $00) Write(EADR7, $00) 'NonBeacon settings Write(RXMCR,%00001111) '**Coordinator & Promiscuous mode to receive ALL packets with a good CRC Write(TXMCR,%00011100) Write(ORDER,%11111111) 'Reset RF state machine: Write(RFCTL,$04) Write(RFCTL,$00) waitcnt(16_000 + cnt) 'wait 200uS (0.0002 sec) PUB SetEndDeviceRegisters 'Program the short MAC Address Write(PANIDL,$25) Write(PANIDH,$25) Write(SADRL,$10) Write(SADRH,$10) 'Program Long MAC Address, 0xDDDDDDDDDDDDDDDD Write(EADR0, $DD) Write(EADR1, $DD) Write(EADR2, $DD) Write(EADR3, $DD) Write(EADR4, $DD) Write(EADR5, $DD) Write(EADR6, $DD) Write(EADR7, $DD) 'NonBeacon settings Write(RXMCR,%00000000) Write(TXMCR,%00011100) Write(ORDER,%11111111) 'Reset RF state machine: Write(RFCTL,$04) Write(RFCTL,$00) waitcnt(16_000 + cnt) 'wait 200uS (0.0002 sec)
Anyways - Do I have to form a MAC command or beacon packet or something to associate/link the endmodule into the coordinator's PAN, or do anything else other than setting the registers and start filling and firing FIFO data packets? Or give me some pointers of what I might want to look into?
Appreciate the help if you can -
Datasheets:
IEEE 802.15.4 - 2003: http://www.cs.jhu.edu/~cliang4/public/datasheets/802.15.4-2003.pdf
The module overview: http://ww1.microchip.com/downloads/en/DeviceDoc/70329b.pdf
The IC of the module - the registers, etc. documentation: http://ww1.microchip.com/downloads/cn/DeviceDoc/cn520295.pdf
Comments
Apparently my transmitter wasn't powered correctly - You'd think I'd have learned by now from using cheap breadboards.
Even though I could read and write to the registers fine, and the interrupt pin was going low after each TX attempt - I had been noticing that the interrupt pin's voltage on my scope was ~2.6v, rather than the 3.3 I had expected, but thought nothing of it... apparently the breadboard's power rail doesn't carry the length of the board, or has some sort of resistive effect... worthless.
Anyways, I now have a fully functional transceiver setup - sending data at 100hz across the house without a single dropped packet - SO much better than the RFM22s I picked up before these, which have awful documentation and equally awful performance. Love these things.
Hi Chemikal,
Sorry for the newbie question, but I was wondering how you would solder this thing on regular prototyping board or even a breadboard?