Also ich verwende 2 Hardware Uarts. Es ist so das der µC als Buskoppler fungieren soll. d.h. er ist Master und Slave zugleich. UART1 ist die Schnittstelle zum Hauptbus und die UART0 ist die Schnittstelle zum "Kartenbus". Dort sollen bis zu 6 weitere µC angeschlossen werden die dann Zyklisch abgefragt werden. deren Daten sollen dann auf Anfrage vom Hauptbus abgeholt werden können. Ich hoffe ihr versteht was ich meine.

So wie das Program im Moment ist funktioniert es auch. Aber zu langsam. Ich Suche einen Weg wie man es schneller machen kann. Schaut es euch mal an, vielleicht habt ihr eine Idee. Aktuelle Version ist ohne Interrupts mit Zyklischer Bufferabfrage, da es mit Interrupts ja nicht funktioniert hat. Ich hoffe ihr könnt mir helfen.

Code:
'--------------------------------------------------------------
'    S-Bus-Koppler
'
'--------------------------------------------------------------
$regfile = "m162def.dat"                                    ' specify the used micro
$crystal = 8000000                                          ' used crystal frequency
' use baud rate (Rackbus)
$baud = 38400
' baud rate for second serial port (Hauptbus)
$baud1 = 38400

$hwstack = 42                                               ' default use 32 for the hardware stack
$swstack = 40                                               ' default use 10 for the SW stack
$framesize = 40                                             ' default use 40 for the frame space
' Lib für die automatische Sende- Empfangsumschaltung
$lib "modbus.lbx"

' Com1 (Rackbus) Schnitstelle auf 9 Bit Modus konfigurieren
Config Com1 = Dummy , Synchrone = 0 , Parity = None , Stopbits = 1 , Databits = 9 , Clockpol = 0
' Com2 (Hauptbus) Schnitstelle auf 9 Bit Modus konfigurieren
Config Com2 = Dummy , Synchrone = 0 , Parity = None , Stopbits = 1 , Databits = 9 , Clockpol = 0


' use OPEN/CLOSE for using the second UART
Open "COM2:" For Binary As #1


Echo Off


Enable Interrupts

' MPCM (MULTI PROCESSOR COMMUNICATION MODE) auf Hauptbus einschalten
Ucsr1a.mpcm = 1


' PORTS DEKLARIEREN

Rs485dir Alias Portd.2
Config Rs485dir = Output
Rs485dir = 0                                                'Auf Empfangsmodus schalten
' Pin für die Sende-Empfangsumschaltung UART
Config Print = Portd.2 , Mode = Set


Rs485dir1 Alias Portb.1
Config Rs485dir1 = Output
Rs485dir1 = 0                                               'Auf Empfangsmodus schalten
' Pin für die Sende-Empfangsumschaltung UART1
Config Print1 = Portb.1 , Mode = Set


Declare Function Checksumme_berechnen(byref Datenbereich As Byte) As Byte


' Empfangspuffer UART
Config Serialin = Buffered , Size = 150
' Sendepuffer UART
Config Serialout = Buffered , Size = 150
' Empfangspuffer UART1
Config Serialin1 = Buffered , Size = 150
' Sendepuffer UART1
Config Serialout1 = Buffered , Size = 150


' TIMER


' Watchdog Timer / LED
Config Timer1 = Timer , Prescale = 256                      ' Timer konfigurieren
On Timer1 Timerroutine1                                     ' Timerinterrupt Subroutine zuweisen
Enable Timer1                                               ' Timer aktivieren
Stop Timer1                                                 ' Timer stoppen
Timer1 = 34286                                              ' Timer auf neuen Startwert einstellen (1s)


' Timeout Timer
Config Timer3 = Timer , Prescale = 256                      ' Timer konfigurieren
On Timer3 Timerroutine3                                     ' Timerinterrupt Subroutine zuweisen
Enable Timer3                                               ' Timer aktivieren
Stop Timer3



