-         

Seite 1 von 2 12 LetzteLetzte
Ergebnis 1 bis 10 von 11

Thema: UART empfangen

  1. #1
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    10.03.2005
    Alter
    28
    Beiträge
    967

    UART empfangen

    Anzeige

    Hi,

    ich will ganze Strings empfangen können. Auf der Suche bin ich dann auf den Befehl "Input" gestoßen. Wie funktioniert dieser Befehl? So wie ich das aus dem Beispieldateien von Bascom rauslese, wartet dieser Befehl immer, bis ein Sting empfangen wurde. Also wenn nix kommt, geht im Programm auch nicht weiter? Oder muss ich den Befehl immer wieder abfragen, also so ne Art Pollen. Aber dann gehn mit ja unter Umständen Daten verloren...was nicht so schön wäre. Das beste wärs natürlich, wenn der Befehl Interrupt gesteuert wäre...aber ich glaube nicht, dass das der Fall ist...oder doch? Könnt ihr mir dann noch einen alternativen Befehl nennen, der Interrupt gesteuert ist? (nach Möglichkeit, wo man gleich ganze Strings empfangen kann. Nicht alle Zeichen einzeln empfangen und dann zu einem String zusammen zu fügen. Das mach ich dann, wenns sonst überhaupt keine Alternative mehr gibt.)

    Gruss Hacker
    Ich würde ja gern die Welt verändern..., doch Gott gibt mir den Quellcode nicht!

  2. #2
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    02.08.2004
    Ort
    Stuttgart
    Alter
    42
    Beiträge
    849
    Servus!

    Input blockt dir den Programmfluss, ist also nicht gut. Mußt das über den UART machen, die Register und Funktinen findest du im betreffenden Datenblatt des AVR's. Interrupts sind hardwaregrundlage im AVR, also löst das eintreffen eines neuen Bytes einen Int aus den du nutzen kannst, aber eben immer nur ein Byte und alles von 0 bis 255!

    Grüße Wolfgang

  3. #3
    Erfahrener Benutzer Roboter Experte Avatar von Rage_Empire
    Registriert seit
    10.03.2005
    Ort
    Pforzheim
    Beiträge
    710
    Schau mal in der Hilfe nach:
    Input
    Waitkey
    Inkey

  4. #4
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    11.04.2005
    Beiträge
    1.469
    Noch ein netter Befehl: "Timeout"
    Wenn der controller auf Daten per Input wartet, aber keine kriegt, dann bleibt er normalerweise stur in der Input Routine stecken.
    Mit Timeout kann man festlegen, wann der Input Befehl übersprungen wird, falls keine Daten kommen.
    Hab's nur gelesen, aber noch nicht ausprobiert.

    Gruß
    Christopher

  5. #5
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    10.03.2005
    Alter
    28
    Beiträge
    967
    Ich muss jetzt leider weg und kann das nicht alles ausprobieren. Danke schonmal für eure Antworten. Wahrscheinlich wirds dann doch drauf rauslaufe, dass ich die einzelnen Bytes zusammen fügen muss.

    Gruss Hacker
    Ich würde ja gern die Welt verändern..., doch Gott gibt mir den Quellcode nicht!

  6. #6
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    02.08.2004
    Ort
    Stuttgart
    Alter
    42
    Beiträge
    849
    Servus Hacker!

    Machs besser Byte für Byte von Hand, dann kannst das neue Byte im UART-Int-Vektor abholen und in ein Byte-Array schreiben nacheinander wie es kommt und dann meinetwegen zu einem String zusammenbauen aus der Folge der ASCII-Zeichen mit einer Wandlung von Byte-Wert in Zeichen das es für einen String passt.

    Kannst dir so deine Bytes ecoen lassen:

    Do
    TmpByte = Waitkey()
    Print Chr(TmpByte);
    Loop

    Oder diekt (ASCII-Code):

    Do
    TmpByte = Waitkey()
    Print TmpByte;
    Loop

    Grüße Wolfgang

  7. #7
    Erfahrener Benutzer Fleißiges Mitglied
    Registriert seit
    09.11.2004
    Ort
    Hard, Vorarlberg
    Beiträge
    155
    Eine Möglichkeit ist den String im Hintergrund zu empfangen und INPUT nur dann aufzurufen, wenn das Zeilenende-Zeichen (&H0D) empfangen wurde.
    Für den Hintergrundempfang gibt es bei BASCOM-AVR den Befehl SERIALIN (Schau dazu in der Hilfe nach). Da gibt es neues Feature, welches eine Anwenderroutine aufruft, wenn ein bestimmtes Zeichen (z.B. Zeilenende) empfangen wurde.

    Code:
    Config Serialin = Buffered , Size = 80 , ByteMatch = 13
    Dim CR_Received as Byte
    Diese Zeile legt einen Buffer von 80 Zeichen an, bindet die ISR-Routine ein, welche die Zeichen im Hintergrund empfängt und ruft Serial0CharMatch auf, wenn das Zeichen mit den ASCII-Code 13 (=Carriage Return/Zeilenende) empfangen wurde.
    Nach dem Label Serial0CharMatch kann der Anwender einen Programmteil implementieren und mit RETURN abschließen, welcher die gewünschte Aktion beim Empfang des bestimmten Zeichens ausführt.
    Da dieses aber in der Interruptroutine ausgeführt wird, sollte hier nur ein Flag (Byte CR_Reiceived ist 0 oder 1) gesetzt werden, welches dann in der Anwendung selbst abgefragt wird.

    Code:
    Serial0CharMatch:
    CR_Received = 1
    return
    Zu beachten ist, dass in dieser Interrupt-Routine nur die Register r0, r16, r24, r25, r26 und r27 gerettet sind. Daher können in diesem Programmteil entweder nur diese Register verwendet werden oder die entsprechenden Register müssen zusätzlich mit PUSH/POP gerettet werden. Da diese Wertzuweisung CR_Received = 1 aber nur r24 verwendet, muss hier nichts weiter unternommen werden.


    Im Hauptprogramm kann wie in folgendem Code-Teil angeführt auf die Eingabe einer kompletten Zeile reagiert werden:

    Code:
    ' Hauptschleife
    DO                       
    
    ' anderer Programmcode
    '------------------------------------------------------------------
    Disable Interrupts 
    If Cr_received = 1 Then 
       Cr_received = 0 ' ISR-Flag zurücksetzen
       Enable Interrupts 
       Input EmpfangsString 
       ' Nun kann der String weiterbehandelt werden
    Else
       Enable Interrupts ' Keine Zeilenende, Interrupt wieder einschalten
    End If 
    '------------------------------------------------------------------
    
    ' anderer Programmcode
    
    LOOP
    
    End

    Damit die Interrupt-Routine und das Hauptprogramm nicht gleichzeitig das Flag CR_Received ändern, wird hier während der Abfrage und Änderung der Interrupt gesperrt.

    Noch eine Bemerkung:
    Der in Serialin definierte Empfangsbuffer muss natürlich die Länge der längsten Eingabezeile (plus einige Reservebytes) haben.
    Viele Grüße
    Josef
    -------------------------------------------------------------------------------------
    DOS-File System für BASCOM-AVR auf http://members.aon.at/voegel

  8. #8
    Erfahrener Benutzer Roboter-Spezialist
    Registriert seit
    11.11.2005
    Beiträge
    321
    verbinde rtx mit int0 unf benutze den int0 ausgaberoutine..


    Castle

  9. #9
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    02.08.2004
    Ort
    Stuttgart
    Alter
    42
    Beiträge
    849
    Servus Castle!

    Wozu soll das gut sein den RXD mit INT0 zu verbinden? Bei jedem Bitwechsel in den seriellen Daten triggert dir da nur der INT0 und springt in den INT0-Vektor. Wozu gibts denn extra den UART-Int-Vektor? Der triggert wenn wirklich Daten sicher da sind und ist extra dafür vorgesehen worden. Der INT0 ist eine reine Performance-Vernichtung und übel umständlich.

    Grüße Wolfgang

  10. #10
    Erfahrener Benutzer Roboter-Spezialist
    Registriert seit
    11.11.2005
    Beiträge
    321
    Einfach für den Anfänger...

    Int0 Falling
    Enable Int0
    Enable Interrupts

    Do
    Print "was sonst noch läuft..." ' zum PC
    WaitMs 255
    Loop

    End

    Interrupt Int0(), Save 2
    Disable Int0
    Input serielle_vom_pc
    Cls
    Lcd serielle_vom_pc ' ausgabe auf LCD
    Reset Int0
    Enable Int0
    End Interrupt

Seite 1 von 2 12 LetzteLetzte

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •