NRF24L01 Funk Modul Problem mit eigener Funktion

Hallo,

ich wollte mit diesen Code ein Text versenden allerdings kommen am Empfänger nur Kästchen an

#include <SPI.h>
#include <nRF24L01.h>
#include <RF24.h>

RF24 radio(7, 8);

char empftext[32];
char haupt[6] = "00000";
char neben[6] = "00001";

void senden (const byte adresse[], char sendetext[32])
{
 radio.stopListening();
 radio.openWritingPipe(adresse);
 radio.write(&sendetext, sizeof(sendetext));
 Serial.print("Sende: ");
 Serial.println(sendetext);
}

String empfangen (const byte adresse[])
{
 radio.startListening();
 radio.openReadingPipe(0, adresse);;
 while (true)
 {
   if (radio.available())
   {
   radio.read(&empftext, sizeof(empftext));
   String wert = empftext;
   Serial.println(wert);
   return wert;
   break;
   }
 }
}

void setup() {
 // put your setup code here, to run once:
 Serial.begin(9600);
 
 radio.begin();
 radio.setPALevel(RF24_PA_MAX);
 radio.setChannel(0x77);
 radio.enableDynamicPayloads();
 radio.powerUp();
 radio.setRetries(15, 15);
}

void loop() {
 // put your main code here, to run repeatedly:
 senden(neben, "Hallo");
 delay(1000);
}

sketch_oct20c.ino (1016 Bytes)

Setze Deinen Sketch bitte in Codetags (</>-Button oben links im Forumseditor oder [code] davor und [/code] dahinter ohne *). Das kannst Du auch noch nachträglich tun.

Dann ist er besser lesbar und wird nicht verstümmelt.

Gruß Tommy

Danke das war mein erster Eintrag

Zum Problem Funk wissen andere mehr aber Dein break nach return in empfangen wird nie ausgeführt.

Gruß Tommy

Und wieso wird der break Befehl nicht ausgeführt?

Was meinst Du, war return macht? Es verläßt sofort die Funktion.

Gruß Tommy

Achso dann lass ich break weg

Ja, kannst Du.

Gruß Tommy

Gruslig.

delay und while (true) haben in einem Programm mit Funkkommunikation nichts zu suchen,
String sollte auf Arduinos vermieden werden.

Die Rückgabe von lokalen Variablen ist zumindestens bedenklich.

sizeof() funktioniert nicht auf übergebenen Arrays, die Adresse eines Zeigers ist etwas anderes als der
Datenbereich auf den erzeigt.

void setup() {
  byte data[32] = "egal was hier steht";
  Serial.begin(250000);
  testen(data);
}
void testen(char sendetext[32]) {
  Serial.print(F("sizeof(sendetext) = "));
  Serial.println(sizeof(sendetext));
  Serial.print(F("der Text nach deiner Methode = '"));
  Serial.print((char*)&sendetext);
  Serial.println("'");
}
void loop() {}
sizeof(sendetext) = 2
der Text nach deiner Methode = '⸮!'

Diese Antwort könnte ich auch an viele andere Postings hängen.

Leute lernt erst mal C und / oder C++ auf einem normalen PC.
Der Einfachheit halber auf der Kommandozeile so das man sich nicht mit der GUI-Programmierung
rum schlagen muss.

Compiler gibt es für lau. Linux sowieso GCC. (Das ist auch der Compiler den die ArduinoIDE nimmt).
Für Windows gibt es den auch. Oder für Windows auc MinGW.
Auch das Microsoft Visualstudio gibt es glaube ich als "lau" Version.

Aber ohne jegliche Programmierkenntnisse auf Mikrocontroller los zu stürmen und in einem
Aufwasch auch noch Hardware verstehen, das ist letztendlich zu viel auf einmal.
So viel kann man gar nicht erklären.

Ulli

Ach ja, noch eine Bemerkung:

wenn man eine selbstgestrickte Kommunikation hat, die Probleme bereitet,
sollte man beide (bzw. alle) Sketche posten, inclusive der erzeugten Ausgaben.

