Advertisement
stanleyseow

Arduino nRF to Serial

Jun 4th, 2013
352
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 11.29 KB | None | 0 0
  1. /*
  2.  This program will TX all data received from the serial pins out to the nRF radio
  3.  and sent out all the data received from the nRF to serial monitor/process the data
  4.  
  5.  For this code, I m using a GPS module Skylab SKM53 running at 9600bps
  6.  
  7.  Max nRF payload size = 30
  8.  1st byte header :-
  9.  8     : fragment/no fragment
  10.  5 - 7 : number of fragments
  11.  4     : unused
  12.  1 - 3 : fragment sequence number
  13.  
  14.  Max buffer is 90 bytes
  15.  
  16.  Serial input pins RX 2 ,TX 3
  17.  nRF pins CE 8, CSN, 9 MOSI 11, MIS0 12, SCK 13
  18.  
  19.  Date : 28/05/2013
  20.  
  21.  Written by Stanley Seow
  22. */
  23.  
  24. #include <SoftwareSerial.h>
  25. #include <SPI.h>
  26. #include "nRF24L01.h"
  27. #include "RF24.h"
  28. #include "printf.h"
  29.  
  30.  
  31. #define DATABUFFERSIZE 90
  32. char dataBuffer[DATABUFFERSIZE];
  33.  
  34. byte dataBufferIndex = 0;
  35. char startChar = '$';
  36. char endChar = '\r';
  37.  
  38. SoftwareSerial mySerial(2,3);
  39.  
  40. // Set up nRF24L01 radio on SPI pin for CE, CSN
  41. RF24 radio(8,9);
  42.  
  43. const uint64_t pipes[2] = { 0xDEDEDEDEE7ULL, 0xDEDEDEDEE9ULL };
  44.  
  45. // Defines for radio buffers
  46. char RXPayload[33] = "";
  47. char TXPayload[33] = "";
  48. char STR1[33],STR2[33],STR3[33] = "";
  49.  
  50. int Sender, storeString = 0;
  51.  
  52. void setup(void)
  53. {
  54.   Serial.begin(115200);
  55.  
  56.   mySerial.begin(9600);
  57.   delay(500);
  58.  
  59.   printf_begin();
  60.   //printf("nRF Serial RX/TX\n\r");
  61.   radio.begin();
  62.  
  63.   // Default radio setings
  64.   radio.enableDynamicPayloads();
  65.   radio.setDataRate(RF24_250KBPS);
  66.   radio.setPALevel(RF24_PA_MAX);
  67.   radio.setChannel(85);
  68.   radio.setRetries(15,15);
  69.  
  70.   //check for which side is the sender ( receive data via softwareserial )
  71.   if ( mySerial.available() ) {
  72.          Sender = true;
  73.   }
  74.    
  75.   if ( Sender ) {
  76.     radio.openWritingPipe(pipes[0]);
  77.     radio.openReadingPipe(1,pipes[1]);
  78.   } else {
  79.     // this side is the receiver connected to Serial Monitor  
  80.     radio.openWritingPipe(pipes[1]);
  81.     radio.openReadingPipe(1,pipes[0]);  
  82.     radio.startListening();  
  83.   }
  84.  
  85.   //radio.printDetails();
  86.   delay(500);
  87.  
  88. }
  89.  
  90. void loop(void) {
  91.  
  92.   if ( !Sender ) {  
  93.       nRF_Receive();
  94.   } else {
  95.       nRF_Sender();
  96.   }
  97. } // End of loop()
  98.  
  99.  
  100. void nRF_Sender() {
  101.  
  102.   char dataBuffer2[DATABUFFERSIZE]="";
  103.   int status = 0;
  104.  
  105.   if ( mySerial.overflow() ) {
  106.        Serial.println("Overflow Checkpoint 1");
  107.   }
  108.  
  109.   if (getSerialString() ) {
  110.     //Serial.println("123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890");
  111.  
  112.     Serial.println(dataBuffer);
  113.    
  114.     //Serial.print("\t\t\t[");
  115.     //Serial.print(strlen(dataBuffer));
  116.     //Serial.println("]");  
  117.     // Make a copy of dataBuffer
  118.     memcpy(&dataBuffer2, &dataBuffer,strlen(dataBuffer));
  119.  
  120.  
  121.     fragmentPackets(dataBuffer2,strlen(dataBuffer2) );
  122.  
  123.   if ( mySerial.overflow() ) {
  124.        Serial.println("Overflow Checkpoint 2");
  125.   }
  126.  
  127.     sendPackets(STR1,STR2,STR3);
  128.    
  129.   if ( mySerial.overflow() ) {
  130.        Serial.println("Overflow Checkpoint 3");
  131.   }  
  132.  
  133.  }  
  134. }
  135.  
  136.  
  137. boolean getSerialString(){
  138.     static byte dataBufferIndex = 0;
  139.     while(mySerial.available()>0){
  140.         char incomingbyte = mySerial.read();
  141.         if(incomingbyte==startChar){
  142.             dataBufferIndex = 0;  //Initialize our dataBufferIndex variable
  143.             storeString = true;
  144.         }
  145.         if(storeString){
  146.             //Let's check our index here, and abort if we're outside our buffer size
  147.             //We use our define here so our buffer size can be easily modified
  148.             if(dataBufferIndex==DATABUFFERSIZE){
  149.                 //Oops, our index is pointing to an array element outside our buffer.
  150.                 dataBufferIndex = 0;
  151.                 break;
  152.             }
  153.             if(incomingbyte==endChar){
  154.                 dataBuffer[dataBufferIndex] = 0; //null terminate the C string
  155.                 //Our data string is complete.  return true
  156.                 return true;
  157.             }
  158.             else{
  159.                 dataBuffer[dataBufferIndex++] = incomingbyte;
  160.                 dataBuffer[dataBufferIndex] = 0; //null terminate the C string
  161.             }
  162.         }
  163.         else{    
  164.         }
  165.     }
  166.     //We've read in all the available Serial data, and don't have a valid string yet, so return false
  167.     return false;
  168. }
  169.  
  170.  
  171. void fragmentPackets(char Buffer2[DATABUFFERSIZE],int len) {
  172. // Two headers with 30 bytes payload
  173. // 1st byte
  174. //      8 bit - fragment, 1 or 0
  175. // 7 to 5 bit - number of fragment, 111, 7 max fragment
  176. //      4 bit - none
  177. // 1 to 3 bit - fragment number, starting with 0 to 7, 000 to 111
  178. //
  179. // 2nd byte, reserved
  180.  
  181. /*
  182. Serial.print("[");
  183. Serial.print(len);
  184. Serial.print("] ");
  185. Serial.print("Buffer2:");
  186. Serial.println(Buffer2);
  187. */
  188.  
  189.    STR1[0], STR2[0], STR3[0] = 0;
  190.    
  191.    if ( len < 31 ) {
  192.      // for ( int i=0;i<len;i++) {
  193.      //   STR1[i+2] = Buffer2[i]; }
  194.        
  195.      STR1[0] = B00010000;    // No fragmentation, 1 segment
  196.      STR1[1] = 0xff;         // Reversed header  
  197.      STR1[2] = 0;            // null terminate string
  198.      strcat(STR1,Buffer2);
  199.        
  200.    } else if ( len < 61 ) {
  201.       //for ( int i=0;i<30;i++) {
  202.       //  STR1[i+2] = Buffer2[i]; }
  203.        
  204.         STR1[0] = 0xA0; // fragmentation, 1010 0000, fragment bit, 2 fragments, fragment no. 0
  205.         STR1[1] = 0xff; // Reverse header          
  206.         STR1[2] = 0;     // null terminate string
  207.         strncat(STR1, Buffer2,30);
  208.        
  209.       //for ( int i=0;i<len-30;i++) {
  210.       //  STR2[i+2] = Buffer2[i+30]; }
  211.        
  212.         STR2[0] = 0xA1; // fragmentation, 1010 0001, fragment bit, 2 fragments, fragment no. 1
  213.         STR2[1] = 0xff; // Reverse header            
  214.         STR2[2] = 0;     // null terminate string, 32 bytes + 2 extra bytes
  215.         strcat(STR2, &Buffer2[30]);    // Copy the balance of pointer address 30 and above
  216.        
  217.    } else if ( len < 91 )  {  
  218.       //for ( int i=0;i<30;i++) {
  219.       //  STR1[i+2] = Buffer2[i]; }
  220.        
  221.         STR1[0] = 0xB0; // fragmentation, 1011 0000, fragment bit, 3 fragments, fragment no. 0
  222.         STR1[1] = 0xff; // Reverse header          
  223.         STR1[2] = 0;     // null terminate string  
  224.         strncat(STR1, Buffer2,30);    // Copy the 1st 30 bytes to STR1
  225.        
  226.       //for ( int i=0;i<30;i++) {
  227.       //  STR2[i+2] = Buffer2[i+30]; }  
  228.        
  229.         STR2[0] = 0xB1; // fragmentation, 1011 0001, fragment bit, 3 fragments, fragment no. 1
  230.         STR2[1] = 0xff; // Reverse header  
  231.         STR2[2] = 0;     // null terminate string
  232.         strncat(STR2, &Buffer2[30],30);  // Copy the next 30 bytes to STR2
  233.        
  234.       //for ( int i=0;i<len-60;i++) {
  235.       //  STR3[i+2] = Buffer2[i+60]; }
  236.        
  237.         STR3[0] = 0xB2; // fragmentation, 1011 0011, fragment bit, 3 fragments, fragment no. 2
  238.         STR3[1] = 0xff; // Reverse header        
  239.         STR3[2] = 0;     // null terminate string      
  240.         strcat(STR3, &Buffer2[60]);        
  241.        
  242.       } else {
  243.       // payload > 90 bytes, discard or add more fragments  
  244.    } // end if
  245.  
  246. /*
  247. Serial.print("\tSTR1:");
  248. Serial.println(STR1);
  249. Serial.print("\tSTR2:");
  250. Serial.println(STR2);
  251. Serial.print("\tSTR3:");
  252. Serial.println(STR3);
  253. */
  254. }  // end fragmentPackets
  255.  
  256.  
  257. void sendPackets(char TMP1[33], char TMP2[33], char TMP3[33]) {
  258.  
  259. //Serial.print("\tTMP1:");
  260. //Serial.println(TMP1);
  261. //Serial.print("\tTMP2:");
  262. //Serial.println(TMP2);
  263. //Serial.print("\tTMP3:");
  264. //Serial.println(TMP3);
  265.  
  266.   int status = (STR1[0] & B00110000)>>4;
  267.      
  268.   radio.stopListening();
  269.  
  270.   // Mask the 1st Byte, bits 5 & 6 and shift 4 places to right
  271.   // Return 0, 2 or 3 fragments
  272.  
  273.   switch (status) {
  274.     case 1:
  275.         if ( !radio.write(TMP1,strlen(TMP1) ) ) {
  276.           //Serial.println("\tNRF error TMP1, frag=0");
  277.          }
  278.         //delay(1);
  279.       break;
  280.     case 2:
  281.         if ( !radio.write(TMP1,strlen(TMP1) ) ) {
  282.             //Serial.println("\tNRF error TMP1, frag=1");
  283.          }
  284.         //delay(1);
  285.         if ( !radio.write(TMP2,strlen(TMP2) ) ) {
  286.            //Serial.println("\tNRF error TMP2, frag=1");
  287.          }    
  288.         //delay(1);    
  289.       break;
  290.     case 3:
  291.         if ( !radio.write(TMP1,strlen(TMP1) ) ) {
  292.             //Serial.println("\tNRF error TMP1, frag=2");
  293.          }
  294.         //delay(1);
  295.         if ( !radio.write(TMP2,strlen(TMP2) ) ) {
  296.             //Serial.println("\tNRF error TMP2, frag=2");  
  297.          }
  298.         //delay(1);
  299.         if ( !radio.write(TMP3,strlen(TMP3) ) ) {
  300.             //Serial.println("\tNRF error TMP3, frag=2");  
  301.          }
  302.         //delay(1);
  303.        break;
  304.     } // switch/case  end
  305.    
  306.     radio.startListening();
  307.  
  308. } // nrf_Send end
  309.  
  310.  
  311.  
  312. // Receive payload from nRF at remote end
  313.  
  314. void nRF_Receive(){
  315.  
  316.   uint8_t len=0, mergeA=0, mergeB=0, Head1 = 0;
  317.   // Call startlistening everytime here
  318.    
  319.   if ( radio.available() ) {
  320.     len = radio.getDynamicPayloadSize();
  321.     radio.read( &RXPayload, len );
  322.    
  323.     RXPayload[len] = 0;
  324.  
  325. //Serial.print("nRF RXPayload:");
  326. //Serial.print(RXPayload);  
  327. //Serial.print(" [");
  328. //Serial.print(len);
  329. //Serial.print("]");    
  330. Head1 = RXPayload[0] & 0xff;
  331. //Serial.print(" Head1:");
  332. //Serial.println(Head1,HEX);
  333.  
  334.     if ( Head1 == 0x00 ) {
  335.      // No fragment, strip off first 2 header bytes
  336.         STR1[0] = 0;
  337.         memcpy(&STR1,&RXPayload[2],len-2 );  
  338.         STR1[len-2]=0;
  339.        
  340.         sprintf(dataBuffer,"%s",STR1);
  341.     } else if ( Head1 == 0xA0 ) {
  342.      // Fragment packets, with 2 fragments
  343.         STR1[0] = 0;
  344.         memcpy(&STR1, &RXPayload[2],30);
  345.  
  346.         //for ( int i=0;i<30;i++ ) {
  347.         //  STR1[i] = RXPayload[i+2]; }
  348.         STR1[30]=0;
  349.         mergeA=0;
  350. //Serial.print("STR1:");
  351. //Serial.println(STR1);
  352.         sprintf(dataBuffer,"%s",STR1);
  353.    } else if ( Head1 == 0xA1 ) {
  354.      // Fragment packets, with 2 fragments
  355.         STR2[0] = 0;
  356.         memcpy(&STR2, &RXPayload[2],len-2 );
  357.  
  358.         STR2[len-2]=0;
  359. //Serial.print("STR2:");
  360. //Serial.println(STR2);        
  361.         mergeA=1;
  362.         sprintf(dataBuffer,"%s%s",dataBuffer,STR2);
  363.     } else if ( Head1 == 0xB0 ) {
  364.      // Fragment packets, with 3 fragments    
  365.          STR1[0] = 0;
  366.          memcpy(&STR1, &RXPayload[2],30);
  367.        
  368.          STR1[30]=0;
  369.          mergeB=0;  
  370. //Serial.print("STR1:");
  371. //Serial.println(STR1);
  372.  
  373.     } else if ( Head1 == 0xB1 ) {
  374.      // Fragment packets, with 3 fragments    
  375.         STR2[0] = 0;
  376.         memcpy(&STR2, &RXPayload[2],30);  
  377.  
  378.         STR2[30]=0;        
  379.         mergeB=0;
  380. //Serial.print("STR2:");
  381. //Serial.println(STR2);
  382.         sprintf(dataBuffer,"%s%s",STR1,STR2);
  383.  
  384.     } else if ( Head1 == 0xB2 ) {
  385.      // Fragment packets, with 3 fragments    
  386.          STR3[0] = 0;
  387.         memcpy(&STR3, &RXPayload[2],len-2 );  
  388.  
  389.         STR2[len-2]=0;        
  390.         mergeB=1;
  391. //Serial.print("STR3:");
  392. //Serial.println(STR3);
  393.         sprintf(dataBuffer,"%s%s",dataBuffer,STR3);
  394.  
  395.     } else {
  396.       // Invalid payload or error payloads
  397.       //Serial.println("Invalid Packets");
  398.       dataBuffer[0] = 0;
  399.     }  
  400. } // end radio.available if
  401.    
  402.        
  403.     // Print merge payload to Serial Monitor
  404.     if ( (dataBuffer[0] == '$') && ( mergeA || mergeB) ) {
  405. //Serial.print("nRF RECV     :");
  406.       Serial.println(dataBuffer);
  407. //Serial.print(" [");
  408. //Serial.print(strlen(dataBuffer));
  409. //Serial.println("]");
  410.     // Reset the merge
  411.     mergeA, mergeB = 0;
  412.     }
  413.    
  414. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement