Brauche bitte Hilfe bei initialisieren der seriellen Schnittstelle

Hallo,

ich moechte gerne die serielle Schnittstelle zur Ausgabe von debug messages in einer Funktion initialisieren.

Hier meine Funktion:

static HardwareSerial *serial_port;
void logger_init(unsigned long baud_rate, HardwareSerial& serialPort) {
    
    serial_port = &serialPort;
       
    serial_port->begin(baud_rate);
}

Main.ino

setup(){
logger_init(115200, Serial);
Serial.println("d");
}

loop(){}

allerdings stuerzt mein esp32 dabei ab wenn ich dies so mache.

Wo ist mein Fehler?

Du rufst zweimal Serial.begin(115200) auf.

Und die Funktionsdefinitionen sind falsch.

Ausserdem sollten void setup() { } und void loop() {}
in einer Datei mit der Extension .ino stehen

Dass file_path zum Glück nur ein unbenutzter Parameter ist, ergibt nur eine Warnung.

Hallo,
sorry war mein Fehler beim Kopieren....

Habe es richtig angepasst nun...

Trotzdem läuft es nicht, aber warum?

Welche Funktionen meinst du sind falsch?

Warum nimmst du nicht einfach Serial.XXX ? Das Konstrukt, das du da hast, beißt sich, auch wenn's kompiliert. Schau dir im Code die Definition von Serial an.

Serial kann nur als pointer übergeben werden, habe es gerade nachgelesen und ich hab's falsch rum gemacht :stuck_out_tongue_winking_eye:

Es kann auch als Referenz übergeben werden.

Gruß Tommy

Ich bekomme einen Haufen Fehler, angefangen mit
sketch.ino:1:9: error: expected constructor, destructor, or type conversion before ';' token
setup() {

wenn vor
setup() { ... }
bzw.
loop() { ... }
der Returnwert-Datentyp void fehlt

Warum ist das static?

Wofür überhaupt der Pointer?

Scheint mir völlig Unsinnig!

Zeige bitte testbaren minimal Code, welcher den Fehler zeigt und keinen untestbaren fantasie Code.

KA, dein Programm ist untestbar

Nein!

So läufts:

HardwareSerial * s;
void logger_init(HardwareSerial& _s, unsigned long baud) {
  s = &_s;
  s->begin(baud);
}
size_t log(const char* msg) {return s->println(msg);}

void setup() {
  logger_init(Serial, 115200);
}

void loop() {
  static unsigned long lastlog;
  static char test[] = " Log 0";
  char* const tp = test+strlen(test)-1;
  if (millis() - lastlog >= 1000) {
    lastlog += 1000;
    log ( test );
    (*tp)++;
    if (*tp > 'z') *tp = '0';
  }
}

Wenn Serial erst in logger_init an eine globale/statische Variable übergeben wird, kann diese leider keine Referenz sein.

Mal abgesehen davon, dass ich das für Mist halte, hatte ich @combie s "Nein" gern mit einem Gegenbeispiel vorgeführt gesehen.

Erstmal halte ich es für falsch, dass der Logger die Baudrate setzen soll!
Das ist ein logischer Fehler. (meiner Ansicht nach)

Warum der Logger nur HardwareSerial können soll, ist mir auch ein Rätsel!
Software Serial kann doch auch, oder eine Datei, als Logziel.
Warum nicht?


void log(Print &print, char * message)
{
   // print.print(millis());
   print.println(message);
}

Das funktioniert mit allen Arduino Streams, also alles Seriellen Schnittstellen, auch Wire, Dateien. Also mit allem, wo Print implementiert wird.

Da stimme ich dir völlig zu. Wenn das die Erläuterung zu "Nein" ist, verstanden.

Ich hatte "Nein" auf das "Referenz statt Pointer" - Detail des vermurksten Ansatzes bezogen.

Warum sollte man das tun?

OOP:
Man kann doch jederzeit Logger Instanzen erzeugen!
Mit beliebigen Zielen.
Ich sehe keine Notwendigkeit für so eine " globale/statische Pointer Variable".

Innerhalb einer solchen Instanz kann das Logziel natürlich eine Referenz sein.

Wenn du dein Ziel beschreibst, das du erreichen möchtest, kann man dir wahrscheinlich besser helfen.

Was soll es am Ende werden?

Z.B. könntest du das API beschreiben wie es aussehen soll (wie du es bedienen willst).

Im void setup() machst du zB folgenden Code rein. Damit initialisierst du es quasi.

void setup(){
   Serial.begin(9600); // oder andere baudrate
}

Im loop oder wo auch immer du dann die Serial Connection verwenden willst kannst du zB folgendes machen. Wichtig ist das Serial.available(). Meines Wissens musst du eine Verbindung zu irgendwas haben weil du sonst nix senden oder empfangen kannst.

void loop() {
  // Siehe post #15
  if (Serial.available() > 0) {
      String datenEmpfangen = Serial.readString(); // Beispiel zum Lesen
      Serial.print("Working"); // Beispiel zum Senden
  }
}

In meinem Fall hab ich meinen Arduino mit dem PC via USB verbunden und mittels des Seriellen Monitors in Arduino IDE (Ctrl + Shift + M) kann ich so Daten zum Arduino senden und Empfangen.

Der Kommentar ist falsch. Hier wird nicht das Vorhandensein der Verbindung geprüft, sondern ob in der Schnittstelle Daten zum Lesen bereit stehen.

Gruß Tommy

Zudem reicht:
if (Serial.available()) {
Denn alles von Null verschiedene wird als true gewertet

Wenn man die Verbindung prüfen will:
if (Serial) {
Was aber nur auf µC mit nativen USB, z.B. Leonardo Sinn macht.
Der z.B. UNO merkt nix von aktiven USB Verbindungen.

available heißt literally "verfügbar" lol melds beim creator mit nem github issue :person_shrugging: mir gehts in erster linie zu helfen nicht um klugzuscheißern und im endeffekt macht es ja was es soll

vor allem ist es im endeffekt eh das gleiche nur mit anderen worten :slight_smile:

Könnte man vereinfachen stimmt, rauskommen tut ja sowieso das gleiche :person_shrugging: denk das is eher was fürs Thema Programmierstil

Och...
Nee, die beiden Abfragen sind unterschiedlich.

available heißt literally "verfügbar"

Daten verfügbar!
Nicht Verbindung verfügbar.

Leider ist diese Aussage zu 100% falsch.