All das natürlich in Code-Tags. :wink:

Wie soll ich das den mit den sizeof() lösen, weil weglassen kann ich es nicht.

Hier sind noch mal meine Codes:

Sender

#include <SPI.h>
#include <nRF24L01.h>
#include <RF24.h>

RF24 radio(7, 8);

char empftext[32];
int start;
const byte haupt[6] = "00000";
const byte neben[6] = "00001";

void senden (const byte adresse[], char sendetext[32])
{
  radio.stopListening();
  radio.openWritingPipe(adresse);
  radio.write(&sendetext, sizeof(sendetext));
  Serial.print("Sende: ");
  Serial.println(sendetext);
}

char empfangen (const byte adresse[], int laenge)
{
  radio.startListening();
  radio.openReadingPipe(0, adresse);
  start = millis();
  while (millis() - start < laenge * 1000)
  {
    if (radio.available())
    {
    radio.read(&empftext, sizeof(empftext));
    Serial.print("Empfangen: ");
    Serial.print(" char: ");
    Serial.println(empftext);
    return empftext;
    }
  }
}

void setup() {
  // put your setup code here, to run once:
  Serial.begin(9600);
  
  radio.begin();
  radio.setPALevel(RF24_PA_MAX);
  radio.setChannel(0x77);
  radio.setDataRate(RF24_250KBPS);
  radio.enableDynamicPayloads();
  radio.powerUp();
  radio.setRetries(15, 15);
}

void loop() {
  // put your main code here, to run repeatedly:
  senden(neben, "Hallo");
  delay(1000);
}

Empfänger

#include <SPI.h>
#include <nRF24L01.h>
#include <RF24.h>

RF24 radio(9, 10);

char empftext[32];
int start;
const byte haupt[6] = "00000";
const byte neben[6] = "00001";

void senden (const byte adresse[], char sendetext[32])
{
  radio.stopListening();
  radio.openWritingPipe(adresse);
  radio.write(&sendetext, sizeof(sendetext));
  Serial.print("Sende: ");
  Serial.println(sendetext);
}

char empfangen (const byte adresse[], int laenge)
{
  radio.startListening();
  radio.openReadingPipe(0, adresse);
  start = millis();
  while (millis() - start < laenge * 1000)
  {
    if (radio.available())
    {
    radio.read(&empftext, sizeof(empftext));
    Serial.print("Empfangen: ");
    Serial.print(" char: ");
    Serial.println(empftext);
    return empftext;
    }
  }
}

void setup() {
  // put your setup code here, to run once:
  Serial.begin(9600);
  
  radio.begin();
  radio.setPALevel(RF24_PA_MAX);
  radio.setChannel(0x77);
  radio.setDataRate(RF24_250KBPS);
  radio.enableDynamicPayloads();
  radio.powerUp();
  radio.setRetries(15, 15);
}

void loop() {
  // put your main code here, to run repeatedly:
  Serial.print("Versuch: ");
  empfangen(neben, 4);
}

The_Snapdragon:
Wie soll ich das den mit den sizeof() lösen, weil weglassen kann ich es nicht.

Sowie es auch in C gelöst wird. Und in der Arduino API. Wieso meinst du weshalb man bei vielen Funktionen extra die Größe übergeben muss?

Man kann Arrays auch als Referenzen übergeben. Dann geht sizeof(). Aber dann kann man nur Arrays dieser Größe übergeben. Das ist daher nicht sinnvoll wenn der Code allgemein sein muss

delay und while (true) haben in einem Programm mit Funkkommunikation nichts zu suchen,

Hier finde ich die Absolutheit der Aussage bedenklich, bis falsch.

Als Leitlinie, ok.
Als Dogma, nicht ok.

Man kann Arrays auch als Referenzen übergeben. Dann geht sizeof(). Aber dann kann man nur Arrays dieser Größe übergeben. Das ist daher nicht sinnvoll wenn der Code allgemein sein muss

