HELP! Simple Send and Receive and No ACK [SOLVED]

Started by K1JOS, June 18, 2014, 11:17:08 PM

K1JOS

I have trimmed down the struct_receive and struct_send to a minimum but cannot get receive to work.

On the Send side, I have the Moteino wait for a serial input and then it sends (with retry) the defined payload but it doesn't get any ACK.  On the Receive side, I monitor and it never seems to receive anything.  Can someone help me spot what I am doing wrong?

Send code:
#include <RFM69.h>
#include <SPI.h>
#include <SPIFlash.h>

#define NODEID      1
#define NETWORKID   100
#define GATEWAYID   1
#define FREQUENCY   RF69_433MHZ //Match this with the version of your Moteino! (others: RF69_433MHZ, RF69_868MHZ)
#define SERIAL_BAUD 115200
#define ACK_TIME    30  // # of ms to wait for an ack

boolean requestACK = false;
SPIFlash flash(8, 0xEF30); //EF40 for 16mbit windbond chip
RFM69 radio;

typedef struct {		
  int ControlCode;
  int compass;
} Payload;
Payload theData;

int MAcompass;
int Code;

void setup() {
  Serial.begin(SERIAL_BAUD);
  radio.initialize(FREQUENCY,NODEID,NETWORKID);
  radio.setHighPower(); //uncomment only for RFM69HW!
   
  if (flash.initialize())
    Serial.println("SPI Flash Init OK!");
  else
    Serial.println("SPI Flash Init FAIL! (is chip present?)");
}

void loop() {
  //INTEGER WILL BE ENTERED VIA SERIAL MONITOR
  
  if (Serial.available() > 0)
  {
    // SEND SOMETHING FOR DEBUGGING ON THE REMOTE MOTEINO
    // TYPE IN INTEGER IN SERIAL MONITOR PLUS CR
    theData.ControlCode = 999;
    theData.compass = 360;
    
    if (radio.sendWithRetry(GATEWAYID, (const void*)(&theData), sizeof(theData)))
      Serial.print(" ok!");
    else Serial.print(" nothing...");
     Serial.println();
    // CLEAR SERIAL BUFFER
    while (Serial.available() > 0){
      byte discard = Serial.read();
    }
  }
}


The receive code:

#include <RFM69.h>
#include <SPI.h>
#include <SPIFlash.h>

#define NODEID      99
#define NETWORKID   100
#define GATEWAYID   1
#define FREQUENCY   RF69_433MHZ //Match this with the version of your Moteino! (others: RF69_433MHZ, RF69_868MHZ)
#define LED         9
#define SERIAL_BAUD 115200
#define ACK_TIME    30  // # of ms to wait for an ack

boolean requestACK = false;
SPIFlash flash(8, 0xEF30); //EF40 for 16mbit windbond chip
RFM69 radio;

typedef struct {		
  int ControlCode;
  int compass;
} Payload;
Payload theData;

void setup() {
  Serial.begin(SERIAL_BAUD);
  radio.initialize(FREQUENCY,NODEID,NETWORKID);
  radio.setHighPower(); //uncomment only for RFM69HW!
    
  if (flash.initialize())
    Serial.println("SPI Flash Init OK!");
  else
    Serial.println("SPI Flash Init FAIL! (is chip present?)");
}

void loop() {
  //REMOTE WILL NOT PROCESS ANY LOCAL SERIAL INPUT EXCEPT FOR DEGBUGGING
   
  if (radio.receiveDone())
  {
    if (radio.DATALEN != sizeof(Payload))
      Serial.print("Invalid payload received, not matching Payload struct!");
    else
      {
        theData = *(Payload*)radio.DATA; //assume radio.DATA actually contains our struct and not something else
        if (radio.ACK_REQUESTED)
          {
            radio.sendACK();
            Serial.print(" - ACK sent");
            delay(10);
          }
      }  
  }

}

luisr320

#1
Been there, done that. :)

Looks like you are trying to send data from the sender moteino to itself.