' VARIABLENDEKLARATION

 Dim Koppleradresse As Byte

 Dim Empfangeneadresse As Byte

 Dim Kopplerstatusbyte As Byte

 Dim Kopplersteuerbyte As Byte

 Dim Kartenadresse As Byte
 Kartenadresse = 255                                        ' Startwert

 Dim Anzahl_karten As Byte

 Dim Aktuelle_karte As Byte
 Aktuelle_karte = 1

 Dim Folge_karte As Byte


 ' Teilnehmer Speicherbereiche
 Dim An_k1 As Word
 Dim Von_k1 As Word

 Dim An_k2 As Word
 Dim Von_k2 As Word

 Dim An_k3 As Word
 Dim Von_k3 As Word

 Dim An_k4 As Word
 Dim Von_k4 As Word

 Dim An_k5 As Word
 Dim Von_k5 As Word

 Dim An_k6 As Word
 Dim Von_k6 As Word

 Dim An_k7 As Word
 Dim Von_k7 As Word

 Dim Sendeword As Word
 Dim Empfangsword As Word
 Dim Empfangene_kartenadresse As Byte

 Dim Schritt1 As Bit
 Schritt1 = 1
 Dim Schritt1a As Bit
 Dim Schritt2 As Bit
 Dim Schritt2a As Bit
 Dim Schritt3 As Bit

 Dim Sendeschritt1 As Bit
 Dim Sendeschritt2 As Bit

 Dim Err_falscher_teilnehmer As Bit
 Dim Err_fehlende_antwort As Bit
 Dim Err_falsche_protokolllaenge As Bit

 Dim Rack_bus_error As Bit
 Dim Karten_error As Bit

 Dim Watch_dog As Bit
 Dim Watchdogtimer As Bit


 ' Variablen zur Datenabwicklung UART / R-Bus

 Dim Rs485_count1 As Word


 ' Variablen zur Datenabwicklung UART1 / S-Hauptbus
 Dim Rs485_1_count1 As Word
 Dim S_bus_empfangsarray(15) As Byte
 Dim S_bus_sendearray(15) As Byte
 Dim S_bus_empfangschecksum As Byte
 Dim S_bus_sendechecksum As Byte
 Dim Datenmodus As Bit


' KOPPLERADRESSE ERRECHNEN

If Code1 = 0 Then
Koppleradresse = Koppleradresse + 1
End If

If Code2 = 0 Then
Koppleradresse = Koppleradresse + 2
End If

If Code3 = 0 Then
Koppleradresse = Koppleradresse + 4
End If

If Code4 = 0 Then
Koppleradresse = Koppleradresse + 8
End If

If Code5 = 0 Then
Koppleradresse = Koppleradresse + 16
End If

If Code6 = 0 Then
Koppleradresse = Koppleradresse + 32
End If

If Code7 = 0 Then
Koppleradresse = Koppleradresse + 64
End If

If Code8 = 0 Then
Koppleradresse = Koppleradresse + 128
End If


' Kopleradresse auf 255 begrenzen
If Koppleradresse >= 255 Then
Koppleradresse = 255
End If


' Koppleradresse für das Sendearray festlegen
S_bus_sendearray(1) = Koppleradresse


' ANZAHL DER ANGESCHLOSSENEN KARTEN ERMITTELN

 Ermittlung:

         ' Restdaten im Eingangspuffer löschen
         Clear Serialin

         ' Gesendete Daten als Adresse deklarieren (TXB8 High = Adresse ; TXB8 Low = Daten)
         Ucsr0b.txb8 = 1

         ' Anfrage an Kartenr. X senden
         Printbin Kartenadresse ;

         ' Die Karte hat 10ms Zeit zu antworten
         Waitms 10

         ' Überprüfen ob ein Zeichen im Empfangspuffer wartet.
         ' Wenn ja, das Zeichen abrufen und...
         If _rs_bufcountr0 > 0 Then

               If _rs_bufcountr0 = 1 Then
                  ' Teilnehmer hat seine Adresse korrekt zurück gesendet

                   Inputbin Empfangene_kartenadresse

                   ' Nur Karten die Ihre Adresse korrekt übermitteln werden Registriert
                   If Empfangene_kartenadresse = Kartenadresse Then

                        ' ...Eine Karte hinzu addieren
                        Incr Anzahl_karten

                        ' ...Kartenadresse um eins verringern
                        Decr Kartenadresse

                        ' Nach einer weiteren Karte suchen
                        Goto Ermittlung

                   End If


               End If



          ' wenn keine Rückmeldung, dann keine Karte gefunden...
         Else

            ' Restdaten im Eingangspuffer löschen
            Clear Serialin
          ' ... und Schleife wird verlassen

         End If





' HAUPTSCHLEIFE


Do

' RINGABFRAGE DER KARTEN