Alternativ:
1 auto
2 template

Naja…
Hat auch so seine Tücken.

char sendetextA[32] = "testA";
char sendetextB[12] = "testB";

template<typename T> void senden(T &sendetext)
{
 Serial.println(sizeof(sendetext));  
}


void setup() 
{
  Serial.begin(9600);      
  Serial.println("Start");
  senden(sendetextA);
  senden(sendetextB);
}

void loop() 
{

}

Der grundlegende "Fehler" ist hier:

void senden (const byte adresse[], char sendetext[32])

Das ist kein richtiger Fehler. Daher die Anführungszeichen. Aber es suggeriert, dass da die Größe übergeben wird. Letztlich ist aber auch nur ein Zeiger. Die Größe hat hier nur eine Kommentar-Funktion für den Anwender. Dem Compiler ist das egal.

Vernünftig übergibt man Arrays daher gleich als Zeiger:

void senden (const byte* adresse, char* sendetext)

Dann ist auch sofort klar dass sizeof() hier nur die Größe des Zeigers zurückliefert. Und auf einem 8-Bit Prozessor sind das 16 Bit = 2 Byte

Wenn ich das mit den Zeigern versuche kommt bei mir folgende Fehlermeldung

cannot convert 'const byte* {aka const unsigned char*}' to 'const byte** {aka const unsigned char**}' for argument '1' to 'void senden(const byte**, char**)'

Wenn ich das mit den Zeigern versuche kommt bei mir folgende Fehlermeldung

cannot convert 'const byte* {aka const unsigned char*}' to 'const byte** {aka const unsigned char**}' for argument '1' to 'void senden(const byte**, char**)'

Mein Code

#include <SPI.h>
#include <nRF24L01.h>
#include <RF24.h>

RF24 radio(7, 8);

char empftext[32];
int start;
const byte haupt[6] = "00000";
const byte neben[6] = "00001";

void senden (const byte* adresse[], char* sendetext[32])
{
  radio.stopListening();
  radio.openWritingPipe(adresse);
  radio.write(&sendetext, sizeof(sendetext));
  Serial.print("Sende: ");
  //Serial.println(sendetext);
}

char empfangen (const byte adresse[], int laenge)
{
  radio.startListening();
  radio.openReadingPipe(0, adresse);
  start = millis();
  while (millis() - start < laenge * 1000)
  {
    if (radio.available())
    {
    radio.read(&empftext, sizeof(empftext));
    Serial.print("Empfangen: ");
    Serial.print(" char: ");
    Serial.println(empftext);
    return empftext;
    }
  }
}

void setup() {
  // put your setup code here, to run once:
  Serial.begin(9600);
  
  radio.begin();
  radio.setPALevel(RF24_PA_MAX);
  radio.setChannel(0x77);
  radio.setDataRate(RF24_250KBPS);
  radio.enableDynamicPayloads();
  radio.powerUp();
  radio.setRetries(15, 15);
}

void loop() {
  senden(neben, "Hallo");
  delay(1000);
}

So ist es ja auch falsch. Das ist ein Zeiger auf Arrays. Also ein Zeiger auf Zeiger (**). Genau was die Fehlermeldung anmeckert

Korrekt:

void senden (const byte* adresse, char* sendetext, byte laenge)

Arrays zerfallen bei der Übergabe zu Zeigern auf das erste Element. Lasse die eckigen Klammern weg wenn du Arrays als Funktionsparameter hast. Das verwirrt dich nur und verschleiert genau diesen Zusammenhang. Siehe auch wieder die Fehlermeldung. Egal wie du das schreibst, der Compiler betrachtet Arrays als Zeiger

Und dann eben den zusätzlichen Parameter laenge verwenden. Dann kannst du sizeof() beim Aufruf der Funktion machen um diese zu übergeben

Eventuell einfach strlen statt sizeof ?

Ulli

Kommt darauf an ob man den Null-Terminator übertragen möchte oder nicht.