On the sender moteino you are defining its node ID as "1" and the GATEWAY ID also as "1". So when you use " if (radio.sendWithRetry(GATEWAYID, (const void*)(&theData), sizeof(theData)))" on a node that has the same ID as the GATEWAY, you are in fact trying to send a data packet to the sender.

Try to set the node ID on the sending moteino to 99 (or some other number except 1) and on the receiving moteino define the node ID to 1 (the number you have assigned to the GATEWAY on both moteinos).

___________________________


It also looks like you are trying to set the radio as " radio.setHighPower(); //uncomment only for RFM69HW!" and not using the "#define IS_RFM69HW    //uncomment only for RFM69HW! Leave out if you have RFM69W!" in the define section, after the include statements.

If you have the RFM69HW radio, you have to include both statements on your sketch. If the receiving Moteino is also a RFM69HW, do it to its corresponding sketch too.

Just check the examples "node" (https://github.com/LowPowerLab/RFM69/blob/master/Examples/Node/Node.ino) and "gateway" (https://github.com/LowPowerLab/RFM69/blob/master/Examples/Gateway/Gateway.ino) sketches.

___________________________


K1JOS

Thanks for the advice.  I thought all Moteino's in a system should use the same Gateway number and only the Node numbers had to be different.  You make it sound like there can only be one receiver (Node 1) and all the rest are senders.  In my project I need to have each have equal status being able to send and receive (when instructed). 

I have my Gateway, NodeId set up exactly like the examples so I am really confused.  Is there any documentation that explains this?

Many thanks in advance

K1JOS

OK !!!  I see that in all the examples the receiver or Gateway code does not have any declaration for a Gateway number.  Only the sender or Node has a declaration for Gateway. 

If I want both my Moteinos to EACH being able to send and receive.

I want the Moteino"1" to send user selected (by momentary switches) special control codes to Moteino"2" instructing to turn on some motor relays.  Then I want Moteino"2" (which has a magentometer sensor) in response to the control codes received to send  sensor data back to Moteino"1" for further processing.

How do I use Gateway?  Does each have to have a unique Gateway number as well as a unique NodeID?

Maybe I should make this a new post.


luisr320

The idea is that all nodes have a different number. The one you decide to use as a gateway also needs a node number. You only call it a "GATEWAY" for convenience. All moteinos can act as senders or receivers. All you have to do is to give them a common NETWORKID, like you did by setting the #define NETWORKID 100 in both sender and receiver.

But each moteino requires a different NODEID. When you send a data packet, it will always automatically includes in that data package the sender NODEID number, and you choose the destination NODEID here: radio.sendWithRetry(GATEWAYID, (const void*)(&theData), sizeof(theData)). If instead you wanted to send the data package to node 2, for instance, you would write: if (radio.sendWithRetry(2, (const void*)(&theData), sizeof(theData)).

You can have in the same sketch a routine to be used as a receiver and as a sender. You could even have them relay a data package that is not intended for that node.

Don't be fooled by the GATEWAY designation. They all can be nodes, gateways and both.
All you have to do is assign a unique NODEID to each and the same NETWORKID to all of them.


K1JOS

Ahhh... so radio.sendWithRetry(GATEWAYID, (const void*)(&theData), sizeof(theData))

here GATEWAYID is the nodeid where I want it sent to?  OK I got that.  Let me see how that works in my code.

many thanks

luisr320

You can check out my RFID project. It does exactly what you want to do. In my project a Moteino is connected to a rfid module and when a tag is approached from the antenna it will send the tag Id to a GATEWAY Moteino that will decide if the tag ID is on a approved list and then sends a command back to the Node to open the door.

luisr320

Quote from: K1JOS on June 19, 2014, 10:06:52 AM
Ahhh... so radio.sendWithRetry(GATEWAYID, (const void*)(&theData), sizeof(theData))

here GATEWAYID is the nodeid where I want it sent to?  OK I got that.  Let me see how that works in my code.

many thanks

Yes, that's it. You call them names just for convenience. You could just use numbers.

K1JOS

Many thanks, it now works fine and I understand why !

best
jerry