If Schritt1 = 1 And Anzahl_karten > 0 And Anlaufphase = 0 Then

   Clear Serialin

   ' Watchdogtimer starten
   Start Timer1

   ' Sendedaten und Kartenadresse zuordnen
   If Aktuelle_karte = 1 Then
   Kartenadresse = 255
   Sendeword = An_k1
   End If

   If Aktuelle_karte = 2 Then
   Kartenadresse = 254
   Sendeword = An_k2
   End If

   If Aktuelle_karte = 3 Then
   Kartenadresse = 253
   Sendeword = An_k3
   End If

   If Aktuelle_karte = 4 Then
   Kartenadresse = 252
   Sendeword = An_k4
   End If

   If Aktuelle_karte = 5 Then
   Kartenadresse = 251
   Sendeword = An_k5
   End If

   If Aktuelle_karte = 6 Then
   Kartenadresse = 250
   Sendeword = An_k6
   End If

   ' Sendedaten als Adresse deklarieren (TXB8 High = Adresse ; TXB8 Low = Daten)
   Ucsr0b.txb8 = 1

   Schritt1a = 1
   Schritt1 = 0

End If


' Warten bis das TXB8 bit gesetzt ist
If Schritt1a = 1 And Ucsr0b.txb8 = 1 Then

     ' Daten an Karte senden
   Printbin Kartenadresse ;

   ' Schritt2 für das Empfangen freigeben
   Schritt1a = 0
   Schritt2 = 1

End If



' Auf Rückmeldung der Karte warten
If Schritt2 = 1 Then

      ' Ein Byte wurde empfangen
      If _rs_bufcountr0 > 0 Then

            Err_fehlende_antwort = 0

            ' Quelladresse auslesen und mit gesendeter vergleichen
            Inputbin Empfangene_kartenadresse

               ' Die richtige Karte hat geantwortet
               If Empfangene_kartenadresse = Kartenadresse Then

                        ' Sende Daten als Daten deklarieren (TXB8 High = Adresse ; TXB8 Low = Daten)
                        Ucsr0b.txb8 = 0


                        Schritt2a = 1
                        Schritt2 = 0

               Else

                        Schritt2 = 0
                        Err_falscher_teilnehmer = 1

               End If

      Else

         Err_fehlende_antwort = 1

      End If

End If


' Warten bis das TXB8 bit zurückgesetzt ist
If Schritt2a = 1 And Ucsr0b.txb8 = 0 Then

      ' Daten an Karte senden
      Printbin Sendeword ;

      Schritt2a = 0
      Schritt3 = 1

End If


' Auf Daten von der Karte warten
If Schritt3 = 1 Then

   ' Wenn erstes Byte der Daten empfangen dann...
   If _rs_bufcountr0 > 0 Then

   Err_fehlende_antwort = 0
   Err_falsche_protokolllaenge = 1

      ' Sind beide Bytes im Puffer eingegangen, dann...
      If _rs_bufcountr0 = 2 Then

            ' Empfangszähler erhöhen
            Incr Rs485_count1

            ' 5 Zyklen lang warten ob weitere Bytes eingehen...
            If Rs485_count1 > 5 Then

               Rs485_count1 = 0

                  ' Stimmt die Anzahl an Daten noch überein, dann...
                  If _rs_bufcountr0 = 2 Then

                     Err_falsche_protokolllaenge = 0

                         ' Empfangswort auslesen
                         Inputbin Empfangsword


                         ' Empfangene Daten auf Speicherbereiche verteilen.
                         If Aktuelle_karte = 1 Then
                                   Von_k1 = Empfangsword
                         End If

                         If Aktuelle_karte = 2 Then
                                   Von_k2 = Empfangsword
                         End If

                         If Aktuelle_karte = 3 Then
                                   Von_k3 = Empfangsword
                         End If

                         If Aktuelle_karte = 4 Then
                                   Von_k4 = Empfangsword
                         End If

                         If Aktuelle_karte = 5 Then
                                   Von_k5 = Empfangsword
                         End If

                         If Aktuelle_karte = 6 Then
                                   Von_k6 = Empfangsword
                         End If

                         ' Aktuellen Teilnehmer um eins erhöhen
                         Incr Aktuelle_karte

                         ' Alle Teilnehmer durchgelaufen, wieder von vorne beginnen
                         If Aktuelle_karte > Anzahl_karten Then
                         Aktuelle_karte = 1
                         End If

                         ' WatschdogTimer zurücksetzen bzw. auf neuen Startwert einstellen (1s)
                         Timer1 = 34286

                         ' Schritt3 beenden
                         Schritt3 = 0
                         ' Schritt1 starten
                         Schritt1 = 1

                  End If
            End If
      End If

   Else

   Err_fehlende_antwort = 1

   End If

End If




' BUSKOPPLER WIRD ANGESPROCHEN


' Wenn erstes Byte eines Protokolls empfangen dann...
If _rs_bufcountr1 > 0 Then


    ' Der Koppler befindet sich im Adressmodus
    If Datenmodus = 0 Then

          ' Adresse auslesen
          Inputbin #1 , S_bus_empfangsarray(1) , 1

         ' Adresse mit eingestellter Koppleradresse vergleichen und prüfen ob Daten für mich.
         If S_bus_empfangsarray(1) = Koppleradresse Then

               ' Weiter mit Sendeschritt1
               Sendeschritt1 = 1

         End If


    End If



    ' Der Koppler befindet sich im Datenmodus
    If Datenmodus = 1 Then

         ' Sind die geforderten 14 Byte eingetroffen
         If _rs_bufcountr1 = 14 Then

            Incr Rs485_1_count1

            ' 10 Zyklen lang warten ob weitere Bytes eingehen.
            If Rs485_1_count1 > 10 Then

               Rs485_1_count1 = 0

               ' Ist die Anzahl an Bytes noch korrekt, dann...
               If _rs_bufcountr1 = 14 Then

                  ' Lese 14 Bytes aus dem Empfangspuffer und schreibe in Array ab Position 2
                  Inputbin #1 , S_bus_empfangsarray(2) , 14

                  ' Checksumme der empfangenen Bytes berechnen
                  S_bus_empfangschecksum = Checksumme_berechnen(s_bus_empfangsarray(1))

                    ' Empfangene Checksumme mit errechneter vergleichen
                     If S_bus_empfangschecksum = S_bus_empfangsarray(15) Then

                          ' Empfangene Bytes mappen.
                          Kopplersteuerbyte = S_bus_empfangsarray(2)
                          An_k1 = Makeint(s_bus_empfangsarray(3) , S_bus_empfangsarray(4))
                          An_k2 = Makeint(s_bus_empfangsarray(5) , S_bus_empfangsarray(6))
                          An_k3 = Makeint(s_bus_empfangsarray(7) , S_bus_empfangsarray(8))
                          An_k4 = Makeint(s_bus_empfangsarray(9) , S_bus_empfangsarray(10))
                          An_k5 = Makeint(s_bus_empfangsarray(11) , S_bus_empfangsarray(12))
                          An_k6 = Makeint(s_bus_empfangsarray(13) , S_bus_empfangsarray(14))


                          ' Sende Daten Mappen
                          S_bus_sendearray(2) = Kopplerstatusbyte
                          S_bus_sendearray(3) = Low(von_k1)
                          S_bus_sendearray(4) = High(von_k1)
                          S_bus_sendearray(5) = Low(von_k2)
                          S_bus_sendearray(6) = High(von_k2)
                          S_bus_sendearray(7) = Low(von_k3)
                          S_bus_sendearray(8) = High(von_k3)
                          S_bus_sendearray(9) = Low(von_k4)
                          S_bus_sendearray(10) = High(von_k4)
                          S_bus_sendearray(11) = Low(von_k5)
                          S_bus_sendearray(12) = High(von_k5)
                          S_bus_sendearray(13) = Low(von_k6)
                          S_bus_sendearray(14) = High(von_k6)

                          ' Checksumme der Sendebytes berechnen
                          S_bus_sendechecksum = Checksumme_berechnen(s_bus_sendearray(1))

                          ' Checksumme an das Sendearray übergeben
                          S_bus_sendearray(15) = S_bus_sendechecksum

                          ' Weiter mit Sendeschritt2
                          Sendeschritt2 = 1


                      End If

               End If

            End If

         End If

    End If



End If


' Prüfen ob der Koppler im Empfangsmodus ist
If Sendeschritt1 = 1 And Rs485dir1 = 0 Then

Waitus 500

         ' Timeouttimer starten
         Start Timer3

         ' wenn ja, dann Koppleradresse als Antwort senden
         Printbin #1 , Koppleradresse ;

         ' in den Datenmodus schalten
         Datenmodus = 1

         ' MPCM abschalten um Daten empfangen zu können
         Ucsr1a.mpcm = 0

         ' Sendeschritt1 beenden
         Sendeschritt1 = 0

End If


' Prüfen ob der Koppler im Empfangsmodus ist
If Sendeschritt2 = 1 And Rs485dir1 = 0 Then
 Waitus 500
         ' Sende 14 Bytes aus dem Bytearray ab Position 2
         Printbin #1 , S_bus_sendearray(2) , 14 ;

         ' in den Datenmodus abschalten
         Datenmodus = 0

         ' MPCM einschalten um Adressen empfangen zu können
         Ucsr1a.mpcm = 1

         ' Sendeschritt2 beenden
         Sendeschritt2 = 0

         ' TimeoutTimer zurücksetzen (Startwert für eine Sekunde)
         Timer3 = 34286

End If



'RACK-BUS FEHLER AUSWERTEN UND AUSGEBEN

If Watch_dog = 1 Then

   ' Kopplerstatus n.i.O.
   Kopplerstatusbyte.7 = 0

   ' Ringabfrage der Karten stoppen
   Schritt1 = 0
   Schritt2 = 0
   Schritt3 = 0

   ' Teilnehmer hat nicht geantwortet
   If Err_fehlende_antwort = 1 And Fehler_erkannt = 0 Then

          Fehler_erkannt = 1

         ' Fehlercode 8: Teilnehmer antwortet nicht
         Call Koppler_fehlercode(8)

   End If


   ' Falsche Protokolllänge empfangen
   If Err_falsche_protokolllaenge = 1 And Fehler_erkannt = 0 Then

          Fehler_erkannt = 1

           ' Fehlercode 5: Falsche Protokolllänge empfangen
          Call Koppler_fehlercode(5)

   End If


   ' Unerwarteter Teilnehmer hat geantwortet
   If Err_falscher_teilnehmer = 1 And Fehler_erkannt = 0 Then

         Fehler_erkannt = 1

         ' Fehlercode 7: Unerwarteter Teilnehmer hat geantwortet
          Call Koppler_fehlercode(7)

   End If



   ' FEHLER GENAUER DEFINIEREN
   If Karten_error = 0 And Rack_bus_error = 0 Then

         ' Eine Karte hat nicht innerhalb der vorgegebenen Zeit geantwortet
         ' Überprüfen ob die nächste Karte Antworten würde.
         Folge_karte = Aktuelle_karte + 1

         If Folge_karte > Anzahl_karten Then
         Folge_karte = 1
         End If

         ' Kartenadresse der nachfolgenden Karte ermitteln
         If Folge_karte = 1 Then
         Kartenadresse = 255
         End If
         If Folge_karte = 2 Then
         Kartenadresse = 254
         End If
         If Folge_karte = 3 Then
         Kartenadresse = 253
         End If
         If Folge_karte = 4 Then
         Kartenadresse = 252
         End If
         If Folge_karte = 5 Then
         Kartenadresse = 251
         End If
         If Folge_karte = 6 Then
         Kartenadresse = 250
         End If

        ' Restdaten im Eingangspuffer löschen
        Clear Serialin

        ' Gesendete Daten als Adresse deklarieren (TXB8 High = Adresse ; TXB8 Low = Daten)
         Ucsr0b.txb8 = 1

        ' Anfrage an Kartenr. X senden
        Printbin Kartenadresse ;                            'Leerbyte ; Leerbyte;

        ' Die Karte hat 10ms Zeit zu antworten
        Waitms 10

        ' Ein Zeichen empfangen und...
        If _rs_bufcountr0 > 0 Then

                  '... es bleibt bei einem Kartenfehler.

                    Karten_error = 1

                  ' An das Statusbyte übergeben um welche Karte es sich handelt.

                  Kopplerstatusbyte.2 = Aktuelle_karte.2
                  Kopplerstatusbyte.1 = Aktuelle_karte.1
                  Kopplerstatusbyte.0 = Aktuelle_karte.0

        Else
        ' Keine Antwort ...
                  '... es handelt sich um einen Rack-Busfehler


                    Rack_bus_error = 1

                    ' Fehlercode 9: R-Bus gestört, kein Teilnehmer antwortet mehr
                    Call Koppler_fehlercode(9)

        End If


   End If


   ' KARTENFEHLER AN ERROR LED AUSGEBEN
   If Karten_error = 1 Then

      Call Blink_code_karten_error

   End If


   ' RACKBUSFEHLER AN ERROR LED AUSGEBEN
   If Rack_bus_error = 1 Then

      Call Blink_code_rbus_error

   End If


End If



Loop